diff --git a/packages/ditto/controllers/api/statuses.ts b/packages/ditto/controllers/api/statuses.ts index 53fab57a..116ad2de 100644 --- a/packages/ditto/controllers/api/statuses.ts +++ b/packages/ditto/controllers/api/statuses.ts @@ -16,6 +16,7 @@ import { lookupPubkey } from '@/utils/lookup.ts'; import { languageSchema } from '@/schema.ts'; import { hydrateEvents } from '@/storages/hydrate.ts'; import { assertAuthenticated, createEvent, parseBody, updateListEvent } from '@/utils/api.ts'; +import { getCustomEmojis } from '@/utils/custom-emoji.ts'; import { getInvoice, getLnurl } from '@/utils/lnurl.ts'; import { purifyEvent } from '@/utils/purify.ts'; import { getZapSplits } from '@/utils/zap-split.ts'; @@ -190,6 +191,23 @@ const createStatusController: AppController = async (c) => { } } + const shortcodes = new Set(); + + for (const [, shortcode] of data.status?.matchAll(/(? { })); }); -interface GetCustomEmojisOpts { - relay: NRelay; - signal?: AbortSignal; -} - -async function getCustomEmojis( - pubkey: string, - opts: GetCustomEmojisOpts, -): Promise> { - const { relay, signal } = opts; - - const emojis = new Map(); - - const [emojiList] = await relay.query([{ kinds: [10030], authors: [pubkey] }], { signal }); - - if (!emojiList) { - return emojis; - } - - const a = new Set(); - - for (const tag of emojiList.tags) { - if (tag[0] === 'emoji') { - const [, shortcode, url] = tag; - - if (!emojis.has(shortcode)) { - try { - emojis.set(shortcode, { url: new URL(url) }); - } catch { - // continue - } - } - } - - if (tag[0] === 'a') { - a.add(tag[1]); - } - } - - const filters: NostrFilter[] = []; - - for (const addr of a) { - const match = addr.match(/^30030:([0-9a-f]{64}):(.+)$/); - - if (match) { - const [, pubkey, d] = match; - filters.push({ kinds: [30030], authors: [pubkey], '#d': [d] }); - } - } - - if (!filters.length) { - return new Map(); - } - - for (const event of await relay.query(filters, { signal })) { - const d = event.tags.find(([name]) => name === 'd')?.[1]; - - for (const [t, shortcode, url] of event.tags) { - if (t === 'emoji') { - if (!emojis.has(shortcode)) { - try { - emojis.set(shortcode, { url: new URL(url), category: d }); - } catch { - // continue - } - } - } - } - } - - return emojis; -} - export default route; diff --git a/packages/ditto/utils/custom-emoji.ts b/packages/ditto/utils/custom-emoji.ts new file mode 100644 index 00000000..8dbcd7a8 --- /dev/null +++ b/packages/ditto/utils/custom-emoji.ts @@ -0,0 +1,74 @@ +import type { NostrFilter, NRelay } from '@nostrify/nostrify'; + +interface GetCustomEmojisOpts { + relay: NRelay; + signal?: AbortSignal; +} + +export async function getCustomEmojis( + pubkey: string, + opts: GetCustomEmojisOpts, +): Promise> { + const { relay, signal } = opts; + + const emojis = new Map(); + + const [emojiList] = await relay.query([{ kinds: [10030], authors: [pubkey] }], { signal }); + + if (!emojiList) { + return emojis; + } + + const a = new Set(); + + for (const tag of emojiList.tags) { + if (tag[0] === 'emoji') { + const [, shortcode, url] = tag; + + if (!emojis.has(shortcode)) { + try { + emojis.set(shortcode, { url: new URL(url) }); + } catch { + // continue + } + } + } + + if (tag[0] === 'a') { + a.add(tag[1]); + } + } + + const filters: NostrFilter[] = []; + + for (const addr of a) { + const match = addr.match(/^30030:([0-9a-f]{64}):(.+)$/); + + if (match) { + const [, pubkey, d] = match; + filters.push({ kinds: [30030], authors: [pubkey], '#d': [d] }); + } + } + + if (!filters.length) { + return new Map(); + } + + for (const event of await relay.query(filters, { signal })) { + const d = event.tags.find(([name]) => name === 'd')?.[1]; + + for (const [t, shortcode, url] of event.tags) { + if (t === 'emoji') { + if (!emojis.has(shortcode)) { + try { + emojis.set(shortcode, { url: new URL(url), category: d }); + } catch { + // continue + } + } + } + } + } + + return emojis; +}