You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

134 lines
5.2 KiB

import { describe, expect, it } from 'vitest'
import { kinds } from 'nostr-tools'
import { ExtendedKind, FAST_READ_RELAY_URLS, FAST_WRITE_RELAY_URLS } from '@/constants'
import {
NEW_USER_BLOCKED_RELAY_URLS,
NEW_USER_HTTP_RELAY_URL,
NEW_USER_TRENDING_RELAY_URL,
buildNewUserTemplateDrafts,
newUserProfileDisplayName,
newUserProfileName,
newUserProfileSuffix
} from '@/lib/new-user-template'
import { newUserTemplatePublishRelays } from '@/lib/new-user-template-broadcast'
import { normalizeAnyRelayUrl } from '@/lib/url'
import type { TRelayList } from '@/types'
const TEST_PUBKEY = 'a'.repeat(63) + 'b'
function relayKey(url: string): string {
return (normalizeAnyRelayUrl(url) || url).toLowerCase()
}
function expectRelayKeys(actual: string[], expected: string[]) {
const actualKeys = new Set(actual.map(relayKey))
for (const url of expected) {
expect(actualKeys.has(relayKey(url))).toBe(true)
}
}
const templateRelayList = (): TRelayList => ({
write: [...FAST_WRITE_RELAY_URLS],
read: [...FAST_READ_RELAY_URLS],
originalRelays: [],
httpRead: [],
httpWrite: [NEW_USER_HTTP_RELAY_URL],
httpOriginalRelays: []
})
describe('newUserProfileSuffix', () => {
it('returns a number between 1000 and 9999', () => {
const suffix = newUserProfileSuffix(TEST_PUBKEY)
expect(suffix).toBeGreaterThanOrEqual(1000)
expect(suffix).toBeLessThanOrEqual(9999)
})
it('formats profile names with the suffix', () => {
const suffix = newUserProfileSuffix(TEST_PUBKEY)
expect(newUserProfileName(TEST_PUBKEY)).toBe(`ImwaldUser${suffix}`)
expect(newUserProfileDisplayName(TEST_PUBKEY)).toBe(`Imwald User ${suffix}`)
})
})
describe('buildNewUserTemplateDrafts', () => {
const drafts = buildNewUserTemplateDrafts(TEST_PUBKEY)
it('builds profile kind 0 with unique names', () => {
expect(drafts.profile.kind).toBe(kinds.Metadata)
const profile = JSON.parse(drafts.profile.content)
expect(profile.name).toBe(newUserProfileName(TEST_PUBKEY))
expect(profile.display_name).toBe(newUserProfileDisplayName(TEST_PUBKEY))
expect(profile.about).toContain('Imwald')
})
it('builds favorite relays kind 10012', () => {
expect(drafts.favoriteRelays.kind).toBe(ExtendedKind.FAVORITE_RELAYS)
const favorites = drafts.favoriteRelays.tags.filter((t) => t[0] === 'relay').map((t) => t[1])
expect(favorites).toContain(NEW_USER_TRENDING_RELAY_URL)
expect(favorites).toHaveLength(3)
})
it('builds blocked relays kind 10006 with dead relays', () => {
expect(drafts.blockedRelays.kind).toBe(ExtendedKind.BLOCKED_RELAYS)
const blocked = drafts.blockedRelays.tags.filter((t) => t[0] === 'relay').map((t) => t[1])
expect(blocked).toEqual([...NEW_USER_BLOCKED_RELAY_URLS])
})
it('splits mailbox read and write relays', () => {
expect(drafts.relayList.kind).toBe(kinds.RelayList)
const readTags = drafts.relayList.tags.filter((t) => t[0] === 'r' && t[2] === 'read')
const writeTags = drafts.relayList.tags.filter((t) => t[0] === 'r' && t[2] === 'write')
expect(readTags).toHaveLength(FAST_READ_RELAY_URLS.length)
expect(writeTags).toHaveLength(FAST_WRITE_RELAY_URLS.length)
})
it('builds HTTP relay list kind 10243 with mercury', () => {
expect(drafts.httpRelayList.kind).toBe(ExtendedKind.HTTP_RELAY_LIST)
expect(drafts.httpRelayList.tags.some((t) => t[1]?.includes('mercury-relay.imwald.eu'))).toBe(true)
})
it('builds interest list with expected topics', () => {
expect(drafts.interestList.kind).toBe(10015)
const topics = drafts.interestList.tags.filter((t) => t[0] === 't').map((t) => t[1])
expect(topics).toEqual([
'art',
'music',
'news',
'foodstr',
'coffeechain',
'travel',
'grownostr',
'plebchain'
])
})
it('builds empty follow and mute lists', () => {
expect(drafts.followList.kind).toBe(kinds.Contacts)
expect(drafts.followList.tags).toHaveLength(0)
expect(drafts.muteList.kind).toBe(10000)
expect(drafts.muteList.tags).toHaveLength(0)
})
})
describe('newUserTemplatePublishRelays', () => {
const relayList = templateRelayList()
it('caps list kinds to three stable write relays and skips flaky mirrors', () => {
const targets = newUserTemplatePublishRelays(10015, relayList)
expect(targets.length).toBeLessThanOrEqual(3)
expect(targets.map(relayKey)).not.toContain(relayKey('wss://relay.layer.systems'))
expect(targets.map(relayKey)).not.toContain(relayKey('wss://profiles.nostrver.se/'))
expect(targets.map(relayKey)).not.toContain(relayKey('wss://indexer.coracle.social/'))
expectRelayKeys(targets, [NEW_USER_HTTP_RELAY_URL])
})
it('adds profile relays for kind 0 and 10002 up to four targets', () => {
const profileTargets = newUserTemplatePublishRelays(kinds.Metadata, relayList)
expect(profileTargets.length).toBeLessThanOrEqual(4)
expectRelayKeys(profileTargets, [NEW_USER_HTTP_RELAY_URL, 'wss://profiles.nostr1.com'])
expect(profileTargets.map(relayKey)).not.toContain(relayKey('wss://indexer.coracle.social/'))
const relayListTargets = newUserTemplatePublishRelays(kinds.RelayList, relayList)
expect(relayListTargets.length).toBeLessThanOrEqual(4)
expectRelayKeys(relayListTargets, [NEW_USER_HTTP_RELAY_URL, 'wss://profiles.nostr1.com'])
})
})