{"version":3,"sources":["../src/waypoints.data.ts","../src/requestDeadline.ts","../src/upstreamFetch.ts","../src/uriParser.ts","../src/reverseParsers.ts","../src/resolve.ts","../src/universalLinks.ts"],"names":["identifier","seg"],"mappings":"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","file":"index.cjs","sourcesContent":["export type WaypointType = 'post' | 'profile' | 'list' | 'record' | 'unknown';\n\n/**\n * Keys identifying which \"data family\" a waypoint belongs to for auto-redirect\n * purposes. Two waypoints can only be the endpoints of an auto-redirect when\n * they share at least one family key (i.e. they render the same underlying\n * atproto collections). Display groupings live in `WAYPOINT_CATEGORIES_DATA`\n * and are independent of this.\n */\nexport type RedirectCompatFamily =\n  | 'bluesky-social'\n  | 'standard-site'\n  | 'tangled'\n  | 'margin'\n  | 'grain'\n  | 'pinksky'\n  | 'semble'\n  | 'streamplace'\n  | 'popfeed'\n  | 'sifa'\n  | 'blento'\n  | 'atproto-explorer';\n\n/**\n * A client's support for Bluesky-style *compose intent links*: a URL that opens\n * the app's composer, optionally pre-filled with text.\n * See https://docs.bsky.app/docs/advanced-guides/intent-links.\n *\n * bsky.app established `/intent/compose?text=…`, and the social-app forks in the\n * catalog inherit the same route, so a link built for one works on any of them.\n * Only add an entry once the client's own route has been confirmed — a link to\n * a client that doesn't handle it lands the user on a 404 or an empty home feed.\n */\nexport type ComposeIntentData = {\n  /**\n   * The compose route, absolute and free of any query string\n   * (e.g. `https://bsky.app/intent/compose`).\n   */\n  url: string;\n  /**\n   * Query parameter carrying the pre-filled post text. Omitted when the client\n   * routes the intent but ignores the text: the link still opens a composer,\n   * just an empty one. Check this before offering a \"share this to…\" affordance,\n   * since there the text is the whole point.\n   *\n   * Bluesky's post limit is 300 grapheme clusters; longer text is the caller's\n   * problem to truncate.\n   */\n  textParam?: string;\n  /**\n   * Deep link into the client's native app for the same intent, when it\n   * publishes a scheme (e.g. `bluesky://intent/compose`).\n   */\n  appUrl?: string;\n};\n\nexport type WaypointData = {\n  id: string;\n  name: string;\n  description: string | ((collection?: string, type?: WaypointType) => string);\n  getUrl: (handle: string, collection?: string, rkey?: string, did?: string) => string | null;\n  supportedTypes: WaypointType[];\n  category: string;\n  /**\n   * Compose intent support, when the client has a confirmed intent route.\n   * Absent means \"no known support\" rather than a proven absence — read it with\n   * `supportsComposeIntent` / `getComposeIntentUrl`.\n   */\n  composeIntent?: ComposeIntentData;\n  /**\n   * Data families this waypoint participates in. Auto-redirect rules are only\n   * emitted between waypoints that share at least one family. An empty array\n   * means the waypoint can never be an auto-redirect source *or* destination\n   * (dev tools / generic record viewers land here by design).\n   */\n  redirectCompat: RedirectCompatFamily[];\n  /**\n   * NSID prefixes that signal this waypoint is meaningfully usable for the\n   * target repo. When set, the extension can call describeRepo on the target\n   * DID and check whether any of the user's collections start with one of\n   * these prefixes — if none do, the waypoint is flagged as \"no records\n   * found\" in the popup and demoted in smart recommendations.\n   *\n   * Use trailing-dot prefixes for whole namespaces (e.g. `'sh.tangled.'`)\n   * or full NSIDs for single-collection apps. Atmosphere apps typically\n   * declare a reversed-domain prefix (`semble.so` → `so.semble.`) so the\n   * popup can flag accounts that haven't published any of that app's\n   * records. Omit the field entirely for generic explorers (PDSls,\n   * atp.tools, Aturi) — those stay in the \"unknown\" / no-opinion state.\n   */\n  expectedCollections?: string[];\n};\n\nexport type CompatFamilyMeta = {\n  id: RedirectCompatFamily;\n  name: string;\n  description: string;\n};\n\n/**\n * Registry of compat families. `description` is shown in the options UI so the\n * user understands what each \"Favorite for X\" controls.\n */\nexport const COMPAT_FAMILIES: Record<RedirectCompatFamily, CompatFamilyMeta> = {\n  'bluesky-social': {\n    id: 'bluesky-social',\n    name: 'Bluesky clients',\n    description: 'Apps that render bsky posts, profiles, and lists at /profile/:handle.',\n  },\n  'standard-site': {\n    id: 'standard-site',\n    name: 'Publications',\n    description: 'Readers for Standard Site and Leaflet publications.',\n  },\n  tangled: {\n    id: 'tangled',\n    name: 'Tangled',\n    description: 'Tangled repositories and related records.',\n  },\n  margin: {\n    id: 'margin',\n    name: 'Margin',\n    description: 'Annotations, highlights, and bookmarks on margin.at.',\n  },\n  grain: {\n    id: 'grain',\n    name: 'Grain',\n    description: 'Photo galleries on grain.social.',\n  },\n  pinksky: {\n    id: 'pinksky',\n    name: 'Pinkleap',\n    description: 'Pinkleap browsing experience.',\n  },\n  semble: {\n    id: 'semble',\n    name: 'Semble',\n    description: 'Semble profiles.',\n  },\n  streamplace: {\n    id: 'streamplace',\n    name: 'Streamplace',\n    description: 'Streamplace profiles.',\n  },\n  popfeed: {\n    id: 'popfeed',\n    name: 'Popfeed',\n    description: 'Popfeed profiles.',\n  },\n  sifa: {\n    id: 'sifa',\n    name: 'Sifa',\n    description: 'Sifa profiles.',\n  },\n  blento: {\n    id: 'blento',\n    name: 'Blento',\n    description: 'Blento profiles.',\n  },\n  'atproto-explorer': {\n    id: 'atproto-explorer',\n    name: 'Record explorers',\n    description:\n      'Raw AT Protocol record explorers (pdsls, atp.tools, Aturi Explore) that render any record by its AT URI.',\n  },\n};\n\nexport const COMPAT_FAMILY_ORDER: RedirectCompatFamily[] = [\n  'bluesky-social',\n  'standard-site',\n  'pinksky',\n  'tangled',\n  'margin',\n  'grain',\n  'semble',\n  'streamplace',\n  'popfeed',\n  'sifa',\n  'blento',\n  'atproto-explorer',\n];\n\nexport type WaypointCategoryData = {\n  id: string;\n  name: string;\n  description?: string;\n  defaultWaypointId: string;\n  subcategories?: WaypointCategoryData[];\n};\n\nexport type CategorizedWaypointsData = {\n  category: WaypointCategoryData;\n  waypoints: WaypointData[];\n};\n\n/**\n * The `/intent/compose?text=…` shape bsky.app established and every social-app\n * fork inherits verbatim, down to the parameter name.\n */\nfunction socialAppComposeIntent(origin: string): ComposeIntentData {\n  return { url: `${origin}/intent/compose`, textParam: 'text' };\n}\n\nexport const WAYPOINT_DESTINATIONS_DATA: Record<string, WaypointData> = {\n  aturi: {\n    id: 'aturi',\n    name: 'Aturi',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on aturi.to';\n      if (collection === 'app.bsky.graph.list') return 'View list on aturi.to';\n      if (collection?.startsWith('site.standard.') || collection?.startsWith('pub.leaflet.')) {\n        return 'View document on aturi.to';\n      }\n      if (collection) return 'View record on aturi.to';\n      return 'View profile on aturi.to';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://aturi.to/profile/${handle}/post/${rkey}`;\n        }\n        if (collection === 'app.bsky.graph.list') {\n          return `https://aturi.to/profile/${handle}/lists/${rkey}`;\n        }\n        // Generic AT-record viewer; prefer the DID (stable across handle changes)\n        // when one is available, falling back to the handle otherwise.\n        const identifier = did || handle;\n        return `https://aturi.to/profile/${identifier}/${collection}/${rkey}`;\n      }\n      return `https://aturi.to/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['bluesky-social', 'standard-site'],\n  },\n\n  anisota: {\n    id: 'anisota',\n    name: 'Anisota',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on anisota.net';\n      if (collection === 'app.bsky.graph.list') return 'View list on anisota.net';\n      if (collection?.startsWith('site.standard.') || collection?.startsWith('pub.leaflet.')) {\n        return 'View document on anisota.net';\n      }\n      return 'View profile on anisota.net';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://anisota.net/profile/${handle}/post/${rkey}`;\n        }\n        if (collection === 'app.bsky.graph.list') {\n          return `https://anisota.net/profile/${handle}/lists/${rkey}`;\n        }\n        if (collection.startsWith('site.standard.') || collection.startsWith('pub.leaflet.')) {\n          // Anisota's document viewer addresses records by DID when available.\n          const identifier = did || handle;\n          return `https://anisota.net/profile/${identifier}/document/${rkey}`;\n        }\n        return `https://anisota.net/profile/${handle}`;\n      }\n      return `https://anisota.net/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'blueskyClients',\n    // Anisota implements the Bluesky shape deliberately, then extends it with\n    // `url`, `tags`, `channel`, and `title` (and answers `/post` with the same\n    // query). What's declared here is the interoperable subset every caller can\n    // rely on; the extras are Anisota-only and unrepresentable in this field.\n    composeIntent: socialAppComposeIntent('https://anisota.net'),\n    // Bluesky-shaped records only. anisota.net also reads Standard Site and\n    // Leaflet documents, but that role belongs to `anisotaReader`: listing both\n    // under `standard-site` put two entries for the same site in every\n    // \"Publications\" destination list, and this one's `expectedCollections`\n    // already says it does not claim those collections.\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.', 'net.anisota.'],\n  },\n\n  bluesky: {\n    id: 'bluesky',\n    name: 'Bluesky',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on bsky.app';\n      if (collection === 'app.bsky.graph.list') return 'View list on bsky.app';\n      return 'View profile on bsky.app';\n    },\n    getUrl: (handle, collection, rkey) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://bsky.app/profile/${handle}/post/${rkey}`;\n        }\n        if (collection === 'app.bsky.graph.list') {\n          return `https://bsky.app/profile/${handle}/lists/${rkey}`;\n        }\n        return `https://bsky.app/profile/${handle}`;\n      }\n      return `https://bsky.app/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'blueskyClients',\n    composeIntent: {\n      ...socialAppComposeIntent('https://bsky.app'),\n      appUrl: 'bluesky://intent/compose',\n    },\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  blacksky: {\n    id: 'blacksky',\n    name: 'Blacksky',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on blacksky.community';\n      if (collection === 'app.bsky.graph.list') return 'View list on blacksky.community';\n      return 'View profile on blacksky.community';\n    },\n    getUrl: (handle, collection, rkey) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://blacksky.community/profile/${handle}/post/${rkey}`;\n        }\n        if (collection === 'app.bsky.graph.list') {\n          return `https://blacksky.community/profile/${handle}/lists/${rkey}`;\n        }\n        return `https://blacksky.community/profile/${handle}`;\n      }\n      return `https://blacksky.community/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'blueskyForks',\n    composeIntent: socialAppComposeIntent('https://blacksky.community'),\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  reddwarf: {\n    id: 'reddwarf',\n    name: 'Red Dwarf',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on reddwarf.app';\n      return 'View profile on reddwarf.app';\n    },\n    getUrl: (handle, collection, rkey) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://reddwarf.app/profile/${handle}/post/${rkey}`;\n        }\n        return `https://reddwarf.app/profile/${handle}`;\n      }\n      return `https://reddwarf.app/profile/${handle}`;\n    },\n    // No `list`: unlike the social-app forks in this family, Red Dwarf has no\n    // `/profile/:handle/lists/:rkey` route, so offering it for a list would\n    // silently land the user on the list's author instead.\n    supportedTypes: ['post', 'profile', 'record'],\n    category: 'blueskyClients',\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  impro: {\n    id: 'impro',\n    name: 'Impro',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on impro.social';\n      if (collection === 'app.bsky.graph.list') return 'View list on impro.social';\n      return 'View profile on impro.social';\n    },\n    getUrl: (handle, collection, rkey) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://impro.social/profile/${handle}/post/${rkey}`;\n        }\n        if (collection === 'app.bsky.graph.list') {\n          return `https://impro.social/profile/${handle}/lists/${rkey}`;\n        }\n        return `https://impro.social/profile/${handle}`;\n      }\n      return `https://impro.social/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'blueskyClients',\n    // Impro routes /intent/compose to its home view, which opens the composer\n    // for a signed-in user — but it never reads `?text`, so no textParam here.\n    composeIntent: { url: 'https://impro.social/intent/compose' },\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  lea: {\n    id: 'lea',\n    name: 'Lea',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on lea.ac';\n      return 'View profile on lea.ac';\n    },\n    getUrl: (handle, collection, rkey) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://lea.ac/profile/${handle}/post/${rkey}`;\n        }\n        return `https://lea.ac/profile/${handle}`;\n      }\n      return `https://lea.ac/profile/${handle}`;\n    },\n    // No `list`: like Red Dwarf, Lea serves only `/profile/:handle` and\n    // `/profile/:handle/post/:rkey` — `/lists/:rkey` 404s — so claiming list\n    // support would drop the user on an error page instead of the list.\n    supportedTypes: ['post', 'profile', 'record'],\n    category: 'blueskyClients',\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  leaflet: {\n    id: 'leaflet',\n    name: 'Leaflet',\n    description: 'View profile on leaflet.pub',\n    getUrl: (handle) => {\n      return `https://leaflet.pub/p/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'publications',\n    redirectCompat: ['standard-site'],\n    expectedCollections: ['pub.leaflet.', 'site.standard.'],\n  },\n\n  pdsls: {\n    id: 'pdsls',\n    name: 'PDSls',\n    description: 'View raw record on pdsls.dev',\n    getUrl: (handle, collection, rkey, did) => {\n      const identifier = did || handle;\n      if (collection && rkey) {\n        return `https://pdsls.dev/at://${identifier}/${collection}/${rkey}`;\n      }\n      return `https://pdsls.dev/at://${identifier}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'devTools',\n    redirectCompat: ['atproto-explorer'],\n  },\n\n  aturiExplore: {\n    id: 'aturiExplore',\n    name: 'Aturi Explore',\n    description: (collection) => {\n      if (collection) return 'Inspect record on aturi.to/explore';\n      return 'Browse repo on aturi.to/explore';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      // The explorer keys URLs by DID when available so handle changes don't\n      // break shared links. Falls back to the handle when no DID was passed.\n      const identifier = did || handle;\n      if (collection && rkey) {\n        return `https://aturi.to/explore/${identifier}/${collection}/${encodeURIComponent(rkey)}`;\n      }\n      if (collection) {\n        return `https://aturi.to/explore/${identifier}/${collection}`;\n      }\n      return `https://aturi.to/explore/${identifier}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'devTools',\n    redirectCompat: ['atproto-explorer'],\n  },\n\n  atptools: {\n    id: 'atptools',\n    name: 'atp.tools',\n    description: 'View raw record on atp.tools',\n    getUrl: (handle, collection, rkey, did) => {\n      const identifier = did || handle;\n      if (collection && rkey) {\n        return `https://atp.tools/at:/${identifier}/${collection}/${rkey}`;\n      }\n      return `https://atp.tools/at:/${identifier}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'devTools',\n    redirectCompat: ['atproto-explorer'],\n  },\n\n  bluepy: {\n    id: 'bluepy',\n    name: 'Bluepy',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on bluepy.social';\n      if (collection === 'app.bsky.graph.list') return 'View list on bluepy.social';\n      if (collection) return 'View record on bluepy.social';\n      return 'View profile on bluepy.social';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      const identifier = did || handle;\n      if (collection && rkey) {\n        return `https://bluepy.social/at://${identifier}/${collection}/${rkey}`;\n      }\n      return `https://bluepy.social/at://${identifier}/app.bsky.actor.profile/self`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'blueskyClients',\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  witchsky: {\n    id: 'witchsky',\n    name: 'Witchsky',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on witchsky.app';\n      if (collection === 'app.bsky.graph.list') return 'View list on witchsky.app';\n      return 'View profile on witchsky.app';\n    },\n    getUrl: (handle, collection, rkey) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://witchsky.app/profile/${handle}/post/${rkey}`;\n        }\n        if (collection === 'app.bsky.graph.list') {\n          return `https://witchsky.app/profile/${handle}/lists/${rkey}`;\n        }\n        return `https://witchsky.app/profile/${handle}`;\n      }\n      return `https://witchsky.app/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'blueskyForks',\n    composeIntent: socialAppComposeIntent('https://witchsky.app'),\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  deer: {\n    id: 'deer',\n    name: 'Deer',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on deer.social';\n      if (collection === 'app.bsky.graph.list') return 'View list on deer.social';\n      return 'View profile on deer.social';\n    },\n    getUrl: (handle, collection, rkey) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://deer.social/profile/${handle}/post/${rkey}`;\n        }\n        if (collection === 'app.bsky.graph.list') {\n          return `https://deer.social/profile/${handle}/lists/${rkey}`;\n        }\n        return `https://deer.social/profile/${handle}`;\n      }\n      return `https://deer.social/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'blueskyForks',\n    composeIntent: socialAppComposeIntent('https://deer.social'),\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  mu: {\n    id: 'mu',\n    name: 'Mu',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on mu.social';\n      if (collection === 'app.bsky.graph.list') return 'View list on mu.social';\n      return 'View profile on mu.social';\n    },\n    getUrl: (handle, collection, rkey) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://mu.social/profile/${handle}/post/${rkey}`;\n        }\n        if (collection === 'app.bsky.graph.list') {\n          return `https://mu.social/profile/${handle}/lists/${rkey}`;\n        }\n        return `https://mu.social/profile/${handle}`;\n      }\n      return `https://mu.social/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'blueskyForks',\n    composeIntent: socialAppComposeIntent('https://mu.social'),\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  northsky: {\n    id: 'northsky',\n    name: 'Northsky',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on northsky.app';\n      if (collection === 'app.bsky.graph.list') return 'View list on northsky.app';\n      return 'View profile on northsky.app';\n    },\n    getUrl: (handle, collection, rkey) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          return `https://northsky.app/profile/${handle}/post/${rkey}`;\n        }\n        if (collection === 'app.bsky.graph.list') {\n          return `https://northsky.app/profile/${handle}/lists/${rkey}`;\n        }\n        return `https://northsky.app/profile/${handle}`;\n      }\n      return `https://northsky.app/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'blueskyForks',\n    composeIntent: socialAppComposeIntent('https://northsky.app'),\n    redirectCompat: ['bluesky-social'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  tangled: {\n    id: 'tangled',\n    name: 'Tangled',\n    description: 'View profile on tangled.org',\n    getUrl: (handle) => {\n      return `https://tangled.org/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['tangled'],\n    expectedCollections: ['sh.tangled.'],\n  },\n\n\n  pinksky: {\n    id: 'pinksky',\n    name: 'Pinkleap',\n    description: (collection) => {\n      if (collection === 'app.bsky.feed.post') return 'View post on pinkleap.app';\n      return 'View profile on pinkleap.app';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      if (collection && rkey) {\n        if (collection === 'app.bsky.feed.post') {\n          const identifier = did || handle;\n          const atUri = `at://${identifier}/${collection}/${rkey}`;\n          const encodedUri = encodeURIComponent(atUri);\n          const encodedDid = encodeURIComponent(identifier);\n          return `https://pinkleap.app/feed?uri=${encodedUri}&src=profile&index=1&did=${encodedDid}&showThreads=${encodedDid}`;\n        }\n        return `https://pinkleap.app/profile/${handle}`;\n      }\n      return `https://pinkleap.app/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['pinksky'],\n    expectedCollections: ['app.bsky.'],\n  },\n\n  margin: {\n    id: 'margin',\n    name: 'Margin',\n    description: (collection) => {\n      if (collection === 'at.margin.annotation') return 'View annotation on margin.at';\n      if (collection === 'at.margin.highlight') return 'View highlight on margin.at';\n      if (collection === 'at.margin.bookmark') return 'View bookmark on margin.at';\n      if (collection?.startsWith('at.margin.')) return 'View on margin.at';\n      return 'View profile on margin.at';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      if (collection && rkey && collection.startsWith('at.margin.')) {\n        const recordType = collection.replace('at.margin.', '');\n        const identifier = did || handle;\n\n        if (recordType === 'annotation' || recordType === 'highlight' || recordType === 'bookmark') {\n          const handleLooksLikeDomain = handle.includes('.') && !handle.startsWith('did:');\n          const domain = handleLooksLikeDomain ? handle : identifier;\n\n          return `https://margin.at/${domain}/${recordType}/${rkey}`;\n        }\n\n        return `https://margin.at/profile/${identifier}`;\n      }\n\n      const identifier = did || handle;\n      return `https://margin.at/profile/${identifier}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['margin'],\n    expectedCollections: ['at.margin.'],\n  },\n\n  semble: {\n    id: 'semble',\n    name: 'Semble',\n    description: 'View profile on semble.so',\n    getUrl: (handle) => {\n      return `https://semble.so/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['semble'],\n    expectedCollections: ['so.semble.'],\n  },\n\n  streamplace: {\n    id: 'streamplace',\n    name: 'Streamplace',\n    description: 'View profile on stream.place',\n    getUrl: (handle) => {\n      return `https://stream.place/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['streamplace'],\n    expectedCollections: ['place.stream.'],\n  },\n\n  grain: {\n    id: 'grain',\n    name: 'Grain',\n    description: (collection) => {\n      if (collection === 'social.grain.gallery') return 'View gallery on grain.social';\n      return 'View profile on grain.social';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      const identifier = did || handle;\n      if (collection === 'social.grain.gallery' && rkey) {\n        return `https://grain.social/profile/${identifier}/gallery/${rkey}`;\n      }\n      return `https://grain.social/profile/${identifier}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['grain'],\n    expectedCollections: ['social.grain.'],\n  },\n\n  popfeed: {\n    id: 'popfeed',\n    name: 'Popfeed',\n    description: 'View profile on popfeed.social',\n    getUrl: (handle, collection, rkey, did) => {\n      const identifier = did || handle;\n      return `https://popfeed.social/profile/${identifier}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['popfeed'],\n    expectedCollections: ['social.popfeed.'],\n  },\n\n  sifa: {\n    id: 'sifa',\n    name: 'Sifa',\n    description: 'View profile on sifa.id',\n    getUrl: (handle) => {\n      return `https://sifa.id/p/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['sifa'],\n    expectedCollections: ['id.sifa.'],\n  },\n\n  blento: {\n    id: 'blento',\n    name: 'Blento',\n    description: 'View profile on blento.app',\n    getUrl: (handle) => {\n      return `https://blento.app/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'atmosphereApps',\n    redirectCompat: ['blento'],\n    expectedCollections: ['app.blento.'],\n  },\n\n  anisotaReader: {\n    id: 'anisotaReader',\n    name: 'Anisota Reader',\n    description: (collection) => {\n      if (collection?.startsWith('site.standard.') || collection?.startsWith('pub.leaflet.')) {\n        return 'Read document on anisota.net';\n      }\n      return 'View publications on anisota.net';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      if (collection && rkey) {\n        if (collection.startsWith('site.standard.') || collection.startsWith('pub.leaflet.')) {\n          const identifier = did || handle;\n          return `https://anisota.net/profile/${identifier}/document/${rkey}`;\n        }\n      }\n      return `https://anisota.net/profile/${handle}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'publications',\n    redirectCompat: ['standard-site'],\n    expectedCollections: ['pub.leaflet.', 'site.standard.'],\n  },\n\n  offprint: {\n    id: 'offprint',\n    name: 'Offprint',\n    description: (collection) => {\n      if (collection?.startsWith('site.standard.') || collection?.startsWith('pub.leaflet.')) {\n        return 'Read document on offprint.app';\n      }\n      return 'View on offprint.app';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      // offprint only has record-level URLs; without a collection+rkey there's\n      // no meaningful destination, so hide the waypoint in profile-only views.\n      if (!collection || !rkey) return null;\n      const identifier = did || handle;\n      return `https://offprint.app/${identifier}/${collection}/${rkey}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'publications',\n    redirectCompat: ['standard-site'],\n    expectedCollections: ['pub.leaflet.', 'site.standard.'],\n  },\n\n  pckt: {\n    id: 'pckt',\n    name: 'pckt',\n    description: (collection) => {\n      if (collection?.startsWith('site.standard.') || collection?.startsWith('pub.leaflet.')) {\n        return 'Read document on pckt.blog';\n      }\n      return 'View on pckt.blog';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      // pckt only has record-level URLs; without a collection+rkey there's no\n      // meaningful destination, so hide the waypoint in profile-only views.\n      if (!collection || !rkey) return null;\n      const identifier = did || handle;\n      return `https://pckt.blog/${identifier}/${collection}/${rkey}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'publications',\n    redirectCompat: ['standard-site'],\n    expectedCollections: ['pub.leaflet.', 'site.standard.'],\n  },\n\n  standardReader: {\n    id: 'standardReader',\n    name: 'Standard Reader',\n    description: (collection) => {\n      if (collection?.startsWith('site.standard.') || collection?.startsWith('pub.leaflet.')) {\n        return 'Read document on standard-reader.app';\n      }\n      return 'View documents on standard-reader.app';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      const identifier = did || handle;\n      if (\n        collection &&\n        rkey &&\n        (collection.startsWith('site.standard.') || collection.startsWith('pub.leaflet.'))\n      ) {\n        return `https://standard-reader.app/a/${identifier}/${rkey}`;\n      }\n      return `https://standard-reader.app/u/${identifier}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'publications',\n    redirectCompat: ['standard-site'],\n    expectedCollections: ['pub.leaflet.', 'site.standard.'],\n  },\n\n  taproot: {\n    id: 'taproot',\n    name: 'Taproot',\n    description: (collection) => {\n      if (collection) return 'Inspect record on atproto.at';\n      return 'Browse repo on atproto.at';\n    },\n    getUrl: (handle, collection, rkey, did) => {\n      const identifier = did || handle;\n      if (collection && rkey) {\n        return `https://atproto.at/uri/at://${identifier}/${collection}/${rkey}`;\n      }\n      return `https://atproto.at/uri/at://${identifier}`;\n    },\n    supportedTypes: ['post', 'profile', 'list', 'record'],\n    category: 'devTools',\n    redirectCompat: [],\n  },\n};\n\nexport const WAYPOINT_ORDER = [\n  'anisota',\n  'bluesky',\n  'bluepy',\n  'reddwarf',\n  'impro',\n  'blacksky',\n  'leaflet',\n  'aturi',\n  'pinksky',\n  'margin',\n  'semble',\n  'streamplace',\n  'grain',\n  'popfeed',\n  'sifa',\n  'blento',\n  'anisotaReader',\n  'offprint',\n  'pckt',\n  'standardReader',\n  'aturiExplore',\n  'pdsls',\n  'tangled',\n  'atptools',\n  'taproot',\n  'witchsky',\n  'mu',\n  'deer',\n  'lea',\n  'northsky',\n];\n\nexport function getWaypointDataForType(type: WaypointType): WaypointData[] {\n  return WAYPOINT_ORDER\n    .map(id => WAYPOINT_DESTINATIONS_DATA[id])\n    .filter(waypoint => waypoint.supportedTypes.includes(type));\n}\n\nexport function getWaypointCountData(): number {\n  return WAYPOINT_ORDER.length;\n}\n\nexport const WAYPOINT_CATEGORIES_DATA: Record<string, WaypointCategoryData> = {\n  blueskyClients: {\n    id: 'blueskyClients',\n    name: 'Bluesky Clients',\n    description: 'Official and alternative Bluesky clients',\n    defaultWaypointId: 'bluesky',\n    subcategories: [{\n      id: 'blueskyForks',\n      name: 'Bluesky Forks',\n      description: 'Community-built Bluesky variants',\n      defaultWaypointId: 'blacksky',\n    }],\n  },\n  blueskyForks: {\n    id: 'blueskyForks',\n    name: 'Bluesky Forks',\n    description: 'Community-built Bluesky variants',\n    defaultWaypointId: 'blacksky',\n  },\n  publications: {\n    id: 'publications',\n    name: 'Publications',\n    description: 'Readers for Standard Site and Leaflet publications',\n    defaultWaypointId: 'leaflet',\n  },\n  atmosphereApps: {\n    id: 'atmosphereApps',\n    name: 'Atmosphere',\n    description: 'Apps built on the AT Protocol',\n    defaultWaypointId: 'tangled',\n  },\n  devTools: {\n    id: 'devTools',\n    name: 'Dev Tools',\n    description: 'Tools for developers and debugging',\n    defaultWaypointId: 'aturiExplore',\n  },\n};\n\nexport const CATEGORY_ORDER = [\n  'blueskyClients',\n  'blueskyForks',\n  'publications',\n  'atmosphereApps',\n  'devTools',\n];\n\nexport function getCategorizedWaypointsData(type: WaypointType): CategorizedWaypointsData[] {\n  const availableWaypoints = getWaypointDataForType(type);\n  const categorized: CategorizedWaypointsData[] = [];\n\n  // Categories that are declared as subcategories of another category should\n  // not also appear as standalone top-level categories. Their waypoints will\n  // be rendered nested under their parent by the picker.\n  const subcategoryIds = new Set<string>();\n  for (const category of Object.values(WAYPOINT_CATEGORIES_DATA)) {\n    for (const subcat of category.subcategories ?? []) {\n      subcategoryIds.add(subcat.id);\n    }\n  }\n\n  for (const categoryId of CATEGORY_ORDER) {\n    if (subcategoryIds.has(categoryId)) continue;\n\n    const category = WAYPOINT_CATEGORIES_DATA[categoryId];\n    const waypoints = availableWaypoints.filter(w => w.category === categoryId);\n\n    if (waypoints.length > 0) {\n      categorized.push({ category, waypoints });\n    }\n  }\n\n  return categorized;\n}\n\ntype RecommendedConfig = {\n  waypointIds: string[];\n  label?: string;\n};\n\nconst RECOMMENDED_WAYPOINTS: Record<string, RecommendedConfig> = {\n  'app.bsky.feed.post': {\n    waypointIds: ['bluesky', 'anisota', 'blacksky'],\n    label: 'Recommended for Posts',\n  },\n  'profile': {\n    waypointIds: ['bluesky', 'anisota'],\n    label: 'Recommended for Profiles',\n  },\n  'app.bsky.graph.list': {\n    waypointIds: ['bluesky', 'anisota'],\n    label: 'Recommended for Lists',\n  },\n  'community.lexicon.calendar.event': {\n    waypointIds: ['aturiExplore', 'pdsls', 'atptools'],\n    label: 'Recommended for Events',\n  },\n  'sh.tangled.repo': {\n    waypointIds: ['tangled'],\n    label: 'Recommended for Repos',\n  },\n  'record': {\n    waypointIds: ['aturiExplore', 'pdsls', 'atptools', 'taproot'],\n    label: 'Recommended for Records',\n  },\n};\n\n/**\n * Recommendations keyed by collection NSID prefix. When a collection is checked,\n * we walk its dotted segments from longest to shortest looking for a registered\n * prefix (e.g. `standard.site.blog.entry` matches `standard.site`). Use this for\n * apps/lexicons that own a whole namespace and have a consistent set of compatible\n * waypoints across all of their record types.\n */\nconst RECOMMENDED_NAMESPACE_PREFIXES: Record<string, RecommendedConfig> = {\n  'site.standard': {\n    waypointIds: ['leaflet', 'standardReader', 'anisotaReader', 'offprint', 'pckt', 'pdsls'],\n    label: 'Recommended for Publications',\n  },\n  'pub.leaflet': {\n    waypointIds: ['leaflet', 'anisotaReader', 'offprint', 'pckt', 'pdsls'],\n    label: 'Recommended for Publications',\n  },\n  'sh.tangled': {\n    waypointIds: ['tangled', 'pdsls', 'atptools'],\n    label: 'Recommended for Tangled',\n  },\n  'at.margin': {\n    waypointIds: ['margin', 'pdsls', 'atptools'],\n    label: 'Recommended for Margin',\n  },\n  'social.grain': {\n    waypointIds: ['grain', 'pdsls', 'atptools'],\n    label: 'Recommended for Grain',\n  },\n};\n\nfunction findNamespacePrefixMatch(collection: string): RecommendedConfig | undefined {\n  const segments = collection.split('.');\n  for (let i = segments.length - 1; i >= 2; i--) {\n    const prefix = segments.slice(0, i).join('.');\n    if (RECOMMENDED_NAMESPACE_PREFIXES[prefix]) {\n      return RECOMMENDED_NAMESPACE_PREFIXES[prefix];\n    }\n  }\n  return undefined;\n}\n\nexport function getRecommendedWaypointsData(\n  type: WaypointType,\n  collection?: string\n): { waypoints: WaypointData[]; label: string } {\n  let config: RecommendedConfig | undefined;\n\n  if (collection && RECOMMENDED_WAYPOINTS[collection]) {\n    config = RECOMMENDED_WAYPOINTS[collection];\n  } else if (collection) {\n    config = findNamespacePrefixMatch(collection);\n  }\n\n  if (!config && RECOMMENDED_WAYPOINTS[type]) {\n    config = RECOMMENDED_WAYPOINTS[type];\n  }\n\n  if (!config) {\n    config = {\n      waypointIds: ['bluesky'],\n      label: 'Recommended',\n    };\n  }\n\n  const waypoints = config.waypointIds\n    .map(id => WAYPOINT_DESTINATIONS_DATA[id])\n    .filter(Boolean);\n\n  return {\n    waypoints,\n    label: config.label || 'Recommended',\n  };\n}\n\nexport function getFeaturedWaypointData(\n  type: WaypointType,\n  collection?: string\n): WaypointData | null {\n  const { waypoints } = getRecommendedWaypointsData(type, collection);\n  return waypoints[0] || null;\n}\n\n/**\n * Result of comparing a waypoint's `expectedCollections` against the set of\n * NSIDs found in the target repo.\n *\n *   - 'present'  — the user has at least one record under a matching prefix.\n *   - 'absent'   — the waypoint declared collections but none are in the repo.\n *   - 'unknown'  — the waypoint didn't declare any expectations, or we\n *                  haven't scanned the repo yet (e.g. scan disabled, no DID).\n */\nexport type WaypointActivity = 'present' | 'absent' | 'unknown';\n\n/**\n * Classify a waypoint against the set of collection NSIDs known to exist on\n * the target repo. Prefix-matches each entry in `expectedCollections` against\n * `repoCollections`. Returns 'unknown' when the waypoint has no declared\n * expectations or the caller passed `null` for `repoCollections` (i.e. scan\n * disabled or still in flight).\n */\nexport function waypointActivity(\n  waypoint: Pick<WaypointData, 'expectedCollections'>,\n  repoCollections: ReadonlySet<string> | null,\n): WaypointActivity {\n  if (!repoCollections) return 'unknown';\n  const expected = waypoint.expectedCollections;\n  if (!expected || expected.length === 0) return 'unknown';\n  for (const c of repoCollections) {\n    for (const prefix of expected) {\n      if (c === prefix || c.startsWith(prefix)) return 'present';\n    }\n  }\n  return 'absent';\n}\n\n/** Placeholder a compose intent template leaves for the caller's post text. */\nexport const COMPOSE_INTENT_TEXT_PLACEHOLDER = '{text}';\n\n/** Whether the client can be handed a link that opens its composer. */\nexport function supportsComposeIntent(\n  waypoint: Pick<WaypointData, 'composeIntent'>,\n): boolean {\n  return !!waypoint.composeIntent;\n}\n\n/**\n * Build a link that opens the client's composer, pre-filled with `text` when\n * the client reads it. Returns null when the client has no known intent route.\n *\n *   getComposeIntentUrl(WAYPOINT_DESTINATIONS_DATA.deer, 'hello!')\n *   // 'https://deer.social/intent/compose?text=hello!'\n */\nexport function getComposeIntentUrl(\n  waypoint: Pick<WaypointData, 'composeIntent'>,\n  text?: string,\n): string | null {\n  const intent = waypoint.composeIntent;\n  if (!intent) return null;\n  return appendComposeText(intent.url, intent.textParam, text);\n}\n\n/**\n * The native-app flavour of `getComposeIntentUrl`. Null unless the client\n * publishes a scheme of its own — most web clients don't, so fall back to the\n * https link rather than treating null as \"unsupported\".\n */\nexport function getComposeIntentAppUrl(\n  waypoint: Pick<WaypointData, 'composeIntent'>,\n  text?: string,\n): string | null {\n  const intent = waypoint.composeIntent;\n  if (!intent?.appUrl) return null;\n  return appendComposeText(intent.appUrl, intent.textParam, text);\n}\n\n/**\n * The client's intent URL with a literal `{text}` where the post text goes, for\n * handing to consumers that build their own links (JSON APIs, docs, templates).\n * Substitute the placeholder with URL-encoded text. Clients that ignore the\n * text get a template with no placeholder at all.\n */\nexport function getComposeIntentTemplate(\n  waypoint: Pick<WaypointData, 'composeIntent'>,\n): string | null {\n  const intent = waypoint.composeIntent;\n  if (!intent) return null;\n  if (!intent.textParam) return intent.url;\n  return `${intent.url}?${intent.textParam}=${COMPOSE_INTENT_TEXT_PLACEHOLDER}`;\n}\n\n/**\n * Catalog-ordered list of every client with a compose intent route, optionally\n * narrowed to those that also render a given record type.\n */\nexport function getComposeIntentWaypoints(type?: WaypointType): WaypointData[] {\n  const waypoints = type\n    ? getWaypointDataForType(type)\n    : WAYPOINT_ORDER.map(id => WAYPOINT_DESTINATIONS_DATA[id]).filter(Boolean);\n  return waypoints.filter(supportsComposeIntent);\n}\n\n/**\n * JSON-safe view of a client's compose intent, for surfaces that can't ship a\n * function (HTTP responses, the extension's message passing, docs tables).\n */\nexport type ComposeIntentDescriptor = {\n  /** Ready to open. Pre-filled when `text` was supplied and the client reads it. */\n  url: string;\n  /** The same URL with a literal `{text}` where the post text goes. */\n  urlTemplate: string;\n  /** Query parameter carrying the text; null when the client ignores it. */\n  textParam: string | null;\n  /**\n   * False when the composer opens empty no matter what you pass — the link is\n   * still a valid \"start a post over there\" jump, just not a share.\n   */\n  prefillsText: boolean;\n  /** Native-app deep link for the same intent, when the client publishes one. */\n  appUrl?: string;\n};\n\n/** Serialize a waypoint's compose intent. Null when it has none. */\nexport function describeComposeIntent(\n  waypoint: Pick<WaypointData, 'composeIntent'>,\n  text?: string,\n): ComposeIntentDescriptor | null {\n  const intent = waypoint.composeIntent;\n  if (!intent) return null;\n  const descriptor: ComposeIntentDescriptor = {\n    url: getComposeIntentUrl(waypoint, text)!,\n    urlTemplate: getComposeIntentTemplate(waypoint)!,\n    textParam: intent.textParam ?? null,\n    prefillsText: !!intent.textParam,\n  };\n  const appUrl = getComposeIntentAppUrl(waypoint, text);\n  if (appUrl) descriptor.appUrl = appUrl;\n  return descriptor;\n}\n\nfunction appendComposeText(\n  base: string,\n  textParam: string | undefined,\n  text: string | undefined,\n): string {\n  if (!textParam || !text) return base;\n  return `${base}?${textParam}=${encodeURIComponent(text)}`;\n}\n","/**\n * Deadline and identification for the direct-fetch upstream clients.\n *\n * Most outbound calls go through `upstreamFetch`, which bounds and retries\n * them. A handful of clients (appview, slingshot, constellation, plc,\n * identity, ufos) deliberately use bare `fetch` instead: they swallow failures\n * into null rather than throwing, and they must not retry. They still need a\n * deadline, since a host that accepts a connection and never answers would\n * otherwise hold a serverless invocation until the platform kills it.\n *\n * Both concerns live here rather than being repeated per module, so the\n * timeout and the User-Agent cannot drift apart between them.\n */\n\n/** Matches upstreamFetch's per-attempt budget. */\nexport const UPSTREAM_TIMEOUT_MS = 8000;\n\n/** The caller's signal, if any, combined with the deadline. */\nexport function withDeadline(signal?: AbortSignal | null): AbortSignal {\n  const deadline = AbortSignal.timeout(UPSTREAM_TIMEOUT_MS);\n  return signal ? AbortSignal.any([signal, deadline]) : deadline;\n}\n\n/**\n * Identify this deployment to the services it reads.\n *\n * Constellation, Slingshot and UFOs are run by volunteers, and Bluesky's\n * public AppView is a courtesy; an operator seeing unusual traffic should be\n * able to tell who it is and where to complain. Set only off-browser: a\n * browser forbids scripts from setting User-Agent, and these modules are\n * imported by the extension too.\n */\nexport const UPSTREAM_USER_AGENT = 'aturi.to (+https://aturi.to/mcp)';\n\n/**\n * The identifying headers to merge into an outbound request, or nothing at\n * all in a browser, where scripts are forbidden from setting User-Agent and\n * the attempt is either ignored or throws.\n */\nexport function identifyingHeaders(\n  existing?: HeadersInit,\n): Record<string, string> | undefined {\n  const headers = existing as Record<string, string> | undefined;\n  if (typeof window !== 'undefined') return headers;\n  return { ...headers, 'User-Agent': UPSTREAM_USER_AGENT };\n}\n\nexport function withIdentification(init?: RequestInit): RequestInit {\n  const merged: RequestInit = { ...init, signal: withDeadline(init?.signal) };\n  const headers = identifyingHeaders(init?.headers);\n  if (headers) merged.headers = headers;\n  return merged;\n}\n","/**\n * Shared fetch wrapper for upstream atproto services (appview, PLC\n * directory, PDS hosts).\n *\n * Every server-rendered page ultimately funnels through these upstream\n * calls, so two failure modes matter in production:\n *\n * - A hung TCP connection with no timeout keeps the whole function alive\n *   until the platform kills it (observed as 300s Vercel timeouts).\n * - Transient socket resets (ECONNRESET against public.api.bsky.app) fail\n *   requests that would succeed on an immediate retry.\n *\n * This wrapper bounds every request with AbortSignal.timeout and retries\n * once on network-level failures (never on HTTP error statuses, which are\n * meaningful responses). Works in Node, edge, and browser runtimes — the\n * extension imports sibling modules from this directory.\n *\n * It also identifies the caller. These requests reach personal data servers\n * and plc.directory, run by individuals and by a small team; an operator\n * looking at unfamiliar traffic should be able to see whose it is without\n * having to guess. Without this the requests go out as undici's default\n * `node`, which says nothing.\n */\n\nimport { identifyingHeaders } from './requestDeadline';\n\nexport type UpstreamFetchOptions = RequestInit & {\n  /** Per-attempt timeout in milliseconds. Defaults to 8000. */\n  timeoutMs?: number;\n  /** Extra attempts after a network-level failure. Defaults to 1. */\n  retries?: number;\n};\n\nconst RETRY_DELAY_MS = 250;\n\nexport async function upstreamFetch(\n  url: string,\n  { timeoutMs = 8000, retries = 1, ...init }: UpstreamFetchOptions = {}\n): Promise<Response> {\n  let lastError: unknown;\n\n  for (let attempt = 0; attempt <= retries; attempt++) {\n    try {\n      const headers = identifyingHeaders(init.headers);\n      return await fetch(url, {\n        ...init,\n        ...(headers ? { headers } : {}),\n        signal: AbortSignal.timeout(timeoutMs),\n      });\n    } catch (error) {\n      lastError = error;\n      if (attempt < retries) {\n        await new Promise((resolve) => setTimeout(resolve, RETRY_DELAY_MS));\n      }\n    }\n  }\n\n  throw lastError;\n}\n\n/**\n * Log an upstream HTTP error at the right level: 4xx responses are almost\n * always caused by user-supplied input (a bad handle or rkey in a shared\n * link) and are expected, so they log as warnings; 5xx and everything else\n * logs as an error. Keeps the production error dashboard signal-rich.\n */\nexport function logUpstreamHttpError(context: string, response: Response): void {\n  if (response.status >= 400 && response.status < 500) {\n    console.warn(`${context}: HTTP ${response.status} (expected for bad input)`);\n  } else {\n    console.error(`${context}: HTTP ${response.status}`);\n  }\n}\n","import { upstreamFetch } from './upstreamFetch';\n\nexport type ParsedURI = {\n  type: 'post' | 'profile' | 'list' | 'record' | 'unknown';\n  uri: string;\n  handle: string;\n  did?: string;\n  collection?: string;\n  rkey?: string;\n  error?: string;\n};\n\n/**\n * Parse URL path segments into structured AT URI data\n * Examples:\n * - /alice.bsky.social -> profile\n * - /alice.bsky.social/app.bsky.feed.post/3k7qw... -> post\n * - /did:plc:xxx/app.bsky.graph.list/abc -> list\n */\nexport function parseURI(handle: string, collection?: string, rkey?: string): ParsedURI {\n  // Handle is required\n  if (!handle) {\n    return {\n      type: 'unknown',\n      uri: '',\n      handle: '',\n      error: 'Handle or DID is required',\n    };\n  }\n\n  // Profile case (no collection/rkey)\n  if (!collection && !rkey) {\n    return {\n      type: 'profile',\n      uri: `at://${handle}`,\n      handle,\n      did: handle.startsWith('did:') ? handle : undefined,\n    };\n  }\n\n  // The literal `space` marker sits where a public collection NSID would in a\n  // permissioned AT URI (at://{did}/space/{type}/{skey}/…). An NSID always\n  // carries at least two dots and the marker carries none, so the two never\n  // collide. A space address needs four or more segments and names private\n  // data, so the three-segment universal-link route can never render one.\n  // Kept as a local literal rather than an import: this file is copied verbatim\n  // into @aturi.to/waypoints, which cannot resolve src/utils/atproto/*.\n  if (collection === 'space') {\n    return {\n      type: 'unknown',\n      uri: '',\n      handle,\n      error: 'Space URIs are not public records',\n    };\n  }\n\n  // Record case (has collection and rkey)\n  if (collection && rkey) {\n    let type: 'post' | 'list' | 'record' = 'record';\n    \n    if (collection === 'app.bsky.feed.post') {\n      type = 'post';\n    } else if (collection === 'app.bsky.graph.list') {\n      type = 'list';\n    }\n    // All other collections are treated as generic records\n\n    return {\n      type,\n      uri: `at://${handle}/${collection}/${rkey}`,\n      handle,\n      did: handle.startsWith('did:') ? handle : undefined,\n      collection,\n      rkey,\n    };\n  }\n\n  // Invalid case\n  return {\n    type: 'unknown',\n    uri: '',\n    handle,\n    error: 'Invalid URI structure',\n  };\n}\n\n/**\n * Resolve a handle to a DID using the Bluesky API\n */\n/**\n * Handle resolution that distinguishes a definitive \"no such handle\" from a\n * transient \"resolver unavailable\". Callers that need to decide between a real\n * 404 and a retry state use this; `resolveHandle` remains for the common\n * did-or-null case.\n *\n * - `not-found`: the appview returned a 4xx (invalid/unknown handle). Safe to\n *   surface as a 404.\n * - `unavailable`: network failure or 5xx. Must NOT be shown as a 404 — it's a\n *   real account we couldn't look up right now.\n */\nexport type HandleResolution =\n  | { did: string; reason?: undefined }\n  | { did: null; reason: 'not-found' | 'unavailable' };\n\nexport async function resolveHandleStatus(handle: string): Promise<HandleResolution> {\n  if (handle.startsWith('did:')) {\n    return { did: handle };\n  }\n\n  try {\n    const apiUrl = process.env.NEXT_PUBLIC_BSKY_API_URL || 'https://public.api.bsky.app';\n    const response = await upstreamFetch(\n      `${apiUrl}/xrpc/com.atproto.identity.resolveHandle?handle=${encodeURIComponent(handle)}`\n    );\n\n    if (!response.ok) {\n      return { did: null, reason: response.status >= 500 ? 'unavailable' : 'not-found' };\n    }\n\n    const data = await response.json();\n    if (data.did) return { did: data.did };\n    return { did: null, reason: 'not-found' };\n  } catch (error) {\n    console.error('Error resolving handle:', error);\n    return { did: null, reason: 'unavailable' };\n  }\n}\n\nexport async function resolveHandle(handle: string): Promise<string | null> {\n  return (await resolveHandleStatus(handle)).did;\n}\n\n/**\n * Get display name from handle or DID\n */\nexport function getDisplayName(handle: string, did?: string): string {\n  if (handle.startsWith('did:')) {\n    return did ? `@${did.slice(0, 16)}...` : 'Unknown';\n  }\n  return `@${handle}`;\n}\n\n\n","import type { ParsedURI } from './uriParser';\n\nexport type SourceApp =\n  | 'aturi'\n  | 'aturiExplore'\n  | 'bluesky'\n  | 'bluepy'\n  | 'blacksky'\n  | 'reddwarf'\n  | 'impro'\n  | 'lea'\n  | 'witchsky'\n  | 'deer'\n  | 'northsky'\n  | 'mu'\n  | 'anisota'\n  | 'pinksky'\n  | 'leaflet'\n  | 'tangled'\n  | 'margin'\n  | 'pdsls'\n  | 'atptools'\n  | 'semble'\n  | 'streamplace'\n  | 'grain'\n  | 'popfeed'\n  | 'sifa'\n  | 'blento'\n  | 'standardReader'\n  | 'taproot'\n  | 'offprint'\n  | 'pckt'\n  | 'headDetected';\n\nexport type ReverseMatch = {\n  source: SourceApp;\n  parsed: ParsedURI;\n};\n\ntype HostConfig = {\n  source: SourceApp;\n  hosts: string[];\n  /**\n   * When true, any subdomain of the listed hosts is treated as this source\n   * too (e.g. Anisota gives each publication its own `*.anisota.net` host).\n   */\n  matchSubdomains?: boolean;\n};\n\n/**\n * Hosts that share the Bluesky-style `/profile/:handle[/(post|lists)/:rkey]` layout.\n */\nconst BLUESKY_FAMILY: HostConfig[] = [\n  { source: 'bluesky', hosts: ['bsky.app'] },\n  { source: 'blacksky', hosts: ['blacksky.community'] },\n  { source: 'reddwarf', hosts: ['reddwarf.app'] },\n  { source: 'impro', hosts: ['impro.social'] },\n  { source: 'lea', hosts: ['lea.ac'] },\n  { source: 'witchsky', hosts: ['witchsky.app'] },\n  { source: 'deer', hosts: ['deer.social'] },\n  { source: 'northsky', hosts: ['northsky.app'] },\n  { source: 'mu', hosts: ['mu.social'] },\n  { source: 'anisota', hosts: ['anisota.net'], matchSubdomains: true },\n];\n\n/**\n * Base hosts whose subdomains are also recognized (e.g. `*.anisota.net`).\n * Derived from the `matchSubdomains` opt-in so there's one source of truth.\n */\nconst SUBDOMAIN_HOSTS: string[] = BLUESKY_FAMILY.filter(f => f.matchSubdomains).flatMap(\n  f => f.hosts,\n);\n\nfunction normalizeHost(host: string): string {\n  return host.toLowerCase().replace(/^www\\./, '');\n}\n\n/** True when `host` is a subdomain of `base` (a real dotted-label boundary). */\nfunction isSubdomainOf(host: string, base: string): boolean {\n  return host.endsWith(`.${base}`);\n}\n\n/** Exact host match, or a subdomain match when the config opts in. */\nfunction hostMatchesConfig(host: string, config: HostConfig): boolean {\n  if (config.hosts.includes(host)) return true;\n  if (!config.matchSubdomains) return false;\n  return config.hosts.some(h => isSubdomainOf(host, h));\n}\n\nfunction matchBlueskyFamily(host: string, parts: string[]): ReverseMatch | null {\n  const entry = BLUESKY_FAMILY.find(f => hostMatchesConfig(host, f));\n  if (!entry) return null;\n\n  if (parts[0] !== 'profile' || !parts[1]) return null;\n  const handle = parts[1];\n  const did = handle.startsWith('did:') ? handle : undefined;\n\n  if (!parts[2]) {\n    return {\n      source: entry.source,\n      parsed: {\n        type: 'profile',\n        uri: `at://${handle}`,\n        handle,\n        did,\n      },\n    };\n  }\n\n  if (parts[2] === 'post' && parts[3]) {\n    return {\n      source: entry.source,\n      parsed: {\n        type: 'post',\n        uri: `at://${handle}/app.bsky.feed.post/${parts[3]}`,\n        handle,\n        did,\n        collection: 'app.bsky.feed.post',\n        rkey: parts[3],\n      },\n    };\n  }\n\n  if ((parts[2] === 'lists' || parts[2] === 'list') && parts[3]) {\n    return {\n      source: entry.source,\n      parsed: {\n        type: 'list',\n        uri: `at://${handle}/app.bsky.graph.list/${parts[3]}`,\n        handle,\n        did,\n        collection: 'app.bsky.graph.list',\n        rkey: parts[3],\n      },\n    };\n  }\n\n  // Anisota's reader addresses Standard Site / Leaflet documents at\n  // `/profile/:handle/document/:rkey` without the collection NSID in the URL.\n  // Mirror Standard Reader's convention and reconstruct the canonical\n  // `site.standard.document` collection so the record still resolves.\n  if (parts[2] === 'document' && parts[3]) {\n    return {\n      source: entry.source,\n      parsed: {\n        type: 'record',\n        uri: `at://${handle}/site.standard.document/${parts[3]}`,\n        handle,\n        did,\n        collection: 'site.standard.document',\n        rkey: parts[3],\n      },\n    };\n  }\n\n  return {\n    source: entry.source,\n    parsed: {\n      type: 'profile',\n      uri: `at://${handle}`,\n      handle,\n      did,\n    },\n  };\n}\n\nfunction inferType(collection: string): 'post' | 'list' | 'record' {\n  if (collection === 'app.bsky.feed.post') return 'post';\n  if (collection === 'app.bsky.graph.list') return 'list';\n  return 'record';\n}\n\nfunction matchPinksky(host: string, parts: string[], search: URLSearchParams): ReverseMatch | null {\n  if (host !== 'pinkleap.app') return null;\n\n  if (parts[0] === 'feed') {\n    const uri = search.get('uri');\n    if (uri && uri.startsWith('at://')) {\n      const stripped = uri.slice('at://'.length);\n      const [handle, collection, rkey] = stripped.split('/');\n      if (handle) {\n        const did = handle.startsWith('did:') ? handle : undefined;\n        if (collection && rkey) {\n          return {\n            source: 'pinksky',\n            parsed: {\n              type: inferType(collection),\n              uri,\n              handle,\n              did,\n              collection,\n              rkey,\n            },\n          };\n        }\n        return {\n          source: 'pinksky',\n          parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n        };\n      }\n    }\n  }\n\n  if (parts[0] === 'profile' && parts[1]) {\n    const handle = parts[1];\n    const did = handle.startsWith('did:') ? handle : undefined;\n    return {\n      source: 'pinksky',\n      parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n    };\n  }\n\n  return null;\n}\n\nfunction matchLeaflet(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'leaflet.pub') return null;\n  if (parts[0] !== 'p' || !parts[1]) return null;\n  const handle = parts[1];\n  const did = handle.startsWith('did:') ? handle : undefined;\n  return {\n    source: 'leaflet',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchTangled(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'tangled.org') return null;\n  if (!parts[0]) return null;\n  const handle = parts[0];\n  const did = handle.startsWith('did:') ? handle : undefined;\n  return {\n    source: 'tangled',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchMargin(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'margin.at') return null;\n\n  if (parts[0] === 'profile' && parts[1]) {\n    const handle = parts[1];\n    const did = handle.startsWith('did:') ? handle : undefined;\n    return {\n      source: 'margin',\n      parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n    };\n  }\n\n  if (parts[0] && parts[1] && parts[2]) {\n    const recordType = parts[1];\n    if (recordType === 'annotation' || recordType === 'highlight' || recordType === 'bookmark') {\n      const handle = parts[0];\n      const did = handle.startsWith('did:') ? handle : undefined;\n      const collection = `at.margin.${recordType}`;\n      const rkey = parts[2];\n      return {\n        source: 'margin',\n        parsed: {\n          type: 'record',\n          uri: `at://${handle}/${collection}/${rkey}`,\n          handle,\n          did,\n          collection,\n          rkey,\n        },\n      };\n    }\n  }\n\n  return null;\n}\n\n/**\n * Parse a path segment of the form `at://identifier[/collection/rkey]` or\n * `at:/identifier[/collection/rkey]` used by pdsls.dev and atp.tools.\n *\n * The leading `at://` or `at:/` is collapsed by the URL parser so the raw\n * `pathname` exposes it as `/at:/identifier/...`. We accept both forms.\n */\nfunction parseAtUriPath(pathname: string): {\n  handle: string;\n  collection?: string;\n  rkey?: string;\n} | null {\n  const cleaned = pathname.replace(/^\\/+/, '');\n  const match = cleaned.match(/^at:\\/{1,2}(.+)$/);\n  if (!match) return null;\n  const rest = match[1];\n  const segments = rest.split('/').filter(Boolean);\n  if (segments.length === 0) return null;\n  // Permissioned space addresses must never be handed to a public explorer;\n  // see the note in matchAturi. The literal is duplicated because this file is\n  // copied verbatim into @aturi.to/waypoints.\n  if (segments[1] === 'space') return null;\n  return {\n    handle: segments[0],\n    collection: segments[1],\n    rkey: segments[2],\n  };\n}\n\nfunction matchPdsls(host: string, pathname: string): ReverseMatch | null {\n  if (host !== 'pdsls.dev') return null;\n  const atUri = parseAtUriPath(pathname);\n  if (!atUri) return null;\n  const { handle, collection, rkey } = atUri;\n  const did = handle.startsWith('did:') ? handle : undefined;\n\n  if (collection && rkey) {\n    return {\n      source: 'pdsls',\n      parsed: {\n        type: inferType(collection),\n        uri: `at://${handle}/${collection}/${rkey}`,\n        handle,\n        did,\n        collection,\n        rkey,\n      },\n    };\n  }\n\n  return {\n    source: 'pdsls',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchAtpTools(host: string, pathname: string): ReverseMatch | null {\n  if (host !== 'atp.tools') return null;\n  const atUri = parseAtUriPath(pathname);\n  if (!atUri) return null;\n  const { handle, collection, rkey } = atUri;\n  const did = handle.startsWith('did:') ? handle : undefined;\n\n  if (collection && rkey) {\n    return {\n      source: 'atptools',\n      parsed: {\n        type: inferType(collection),\n        uri: `at://${handle}/${collection}/${rkey}`,\n        handle,\n        did,\n        collection,\n        rkey,\n      },\n    };\n  }\n\n  return {\n    source: 'atptools',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchBluepy(host: string, pathname: string): ReverseMatch | null {\n  if (host !== 'bluepy.social') return null;\n  const atUri = parseAtUriPath(pathname);\n  if (!atUri) return null;\n  const { handle, collection, rkey } = atUri;\n  const did = handle.startsWith('did:') ? handle : undefined;\n\n  if (collection === 'app.bsky.actor.profile') {\n    return {\n      source: 'bluepy',\n      parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n    };\n  }\n\n  if (collection && rkey) {\n    return {\n      source: 'bluepy',\n      parsed: {\n        type: inferType(collection),\n        uri: `at://${handle}/${collection}/${rkey}`,\n        handle,\n        did,\n        collection,\n        rkey,\n      },\n    };\n  }\n\n  return {\n    source: 'bluepy',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchSemble(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'semble.so') return null;\n  if (parts[0] !== 'profile' || !parts[1]) return null;\n  const handle = parts[1];\n  const did = handle.startsWith('did:') ? handle : undefined;\n  return {\n    source: 'semble',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchStreamplace(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'stream.place') return null;\n  if (!parts[0]) return null;\n  const handle = parts[0];\n  const did = handle.startsWith('did:') ? handle : undefined;\n  return {\n    source: 'streamplace',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchGrain(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'grain.social') return null;\n  if (parts[0] !== 'profile' || !parts[1]) return null;\n  const handle = parts[1];\n  const did = handle.startsWith('did:') ? handle : undefined;\n\n  if (parts[2] === 'gallery' && parts[3]) {\n    return {\n      source: 'grain',\n      parsed: {\n        type: 'record',\n        uri: `at://${handle}/social.grain.gallery/${parts[3]}`,\n        handle,\n        did,\n        collection: 'social.grain.gallery',\n        rkey: parts[3],\n      },\n    };\n  }\n\n  return {\n    source: 'grain',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchPopfeed(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'popfeed.social') return null;\n  if (parts[0] !== 'profile' || !parts[1]) return null;\n  const handle = parts[1];\n  const did = handle.startsWith('did:') ? handle : undefined;\n  return {\n    source: 'popfeed',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchSifa(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'sifa.id') return null;\n  if (parts[0] !== 'p' || !parts[1]) return null;\n  const handle = parts[1];\n  const did = handle.startsWith('did:') ? handle : undefined;\n  return {\n    source: 'sifa',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\nfunction matchBlento(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'blento.app') return null;\n  if (!parts[0]) return null;\n  const handle = parts[0];\n  const did = handle.startsWith('did:') ? handle : undefined;\n  return {\n    source: 'blento',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\n/**\n * Standard Reader: `/u/<identifier>` is a profile (document list) and\n * `/a/<identifier>/<rkey>` is a document. The document route omits the\n * collection NSID, but every `/a/` link is a Standard Site document, so we\n * reconstruct the full `site.standard.document/<rkey>` AT URI.\n */\nfunction matchStandardReader(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'standard-reader.app') return null;\n\n  if (parts[0] === 'a' && parts[1] && parts[2]) {\n    const handle = parts[1];\n    const did = handle.startsWith('did:') ? handle : undefined;\n    const rkey = parts[2];\n    return {\n      source: 'standardReader',\n      parsed: {\n        type: 'record',\n        uri: `at://${handle}/site.standard.document/${rkey}`,\n        handle,\n        did,\n        collection: 'site.standard.document',\n        rkey,\n      },\n    };\n  }\n\n  if (parts[0] === 'u' && parts[1]) {\n    const handle = parts[1];\n    const did = handle.startsWith('did:') ? handle : undefined;\n    return {\n      source: 'standardReader',\n      parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n    };\n  }\n\n  return null;\n}\n\n/**\n * Offprint (offprint.app) and pckt (pckt.blog) address publications at the\n * flat path `/<identifier>/<collection>/<rkey>` — the collection NSID sits in\n * the path verbatim, so we can round-trip it straight back. Both only expose\n * record-level URLs, so a profile-only path has no meaningful match.\n */\nfunction matchFlatRecordHost(\n  host: string,\n  parts: string[],\n  target: { host: string; source: SourceApp },\n): ReverseMatch | null {\n  if (host !== target.host) return null;\n  const [handle, collection, rkey] = parts;\n  if (!handle || !collection || !rkey) return null;\n  // Guard against non-record pages (settings, landing, …): a real record path\n  // always carries an NSID collection segment.\n  if (!collection.includes('.')) return null;\n  const did = handle.startsWith('did:') ? handle : undefined;\n  return {\n    source: target.source,\n    parsed: {\n      type: inferType(collection),\n      uri: `at://${handle}/${collection}/${rkey}`,\n      handle,\n      did,\n      collection,\n      rkey,\n    },\n  };\n}\n\n/**\n * Taproot (atproto.at): a generic AT-URI explorer addressed at\n * `/uri/at://<identifier>[/<collection>/<rkey>]`.\n */\nfunction matchTaproot(host: string, pathname: string): ReverseMatch | null {\n  if (host !== 'atproto.at') return null;\n  const m = pathname.replace(/^\\/+/, '').match(/^uri\\/at:\\/{1,2}(.+)$/);\n  if (!m) return null;\n  const segments = m[1].split('/').filter(Boolean);\n  if (segments.length === 0) return null;\n  // Permissioned space addresses must never be handed to a public explorer;\n  // see the note in matchAturi. The literal is duplicated because this file is\n  // copied verbatim into @aturi.to/waypoints.\n  if (segments[1] === 'space') return null;\n  const handle = segments[0];\n  const collection = segments[1];\n  const rkey = segments[2];\n  const did = handle.startsWith('did:') ? handle : undefined;\n\n  if (collection && rkey) {\n    return {\n      source: 'taproot',\n      parsed: {\n        type: inferType(collection),\n        uri: `at://${handle}/${collection}/${rkey}`,\n        handle,\n        did,\n        collection,\n        rkey,\n      },\n    };\n  }\n\n  return {\n    source: 'taproot',\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\n/**\n * Aturi's own pages. Two URL spaces share the aturi.to host:\n *   - `/explore/<identifier>[/<collection>[/<rkey>]]` — the raw record explorer\n *     (source id `aturiExplore`).\n *   - `/profile/<identifier>[/post/<rkey> | /lists/<rkey> | /<collection>/<rkey>]`\n *     — the universal-link view (source id `aturi`).\n *\n * Detecting these lets the popup offer jumps to other clients and explorers\n * while you're already on Aturi. Reporting the source id as the matching\n * waypoint (`aturiExplore` vs `aturi`) also keeps the page you're on out of the\n * suggestion list.\n */\nfunction matchAturi(host: string, parts: string[]): ReverseMatch | null {\n  if (host !== 'aturi.to') return null;\n\n  // A repo identifier is always a DID (`did:…`) or a dotted handle. This rules\n  // out the explorer's own sub-tools — `/explore/lexicons`, `/explore/pds` —\n  // whose first segment is a bare word, not an account.\n  const isIdentifier = (seg: string | undefined): boolean =>\n    !!seg && (seg.startsWith('did:') || seg.includes('.'));\n\n  // Explorer: /explore/<identifier>[/<collection>[/<rkey>]]\n  if (parts[0] === 'explore' && isIdentifier(parts[1])) {\n    // `/explore/<did>/space/…` addresses permissioned data. A match here would\n    // be handed to the popup as a record other explorers can open, leaking the\n    // address of private data to public tools, so the tab reads as\n    // unrecognized instead. The marker is a local literal because this file is\n    // copied verbatim into @aturi.to/waypoints, which cannot resolve\n    // src/utils/atproto/*. A real NSID never equals `space` — it needs dots.\n    if (parts[2] === 'space') return null;\n    const handle = parts[1];\n    const did = handle.startsWith('did:') ? handle : undefined;\n    const collection = parts[2];\n    const rkey = parts[3];\n    if (collection && rkey) {\n      return {\n        source: 'aturiExplore',\n        parsed: {\n          type: inferType(collection),\n          uri: `at://${handle}/${collection}/${rkey}`,\n          handle,\n          did,\n          collection,\n          rkey,\n        },\n      };\n    }\n    // Repo browse or a collection listing (no rkey): treat as profile-level so\n    // the popup offers profile waypoints for the identifier.\n    return {\n      source: 'aturiExplore',\n      parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n    };\n  }\n\n  // Universal-link view: /profile/<identifier>[/post|/lists|/<collection>/<rkey>]\n  if (parts[0] === 'profile' && isIdentifier(parts[1])) {\n    const handle = parts[1];\n    const did = handle.startsWith('did:') ? handle : undefined;\n\n    if (parts[2] === 'post' && parts[3]) {\n      return {\n        source: 'aturi',\n        parsed: {\n          type: 'post',\n          uri: `at://${handle}/app.bsky.feed.post/${parts[3]}`,\n          handle,\n          did,\n          collection: 'app.bsky.feed.post',\n          rkey: parts[3],\n        },\n      };\n    }\n\n    if (parts[2] === 'lists' && parts[3]) {\n      return {\n        source: 'aturi',\n        parsed: {\n          type: 'list',\n          uri: `at://${handle}/app.bsky.graph.list/${parts[3]}`,\n          handle,\n          did,\n          collection: 'app.bsky.graph.list',\n          rkey: parts[3],\n        },\n      };\n    }\n\n    // Generic record view: /profile/<identifier>/<collection>/<rkey>. Guard on\n    // the dot so non-record profile subpages don't masquerade as records.\n    if (parts[2] && parts[2].includes('.') && parts[3]) {\n      return {\n        source: 'aturi',\n        parsed: {\n          type: inferType(parts[2]),\n          uri: `at://${handle}/${parts[2]}/${parts[3]}`,\n          handle,\n          did,\n          collection: parts[2],\n          rkey: parts[3],\n        },\n      };\n    }\n\n    return {\n      source: 'aturi',\n      parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n    };\n  }\n\n  return null;\n}\n\n/**\n * Reverse-match any supported Aturi waypoint site URL back into a structured\n * ParsedURI (handle/collection/rkey). Returns `null` if the URL isn't on a\n * supported site or isn't a shape we recognize.\n */\nexport function matchSupportedUrl(url: URL): ReverseMatch | null {\n  const host = normalizeHost(url.hostname);\n  const parts = url.pathname.split('/').filter(Boolean);\n  const search = url.searchParams;\n\n  return (\n    matchAturi(host, parts) ||\n    matchBlueskyFamily(host, parts) ||\n    matchPinksky(host, parts, search) ||\n    matchLeaflet(host, parts) ||\n    matchTangled(host, parts) ||\n    matchMargin(host, parts) ||\n    matchPdsls(host, url.pathname) ||\n    matchAtpTools(host, url.pathname) ||\n    matchBluepy(host, url.pathname) ||\n    matchSemble(host, parts) ||\n    matchStreamplace(host, parts) ||\n    matchGrain(host, parts) ||\n    matchPopfeed(host, parts) ||\n    matchSifa(host, parts) ||\n    matchBlento(host, parts) ||\n    matchStandardReader(host, parts) ||\n    matchFlatRecordHost(host, parts, { host: 'offprint.app', source: 'offprint' }) ||\n    matchFlatRecordHost(host, parts, { host: 'pckt.blog', source: 'pckt' }) ||\n    matchTaproot(host, url.pathname)\n  );\n}\n\n/**\n * Parse an AT URI string (e.g. \"at://did:plc:abc123/collection/rkey\") into\n * its components. Used by head-based detection when an AT URI is found in\n * a <link> tag's href attribute.\n */\nexport function parseAtUri(uri: string): ReverseMatch | null {\n  if (!uri.startsWith('at://')) return null;\n  const rest = uri.slice('at://'.length);\n  const segments = rest.split('/').filter(Boolean);\n  if (segments.length === 0) return null;\n  // Permissioned space addresses must never be handed to a public explorer;\n  // see the note in matchAturi. The literal is duplicated because this file is\n  // copied verbatim into @aturi.to/waypoints.\n  if (segments[1] === 'space') return null;\n\n  const handle = segments[0];\n  const did = handle.startsWith('did:') ? handle : undefined;\n  const collection = segments[1];\n  const rkey = segments[2];\n\n  if (collection && rkey) {\n    return {\n      source: 'headDetected' as SourceApp,\n      parsed: {\n        type: inferType(collection),\n        uri,\n        handle,\n        did,\n        collection,\n        rkey,\n      },\n    };\n  }\n\n  return {\n    source: 'headDetected' as SourceApp,\n    parsed: { type: 'profile', uri: `at://${handle}`, handle, did },\n  };\n}\n\n/**\n * All host names we know how to reverse-parse. Used by the popup + background\n * worker to decide if a tab is \"relevant\" before doing more expensive work.\n */\nexport const SUPPORTED_HOSTS: string[] = [\n  'aturi.to',\n  ...BLUESKY_FAMILY.flatMap(e => e.hosts),\n  'pinkleap.app',\n  'leaflet.pub',\n  'tangled.org',\n  'margin.at',\n  'pdsls.dev',\n  'atp.tools',\n  'bluepy.social',\n  'semble.so',\n  'stream.place',\n  'grain.social',\n  'popfeed.social',\n  'sifa.id',\n  'blento.app',\n  'standard-reader.app',\n  'offprint.app',\n  'pckt.blog',\n  'atproto.at',\n];\n\n/**\n * Whether a hostname belongs to a supported waypoint. Prefer this over a raw\n * `SUPPORTED_HOSTS.includes(...)` check: it strips a leading `www.` and also\n * recognizes subdomains of hosts that opt in (e.g. `eclose.anisota.net`), so\n * the extension popup and resolve API treat those tabs as known.\n */\nexport function isSupportedHost(host: string): boolean {\n  const h = normalizeHost(host);\n  if (SUPPORTED_HOSTS.includes(h)) return true;\n  return SUBDOMAIN_HOSTS.some(base => isSubdomainOf(h, base));\n}\n","import {\n  WAYPOINT_DESTINATIONS_DATA,\n  WAYPOINT_ORDER,\n  describeComposeIntent,\n  getRecommendedWaypointsData,\n  type ComposeIntentDescriptor,\n  type WaypointType,\n} from './waypoints.data';\nimport {\n  matchSupportedUrl,\n  parseAtUri,\n  type SourceApp,\n} from './reverseParsers';\nimport type { ParsedURI } from './uriParser';\n\nexport type ResolvedWaypoint = {\n  id: string;\n  name: string;\n  category: string;\n  url: string;\n  /**\n   * Whether this client can be handed a link that opens its composer, and how\n   * to build one. Null when it has no confirmed compose intent route. Supply\n   * `composeText` to get the links back pre-filled.\n   */\n  composeIntent: ComposeIntentDescriptor | null;\n};\n\nexport type ResolvedRecommendation = {\n  ids: string[];\n  label: string;\n};\n\nexport type ResolveResult = {\n  parsed: ParsedURI;\n  source: SourceApp;\n  did: string | null;\n  didResolved: boolean;\n  waypoints: ResolvedWaypoint[];\n  recommended: ResolvedRecommendation;\n};\n\n/**\n * Waypoints whose `getUrl` only produces a useful destination when a DID is\n * available. These are filtered out unless a DID is known. Mirrors the hosted\n * aturi.to/api/resolve route exactly.\n */\nexport const DID_REQUIRED_WAYPOINTS: ReadonlySet<string> = new Set([\n  'pdsls',\n  'atptools',\n  'margin',\n  'grain',\n  'popfeed',\n]);\n\nexport type BuildWaypointsOptions = {\n  /** DID to pass to each waypoint's getUrl. Falls back to `parsed.did`. */\n  did?: string;\n  /** Waypoint id to omit (e.g. the source app the user is already on). */\n  excludeSourceId?: string;\n  /** Text to pre-fill into each waypoint's compose intent link, if it has one. */\n  composeText?: string;\n};\n\n/**\n * Turn a parsed AT URI into the list of waypoints that can render it plus the\n * recommended set, applying the DID-required filter and dropping waypoints\n * whose getUrl returns null. This is the framework-agnostic core of the\n * hosted resolve endpoint.\n */\nexport function buildWaypointsForParsed(\n  parsed: ParsedURI,\n  options: BuildWaypointsOptions = {},\n): { waypoints: ResolvedWaypoint[]; recommended: ResolvedRecommendation } {\n  const did = options.did ?? parsed.did;\n  const exclude = options.excludeSourceId;\n  const type: WaypointType = parsed.type === 'unknown' ? 'profile' : parsed.type;\n\n  const waypoints = WAYPOINT_ORDER.map((id) => WAYPOINT_DESTINATIONS_DATA[id])\n    .filter((w): w is NonNullable<typeof w> => !!w)\n    .filter((w) => w.id !== exclude)\n    .filter((w) => w.supportedTypes.includes(type))\n    .map((w): ResolvedWaypoint | null => {\n      if (DID_REQUIRED_WAYPOINTS.has(w.id) && !did) return null;\n      const url = w.getUrl(parsed.handle, parsed.collection, parsed.rkey, did);\n      if (!url) return null;\n      return {\n        id: w.id,\n        name: w.name,\n        category: w.category,\n        url,\n        composeIntent: describeComposeIntent(w, options.composeText),\n      };\n    })\n    .filter((w): w is ResolvedWaypoint => !!w);\n\n  const recommendedRaw = getRecommendedWaypointsData(type, parsed.collection);\n  const availableIds = new Set(waypoints.map((w) => w.id));\n  const ids = recommendedRaw.waypoints\n    .map((w) => w.id)\n    .filter((id) => id !== exclude && availableIds.has(id));\n\n  return { waypoints, recommended: { ids, label: recommendedRaw.label } };\n}\n\n/**\n * Resolve an AT URI string (e.g. \"at://did:plc:abc/app.bsky.feed.post/rkey\")\n * directly into its waypoints. Returns null if the string isn't a valid AT URI.\n */\nexport function resolveAtUri(\n  uri: string,\n  options: Pick<BuildWaypointsOptions, 'composeText'> = {},\n): ResolveResult | null {\n  const match = parseAtUri(uri);\n  if (!match) return null;\n  const { parsed, source } = match;\n  const { waypoints, recommended } = buildWaypointsForParsed(parsed, {\n    composeText: options.composeText,\n  });\n  return {\n    parsed,\n    source,\n    did: parsed.did ?? null,\n    didResolved: false,\n    waypoints,\n    recommended,\n  };\n}\n\nexport type ResolveUrlOptions = {\n  /**\n   * When the URL pattern isn't recognized, fetch the page and look for a\n   * `<link href=\"at://…\">` in <head>. Off by default to keep the resolver\n   * isomorphic (no network unless explicitly requested).\n   */\n  fetchHead?: boolean;\n  /** Timeout for the optional head probe. Defaults to 4000ms. */\n  fetchHeadTimeoutMs?: number;\n  /**\n   * Resolve a handle to a DID so DID-only waypoints (pdsls, atptools, margin,\n   * grain, popfeed) are included. Pass `resolveHandle` from this package, or\n   * your own implementation.\n   */\n  resolveHandle?: (handle: string) => Promise<string | null>;\n  /** Text to pre-fill into each waypoint's compose intent link, if it has one. */\n  composeText?: string;\n};\n\n/**\n * Resolve a pasted/shared page URL back into the AT URI it represents and the\n * waypoints that can render it. Uses local URL-pattern matching by default;\n * optionally falls back to a `<head>` link probe and/or handle→DID resolution.\n *\n * The source app's own waypoint is omitted from the result (you're already\n * there), mirroring the extension popup and hosted endpoint.\n */\nexport async function resolveUrl(\n  url: string | URL,\n  options: ResolveUrlOptions = {},\n): Promise<ResolveResult | null> {\n  let target: URL;\n  try {\n    target = typeof url === 'string' ? new URL(url) : url;\n  } catch {\n    return null;\n  }\n  if (!/^https?:$/.test(target.protocol)) return null;\n\n  let match = matchSupportedUrl(target);\n  if (!match && options.fetchHead) {\n    const headUri = await detectAtUriInHead(\n      target.toString(),\n      options.fetchHeadTimeoutMs ?? 4000,\n    );\n    if (headUri) match = parseAtUri(headUri);\n  }\n  if (!match) return null;\n\n  const { parsed, source } = match;\n  let did = parsed.did;\n  let didResolved = false;\n  if (!did && options.resolveHandle) {\n    try {\n      const resolved = await options.resolveHandle(parsed.handle);\n      if (resolved) {\n        did = resolved;\n        didResolved = true;\n      }\n    } catch {\n      // Swallow; DID-required waypoints will simply be omitted from the result.\n    }\n  }\n\n  const { waypoints, recommended } = buildWaypointsForParsed(parsed, {\n    did,\n    excludeSourceId: source,\n    composeText: options.composeText,\n  });\n  return {\n    parsed: { ...parsed, did },\n    source,\n    did: did ?? null,\n    didResolved,\n    waypoints,\n    recommended,\n  };\n}\n\nexport type ResolveApiInput = {\n  url?: string;\n  atUri?: string;\n  /** Set false to skip the server-side <head> probe. */\n  headDetect?: boolean;\n  /** Text to pre-fill into the returned compose intent links. */\n  composeText?: string;\n};\n\nexport type ResolveApiParsed = {\n  type: WaypointType;\n  uri: string;\n  handle: string;\n  did: string | null;\n  collection: string | null;\n  rkey: string | null;\n};\n\nexport type ResolveApiSuccess = {\n  ok: true;\n  inputKind: 'atUri' | 'url';\n  /**\n   * How the endpoint found the AT URI. `atTags` means the page declared it\n   * itself via `<meta name=\"at:canonical\">` (or `at:alternate`); `headLink` is\n   * the older `<link href=\"at://…\">` the same probe falls back to.\n   */\n  detectedVia: 'atUri' | 'urlPattern' | 'atTags' | 'headLink' | null;\n  source: SourceApp;\n  isKnownHost: boolean;\n  parsed: ResolveApiParsed;\n  didResolved: boolean;\n  recommended: ResolvedRecommendation;\n  waypoints: ResolvedWaypoint[];\n};\n\nexport type ResolveApiFailure = {\n  ok: false;\n  input?: string | null;\n  inputKind?: 'atUri' | 'url';\n  isKnownHost?: boolean;\n  reason?: string;\n  message?: string;\n  error?: string;\n};\n\nexport type ResolveApiResponse = ResolveApiSuccess | ResolveApiFailure;\n\nexport type ResolveViaApiOptions = {\n  /** Defaults to the hosted endpoint, https://aturi.to/api/resolve. */\n  endpoint?: string;\n  /** Custom fetch implementation (e.g. a polyfill or instrumented client). */\n  fetch?: typeof fetch;\n  signal?: AbortSignal;\n};\n\n/**\n * Typed client for the hosted resolve endpoint. Use this when you want the\n * server to do the work — notably the <head> link probe, which needs to fetch\n * the target page (something you may not want to do from the browser for CORS\n * reasons). Returns the same response shape the route emits.\n */\nexport async function resolveViaApi(\n  input: ResolveApiInput,\n  options: ResolveViaApiOptions = {},\n): Promise<ResolveApiResponse> {\n  const endpoint = options.endpoint ?? 'https://aturi.to/api/resolve';\n  const fetchImpl = options.fetch ?? fetch;\n  const params = new URLSearchParams();\n  if (input.atUri) {\n    params.set('atUri', input.atUri);\n  } else if (input.url) {\n    params.set('url', input.url);\n  } else {\n    throw new Error('resolveViaApi requires either `url` or `atUri`');\n  }\n  if (input.headDetect === false) params.set('headDetect', 'false');\n  if (input.composeText) params.set('composeText', input.composeText);\n\n  const res = await fetchImpl(`${endpoint}?${params.toString()}`, {\n    method: 'GET',\n    headers: { Accept: 'application/json' },\n    signal: options.signal,\n  });\n  return (await res.json()) as ResolveApiResponse;\n}\n\n/**\n * Best-effort <head> probe for a `<link href=\"at://…\">`. Reads the response as\n * text, scans the document head, and returns the first AT URI found. Returns\n * null on any error, non-HTML content, or timeout.\n */\nasync function detectAtUriInHead(\n  url: string,\n  timeoutMs: number,\n): Promise<string | null> {\n  if (typeof fetch === 'undefined') return null;\n  const controller =\n    typeof AbortController !== 'undefined' ? new AbortController() : null;\n  const timeout = controller\n    ? setTimeout(() => controller.abort(), timeoutMs)\n    : null;\n  try {\n    const response = await fetch(url, {\n      signal: controller?.signal,\n      redirect: 'follow',\n      headers: {\n        'User-Agent':\n          'Mozilla/5.0 (compatible; AturiResolver/1.0; +https://aturi.to)',\n        Accept:\n          'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.5',\n      },\n    });\n    if (!response.ok) return null;\n\n    const ct = response.headers.get('content-type') || '';\n    if (!/text\\/html|application\\/xhtml/i.test(ct)) return null;\n\n    const html = await response.text();\n    const headMatch = html.match(/<head[\\s\\S]*?<\\/head>/i);\n    const haystack = headMatch ? headMatch[0] : html.slice(0, 256 * 1024);\n    const linkRe =\n      /<link\\b[^>]*\\bhref\\s*=\\s*[\"'](at:\\/\\/[^\"']+)[\"'][^>]*>/gi;\n    let m: RegExpExecArray | null;\n    while ((m = linkRe.exec(haystack)) !== null) {\n      if (m[1].startsWith('at://')) return m[1];\n    }\n    return null;\n  } catch {\n    return null;\n  } finally {\n    if (timeout) clearTimeout(timeout);\n  }\n}\n","import { matchSupportedUrl, parseAtUri } from './reverseParsers';\nimport type { ParsedURI } from './uriParser';\nimport type { WaypointType } from './waypoints.data';\n\n/**\n * Universal links: the aturi.to URL for a record or an identity.\n *\n * A universal link is the client-agnostic address of an atproto record. Drop\n * one anywhere and the recipient lands on a preview of the record and picks\n * the client they want to open it in, instead of being pushed into whichever\n * app the sender happened to use.\n *\n * This module is the whole round trip:\n *   - `buildUniversalLink` returns that address for anything that names a\n *     record: an AT URI, a handle, a DID, a URL from any client in the catalog.\n *   - `parseUniversalLink` turns one back into a `ParsedURI`.\n *   - `describeUniversalLink` adds the strings a share sheet or a copy button\n *     needs (a label, a `navigator.share()` payload, markdown/HTML snippets).\n *   - `buildUniversalLinkTags` emits the `<head>` tags that let *other* apps\n *     be resolved back into records, the read side of the same trip.\n *\n * Everything here is pure and synchronous. Nothing fetches.\n */\n\n/** Where universal links point unless an `origin` says otherwise. */\nexport const UNIVERSAL_LINK_ORIGIN = 'https://aturi.to';\n\n/**\n * The hosted oEmbed endpoint. Only `app.bsky.feed.post` records render, so\n * the oEmbed pointer is omitted for everything else rather than advertising a\n * URL that 404s.\n */\nconst OEMBED_PATH = '/api/oembed';\nconst OEMBED_COLLECTION = 'app.bsky.feed.post';\n\n/** The oEmbed link `type` attribute, per the spec's discovery section. */\nexport const OEMBED_LINK_TYPE = 'application/json+oembed';\n\n/**\n * Anything that names a record or an identity:\n *   - an AT URI (`at://did:plc:abc/app.bsky.feed.post/3k7`)\n *   - a bare handle or DID (`alice.bsky.social`, `@alice.bsky.social`, `did:plc:abc`)\n *   - a scheme-less AT URI (`alice.bsky.social/app.bsky.feed.post/3k7`)\n *   - a page URL from any client in the catalog, an aturi.to link included\n *   - a `ParsedURI` you already have from `parseURI` / `matchSupportedUrl`\n */\nexport type UniversalLinkTarget = string | ParsedURI;\n\nexport type UniversalLinkOptions = {\n  /**\n   * Origin to build against. Defaults to aturi.to; point it at your own\n   * deployment if you run a fork. Trailing slashes are trimmed.\n   */\n  origin?: string;\n  /**\n   * DID for the target, for input that only carries a handle. Handle → DID\n   * resolution is a network call, so this package never does it for you:\n   * pass `resolveHandle`'s result if you want DID-stable links.\n   */\n  did?: string;\n  /**\n   * Address every link by DID instead of handle. A handle can be reassigned\n   * to another identity; a DID is stable for the life of the account, so a\n   * DID link never rots. Ignored when no DID is known.\n   */\n  preferDid?: boolean;\n  /** Query parameters to append, e.g. `{ ref: 'my-app' }`. Empty values are dropped. */\n  params?: Record<string, string | number | boolean | null | undefined>;\n};\n\n/** `navigator.share()`'s payload, which most native share sheets also accept. */\nexport type UniversalLinkSharePayload = {\n  title: string;\n  text: string;\n  url: string;\n};\n\n/** Ready-to-paste forms of the same link. */\nexport type UniversalLinkSnippets = {\n  url: string;\n  atUri: string;\n  markdown: string;\n  html: string;\n};\n\nexport type UniversalLink = {\n  url: string;\n  atUri: string;\n  type: WaypointType;\n  handle: string;\n  did: string | null;\n  collection: string | null;\n  rkey: string | null;\n  /** Human label for the target, e.g. `Post by @alice.bsky.social`. */\n  label: string;\n  share: UniversalLinkSharePayload;\n  snippets: UniversalLinkSnippets;\n  /** oEmbed endpoint for this link, or null for anything that isn't a post. */\n  oembedUrl: string | null;\n};\n\nexport type DescribeUniversalLinkOptions = UniversalLinkOptions & {\n  /** Override the share sheet's title. Defaults to the label. */\n  title?: string;\n  /** Override the share sheet's text. Defaults to the label. */\n  text?: string;\n};\n\nexport type UniversalLinkMetaTag = { name: string; content: string };\nexport type UniversalLinkLinkTag = { rel: string; href: string; type?: string };\n\nexport type UniversalLinkTags = {\n  meta: UniversalLinkMetaTag[];\n  link: UniversalLinkLinkTag[];\n  /** The same tags as a ready-to-paste `<head>` fragment. */\n  html: string;\n};\n\n/**\n * Build the aturi.to link for a target. Returns null for input that doesn't\n * name a record or an identity.\n *\n * ```ts\n * buildUniversalLink('at://did:plc:abc/app.bsky.feed.post/3k7');\n * // 'https://aturi.to/profile/did:plc:abc/post/3k7'\n * buildUniversalLink('https://bsky.app/profile/alice.bsky.social/post/3k7');\n * // 'https://aturi.to/profile/alice.bsky.social/post/3k7'\n * ```\n */\nexport function buildUniversalLink(\n  input: UniversalLinkTarget,\n  options: UniversalLinkOptions = {},\n): string | null {\n  const parsed = parseTarget(input);\n  if (!parsed) return null;\n\n  const origin = normalizeOrigin(options.origin);\n  const did = options.did ?? parsed.did;\n  const { collection, rkey } = parsed;\n\n  // Deliberately the same shape the `aturi` waypoint's own `getUrl` produces,\n  // so a link copied out of the catalog and a link built here are the same\n  // string: posts and lists take the friendly `/post/` and `/lists/` aliases\n  // and keep whichever identifier they were given, while the generic record\n  // route prefers a DID when one is known. `preferDid` overrides all of it.\n  const identifier = options.preferDid && did ? did : parsed.handle;\n\n  let path: string;\n  if (collection && rkey) {\n    if (collection === 'app.bsky.feed.post') {\n      path = `/profile/${seg(identifier)}/post/${seg(rkey)}`;\n    } else if (collection === 'app.bsky.graph.list') {\n      path = `/profile/${seg(identifier)}/lists/${seg(rkey)}`;\n    } else {\n      path = `/profile/${seg(did || parsed.handle)}/${seg(collection)}/${seg(rkey)}`;\n    }\n  } else {\n    path = `/profile/${seg(identifier)}`;\n  }\n\n  return `${origin}${path}${queryString(options.params)}`;\n}\n\n/**\n * Turn an aturi.to URL back into the record it addresses. Accepts every shape\n * the site serves: the canonical `/profile/…` links, the `/explore/…` record\n * views, the legacy bare-path (`aturi.to/{handle}/{collection}/{rkey}`) and\n * `at://`-in-path forms. Returns null for any other host or path.\n */\nexport function parseUniversalLink(\n  url: string | URL,\n  options: Pick<UniversalLinkOptions, 'origin'> = {},\n): ParsedURI | null {\n  let target: URL;\n  try {\n    target = typeof url === 'string' ? new URL(url.trim()) : url;\n  } catch {\n    return null;\n  }\n  if (!/^https?:$/.test(target.protocol)) return null;\n\n  let expectedHost: string;\n  try {\n    expectedHost = bareHost(new URL(normalizeOrigin(options.origin)).hostname);\n  } catch {\n    return null;\n  }\n  if (bareHost(target.hostname) !== expectedHost) return null;\n\n  // The catalog's reverse parsers key off the aturi.to hostname, so a link\n  // from a fork's own origin is rewritten onto it before matching. The host\n  // has already been checked against `origin` above.\n  const probe = new URL(target.toString());\n  probe.protocol = 'https:';\n  probe.hostname = 'aturi.to';\n  probe.port = '';\n\n  const match = matchSupportedUrl(probe);\n  if (match && (match.source === 'aturi' || match.source === 'aturiExplore')) {\n    return normalizeParsed(match.parsed);\n  }\n\n  return parseEmbeddedAtUri(probe.pathname) ?? parsePath(probe.pathname);\n}\n\n/** Whether a URL is an aturi.to link this package can resolve to a record. */\nexport function isUniversalLink(\n  url: string | URL,\n  options: Pick<UniversalLinkOptions, 'origin'> = {},\n): boolean {\n  return parseUniversalLink(url, options) !== null;\n}\n\n/**\n * Everything a copy button or a share sheet needs for one target: the link\n * itself, a human label, a `navigator.share()` payload, and the link in the\n * forms people paste it in.\n *\n * ```ts\n * const link = describeUniversalLink('at://did:plc:abc/app.bsky.feed.post/3k7');\n * await navigator.share(link.share);\n * await navigator.clipboard.writeText(link.snippets.markdown);\n * ```\n */\nexport function describeUniversalLink(\n  input: UniversalLinkTarget,\n  options: DescribeUniversalLinkOptions = {},\n): UniversalLink | null {\n  const parsed = parseTarget(input);\n  if (!parsed) return null;\n  const url = buildUniversalLink(parsed, options);\n  if (!url) return null;\n\n  const did = options.did ?? parsed.did ?? null;\n  const collection = parsed.collection ?? null;\n  const rkey = parsed.rkey ?? null;\n  // A caller who supplies a DID gets AT URIs addressed by it, the canonical\n  // rename-proof form. Without one, the input's own identifier is echoed back\n  // rather than silently changing what was passed in.\n  const authority = did ?? parsed.handle;\n  const atUri = collection && rkey\n    ? `at://${authority}/${collection}/${rkey}`\n    : `at://${authority}`;\n  const label = describeTarget(parsed);\n\n  return {\n    url,\n    atUri,\n    type: parsed.type,\n    handle: parsed.handle,\n    did,\n    collection,\n    rkey,\n    label,\n    share: {\n      title: options.title ?? label,\n      text: options.text ?? label,\n      url,\n    },\n    snippets: {\n      url,\n      atUri,\n      markdown: `[${label}](${url})`,\n      html: `<a href=\"${escapeHtml(url)}\">${escapeHtml(label)}</a>`,\n    },\n    oembedUrl: buildOEmbedUrl(url, collection, options.origin),\n  };\n}\n\n/**\n * `<head>` tags that connect a page to the record it renders, so the rest of\n * the Atmosphere can find its way back. Two consumers today:\n *\n *   - `<meta name=\"at:canonical\">` is the AT Tags proposal\n *     (https://tangled.org/chrisshank.com/at-tags/). Aturi's browser extension\n *     reads it off the live page and `aturi.to/api/resolve` reads it off the\n *     HTML, which is what turns your URL into \"…and here are the 25 other\n *     clients that can open this\". The `<link rel=\"alternate\" href=\"at://…\">`\n *     alongside it is the older spelling of the same declaration, kept because\n *     the resolver still falls back to it.\n *   - `<link type=\"application/json+oembed\">` points unfurlers at the hosted\n *     oEmbed endpoint, so a link to your page previews as the post it is.\n *     Emitted for posts only, since that's all the endpoint renders.\n *\n * Serving these does not hand anything to aturi.to; they're static strings\n * describing a record you already display.\n */\nexport function buildUniversalLinkTags(\n  input: UniversalLinkTarget,\n  options: UniversalLinkOptions = {},\n): UniversalLinkTags | null {\n  const described = describeUniversalLink(input, options);\n  if (!described) return null;\n\n  const meta: UniversalLinkMetaTag[] = [\n    { name: 'at:canonical', content: described.atUri },\n  ];\n  // A record lives in its author's repo, so the repo identifier *is* the\n  // author. For a profile the canonical tag already says so; a second tag\n  // naming the same identity would be noise.\n  if (described.collection && described.rkey) {\n    meta.push({\n      name: 'at:author',\n      content: `at://${described.did ?? described.handle}`,\n    });\n  }\n\n  const link: UniversalLinkLinkTag[] = [\n    { rel: 'alternate', href: described.atUri },\n  ];\n  if (described.oembedUrl) {\n    link.push({\n      rel: 'alternate',\n      type: OEMBED_LINK_TYPE,\n      href: described.oembedUrl,\n    });\n  }\n\n  const html = [\n    ...meta.map(\n      (tag) =>\n        `<meta name=\"${escapeHtml(tag.name)}\" content=\"${escapeHtml(tag.content)}\" />`,\n    ),\n    ...link.map((tag) => {\n      const type = tag.type ? ` type=\"${escapeHtml(tag.type)}\"` : '';\n      return `<link rel=\"${escapeHtml(tag.rel)}\"${type} href=\"${escapeHtml(tag.href)}\" />`;\n    }),\n  ].join('\\n');\n\n  return { meta, link, html };\n}\n\n/**\n * Coerce any accepted target into a `ParsedURI`. Order matters: AT URIs and\n * page URLs are unambiguous, so they're tried first, and the loose bare-input\n * forms only get a look once those have declined.\n */\nfunction parseTarget(input: UniversalLinkTarget): ParsedURI | null {\n  if (typeof input !== 'string') {\n    return input && input.handle ? normalizeParsed(input) : null;\n  }\n\n  const trimmed = input.trim();\n  if (!trimmed) return null;\n\n  if (trimmed.toLowerCase().startsWith('at://')) {\n    const parsed = parseAtUri(trimmed)?.parsed;\n    return parsed ? normalizeParsed(parsed) : null;\n  }\n\n  if (/^https?:\\/\\//i.test(trimmed)) {\n    let target: URL;\n    try {\n      target = new URL(trimmed);\n    } catch {\n      return null;\n    }\n    // Any host can carry an AT URI in its path: `example.com/at://did:plc:…`,\n    // and the single-slash `at:/…` spelling servers and browsers normalize it\n    // to. Checked before the catalog's URL patterns because a host in the\n    // catalog can serve both shapes.\n    const embedded = parseEmbeddedAtUri(target.pathname);\n    if (embedded) return embedded;\n    const matched = matchSupportedUrl(target)?.parsed;\n    return matched ? normalizeParsed(matched) : null;\n  }\n\n  // Bare identifiers and scheme-less AT URIs.\n  return parsePath(trimmed.startsWith('@') ? trimmed.slice(1) : trimmed);\n}\n\n/**\n * Parse `{identifier}[/{collection}/{rkey}]`, the shape shared by a bare\n * handle, a scheme-less AT URI, and aturi.to's legacy bare paths. The\n * identifier must look like a DID or a dotted handle, which is what keeps\n * ordinary site paths (`/docs`, `/explore/lexicons`) from parsing as repos.\n */\nfunction parsePath(path: string): ParsedURI | null {\n  const segments = path.split('/').filter(Boolean);\n  const handle = decodeSegment(segments[0] ?? '');\n  if (!handle) return null;\n  if (!handle.startsWith('did:') && !handle.includes('.')) return null;\n\n  // Parsed from the raw segments so an escaped character can never be mistaken\n  // for a path separator, then decoded on the way out.\n  const parsed = parseAtUri(`at://${segments.join('/')}`)?.parsed;\n  if (!parsed) return null;\n\n  const collection = parsed.collection\n    ? decodeSegment(parsed.collection)\n    : undefined;\n  const rkey = parsed.rkey ? decodeSegment(parsed.rkey) : undefined;\n  return {\n    ...parsed,\n    handle,\n    did: handle.startsWith('did:') ? handle : undefined,\n    collection,\n    rkey,\n    uri:\n      collection && rkey\n        ? `at://${handle}/${collection}/${rkey}`\n        : `at://${handle}`,\n  };\n}\n\n/**\n * An `@` in front of a handle is display sugar, never part of the identifier,\n * but some clients put it in the path (`tangled.org/@alice.example`), so the\n * catalog's reverse parsers hand it back attached. Strip it before it reaches\n * a URL, where it would be escaped to `%40` and address nobody.\n */\nfunction normalizeParsed(parsed: ParsedURI): ParsedURI {\n  if (!parsed.handle.startsWith('@')) return parsed;\n  const handle = parsed.handle.slice(1);\n  if (!handle) return parsed;\n  return {\n    ...parsed,\n    handle,\n    uri:\n      parsed.collection && parsed.rkey\n        ? `at://${handle}/${parsed.collection}/${parsed.rkey}`\n        : `at://${handle}`,\n  };\n}\n\n/** Pull `at://…` out of a URL path that embeds one. */\nfunction parseEmbeddedAtUri(pathname: string): ParsedURI | null {\n  const match = /^\\/at:\\/{1,2}(.+)$/i.exec(pathname);\n  if (!match) return null;\n  return parsePath(match[1]);\n}\n\nfunction buildOEmbedUrl(\n  url: string,\n  collection: string | null,\n  origin?: string,\n): string | null {\n  if (collection !== OEMBED_COLLECTION) return null;\n  return `${normalizeOrigin(origin)}${OEMBED_PATH}?url=${encodeURIComponent(url)}`;\n}\n\nfunction describeTarget(parsed: ParsedURI): string {\n  const who = parsed.handle.startsWith('did:')\n    ? parsed.handle\n    : `@${parsed.handle}`;\n  if (parsed.type === 'post') return `Post by ${who}`;\n  if (parsed.type === 'list') return `List by ${who}`;\n  if (parsed.collection) return `${parsed.collection} record by ${who}`;\n  return who;\n}\n\nfunction normalizeOrigin(origin?: string): string {\n  if (!origin) return UNIVERSAL_LINK_ORIGIN;\n  return origin.trim().replace(/\\/+$/, '') || UNIVERSAL_LINK_ORIGIN;\n}\n\n/** Hostnames compare without a `www.` prefix; aturi.to serves both. */\nfunction bareHost(hostname: string): string {\n  return hostname.toLowerCase().replace(/^www\\./, '');\n}\n\n/**\n * Percent-encode a path segment without touching the characters atproto\n * identifiers are made of. `encodeURIComponent` would turn the colons in\n * `did:plc:…` into `%3A`, and these routes serve DIDs unencoded, so an encoded\n * one points at a URL that doesn't exist. DIDs, NSIDs and record keys are\n * drawn from alphabets that need no escaping, so they pass through\n * byte-identical; anything else still gets escaped rather than forming a\n * broken URL.\n */\nfunction seg(value: string): string {\n  return encodeURIComponent(value).replace(/%3A/gi, ':');\n}\n\nfunction decodeSegment(value: string): string {\n  try {\n    return decodeURIComponent(value);\n  } catch {\n    return value;\n  }\n}\n\nfunction queryString(params?: UniversalLinkOptions['params']): string {\n  if (!params) return '';\n  const search = new URLSearchParams();\n  for (const [key, value] of Object.entries(params)) {\n    if (value === null || value === undefined || value === '') continue;\n    search.set(key, String(value));\n  }\n  const query = search.toString();\n  return query ? `?${query}` : '';\n}\n\nfunction escapeHtml(value: string): string {\n  return value\n    .replace(/&/g, '&amp;')\n    .replace(/</g, '&lt;')\n    .replace(/>/g, '&gt;')\n    .replace(/\"/g, '&quot;')\n    .replace(/'/g, '&#39;');\n}\n"]}