Something went wrong. Try again.
Browser extension: detect and subscribe to standard.site publications on ATProto
Something went wrong. Try again.
7.7 kB · 208 lines
TypeScript
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209import { describe, expect, it } from 'vitest'import { badgeFor, iconStateFor, titleFor } from './icon'import type { IconState } from './icon'import type { PageState, PubInfo } from './types'
const ALL_STATES: IconState[] = [ 'idle', 'checking', 'none', 'offline', 'failed', 'blocked', 'detected', 'signedout', 'subscribed', 'detected-unverified', 'signedout-unverified', 'subscribed-unverified',]
const BADGED_STATES: IconState[] = ALL_STATES.filter( (s) => s !== 'idle' && s !== 'none' && s !== 'offline',)
const UNVERIFIED_STATES: IconState[] = [ 'detected-unverified', 'signedout-unverified', 'subscribed-unverified',]
function pub(verified: boolean): PubInfo { return { uri: 'at://did:plc:abc123/site.standard.publication/3kpubrkey', did: 'did:plc:abc123', pds: 'https://pds.example.com', record: { $type: 'site.standard.publication', url: 'https://blog.example.com', name: 'Blog' }, verified, }}
function state(overrides: Partial<PageState>): PageState { return { url: 'https://blog.example.com/post', fetchedAt: 0, ...overrides }}
describe('iconStateFor', () => { it('is idle when the tab has no detection state (non-http page)', () => { expect(iconStateFor(undefined)).toBe('idle') })
it('is none when the page was checked and no publication was found', () => { expect(iconStateFor(state({}))).toBe('none') })
it('is failed when detection could not run for this page', () => { expect(iconStateFor(state({ error: 'fetch-failed' }))).toBe('failed') })
it('is offline, not failed, when the browser has no connection', () => { expect(iconStateFor(state({ error: 'offline' }))).toBe('offline') })
it('is blocked when the publication belongs to a blocked account', () => { expect(iconStateFor(state({ pub: pub(true), blocked: true, subscriptionRkey: null }))).toBe( 'blocked', ) })
it('prefers blocked over every other publication state', () => { expect(iconStateFor(state({ pub: pub(true), blocked: true, subscriptionRkey: '3ksub' }))).toBe( 'blocked', ) expect(iconStateFor(state({ pub: pub(false), blocked: true }))).toBe('blocked') })
it('does not claim a block when the block list is unknown', () => { expect(iconStateFor(state({ pub: pub(true), subscriptionRkey: null }))).toBe('detected') })
it('is subscribed when a subscription rkey is known', () => { expect(iconStateFor(state({ pub: pub(true), subscriptionRkey: '3ksub' }))).toBe('subscribed') })
it('is detected for a verified publication the user is not subscribed to', () => { expect(iconStateFor(state({ pub: pub(true), subscriptionRkey: null }))).toBe('detected') })
it('is signedout when subscription state is unknown', () => { expect(iconStateFor(state({ pub: pub(true), subscriptionRkey: undefined }))).toBe('signedout') })
// The bug this split fixes: a subscription used to swallow the verification // warning outright, so the badge said "✓, all well" on a page the popup was // simultaneously calling unverified. it('keeps the subscription and the verification warning together', () => { expect(iconStateFor(state({ pub: pub(false), subscriptionRkey: '3ksub' }))).toBe( 'subscribed-unverified', ) })
it('qualifies every other relation the same way', () => { expect(iconStateFor(state({ pub: pub(false), subscriptionRkey: null }))).toBe( 'detected-unverified', ) expect(iconStateFor(state({ pub: pub(false), subscriptionRkey: undefined }))).toBe( 'signedout-unverified', ) })})
describe('badgeFor', () => { it('shows no badge when there is nothing worth noticing', () => { for (const s of ['idle', 'none', 'offline'] as const) { expect(badgeFor(s), s).toBeNull() } })
it('uses green with a relationship glyph for every verified publication state', () => { expect(badgeFor('detected')).toEqual({ text: '+', background: '#1a7f37', color: '#ffffff' }) expect(badgeFor('signedout')?.text).toBe('?') expect(badgeFor('subscribed')?.text).toBe('✓') for (const s of ['detected', 'signedout', 'subscribed'] as const) { expect(badgeFor(s)?.background).toBe('#1a7f37') } })
it('marks an unverified page with a * on the relation glyph, in amber', () => { for (const s of UNVERIFIED_STATES) { const verified = s.replace('-unverified', '') as IconState expect(badgeFor(s)?.text, s).toBe(`${badgeFor(verified)?.text}*`) expect(badgeFor(s)?.background, s).toBe('#d4a72c') } })
it('reserves red for the one state the user should stop at', () => { expect(badgeFor('blocked')).toEqual({ text: 'X', background: '#cf222e', color: '#ffffff' }) for (const s of ALL_STATES.filter((s) => s !== 'blocked')) { expect(badgeFor(s)?.background, s).not.toBe('#cf222e') } })
it('uses dark text on every amber badge', () => { for (const s of ['failed', ...UNVERIFIED_STATES] as IconState[]) { expect(badgeFor(s)?.background, s).toBe('#d4a72c') expect(badgeFor(s)?.color, s).toBe('#24292f') } })
// `!` used to mean both "unverified candidate" and "could not check". Now // the `*` states carry the first, so a bare `!` is only ever the second. it('keeps the bare ! for detection failing outright', () => { expect(badgeFor('failed')?.text).toBe('!') for (const s of ALL_STATES.filter((s) => s !== 'failed')) { expect(badgeFor(s)?.text ?? '', s).not.toContain('!') } })
it('gives every badged state a distinct visible glyph, never color alone', () => { const glyphs = BADGED_STATES.map((s) => badgeFor(s)?.text) for (const g of glyphs) expect(g?.trim()).toBeTruthy() expect(new Set(glyphs).size).toBe(BADGED_STATES.length) })
it('keeps badge text at most two glyphs (Chrome truncates at 4)', () => { for (const s of ALL_STATES) { const text = [...(badgeFor(s)?.text ?? '')] expect(text.length, s).toBeLessThanOrEqual(2) // The second is only ever the modifier; the badge never shows two // states at once. if (text.length === 2) expect(text[1], s).toBe('*') } })})
describe('titleFor', () => { it('restores the default title for idle (non-http pages)', () => { expect(titleFor('idle')).toBeNull() })
it('gives every non-idle state a distinct title naming the extension', () => { const states = ALL_STATES.filter((s) => s !== 'idle') const titles = states.map((s) => titleFor(s)) for (const t of titles) expect(t).toMatch(/^substandard — /) expect(new Set(titles).size).toBe(states.length) })
it('speaks for the badge-less states, whose only voice it is', () => { expect(titleFor('none')).toContain('no publication') expect(titleFor('offline')).toContain('offline') })
it('spells out states the badge shows only as a glyph', () => { expect(titleFor('detected')).toContain('publication detected') expect(titleFor('signedout')).toContain('unknown') expect(titleFor('blocked')).toContain('blocked') expect(titleFor('failed')).toContain('could not check') })
// The * is the whole point of the state, so the words have to carry both // halves — the relation the reader has, and the caveat on the page. it('says both halves for a * state', () => { for (const s of UNVERIFIED_STATES) { expect(titleFor(s), s).toContain('not the verified publisher') } expect(titleFor('subscribed-unverified')).toContain('subscribed') expect(titleFor('detected-unverified')).toContain('publication detected') expect(titleFor('signedout-unverified')).toContain('unknown') })})