@aglyn/plugins-redirects 1.0.0-beta.221 → 1.0.0-beta.223

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../../../../../../libs/plugins/redirects/src/lib/transfer/redirects-transfer.ts"],"sourcesContent":["/**\n * @license\n * Copyright 2026 Aglyn LLC\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport { createResourceUid } from '@aglyn/aglyn/app-utils/create-resource-uid'\nimport { TENANT_APEX } from '@aglyn/aglyn/app-utils/tenant-apex'\nimport { hostRoleCanPublish, hostRoleCanWrite } from '@aglyn/aglyn/app-utils/organizations'\nimport { checkEntitlement, checkQuota } from '@aglyn/aglyn/app-utils/plan-entitlements'\nimport {\n ACKNOWLEDGED_WARNING_CLASSES,\n TRANSFER_ID_FIELD,\n TRANSFER_WARNING_CLASSES,\n buildTransferPlan,\n isBlankTransferValue,\n matchLookupKey,\n planTransferUndo,\n transferValuesEqual,\n withTransferResourceFindings,\n type BuildTransferPlanInput,\n type PlannedTransferRow,\n type RowMatchOutcome,\n type TransferFieldChange,\n type TransferPlan,\n type TransferPlanRow,\n type TransferPlanSummary,\n type TransferResourceFinding,\n type TransferRowResult,\n type TransferUndoEntry,\n type TransferUndoStep,\n type TransferWarning,\n} from '@aglyn/aglyn/data-transfer'\nimport {\n pluginHostResource,\n type ResolvedPluginHostResource,\n} from '@aglyn/aglyn/plugin-manager/plugin-host-resources'\nimport { dropPluginSiteCache } from '@aglyn/aglyn/plugin-manager/plugin-site-cache'\nimport type {\n PluginTransferResource,\n TransferApplyResult,\n TransferApplyWriter,\n TransferLookupResult,\n TransferMatchAnswer,\n TransferReadOptions,\n TransferReadPage,\n TransferResourceContext,\n TransferRevertDecisions,\n TransferRevertResult,\n} from '@aglyn/aglyn/plugin-manager/plugin-transfer-resources'\nimport { FieldPath, FieldValue, Timestamp } from 'firebase-admin/firestore'\nimport {\n REDIRECT_DEFAULT_PRIORITY,\n REDIRECT_STATUS_CODES,\n findDuplicateRedirect,\n isExternalRedirectDestination,\n isSelfRedirect,\n normalizeRedirectDestination,\n normalizeRedirectSource,\n redirectHitKey,\n redirectSourceIsLivePage,\n validateRedirectRule,\n walkRedirectChain,\n type RedirectRuleRow,\n} from '../model/redirects'\nimport {\n REDIRECTS_ALIAS_DICTIONARIES,\n REDIRECTS_DEFAULT_POLICY,\n REDIRECTS_MATCH_KEYS,\n REDIRECT_FIELD,\n REDIRECT_HOST_RESOURCE_KIND,\n REDIRECT_WRITABLE_FIELDS,\n canonicalRedirectKind,\n redirectValuesEqual,\n redirectsTransferCatalog,\n} from './redirects-transfer-fields'\n\n/*==========================================\n * THE REDIRECTS RESOURCE — a site's redirect rules, in and out of a file.\n *\n * A rule is a routing statement over the live site the moment it is written,\n * so an import writes nothing the redirects page or the create route would\n * not. Every write here makes the checks those paths make, in the same words:\n *\n * - who: the publishing role on the site (`hostRoleCanPublish`, the axis the\n * Firestore rules gate the collection on) and the plan's `redirects`\n * feature — read from the create route's own declaration of the kind, not\n * restated. Without either, every row is refused with the reason.\n * - what: the declaration's allow-list of fields, the page's normalization\n * of the from-path and the destination, its defaults (exact, 302, priority\n * 100, on), and `validateRedirectRule` — so a lookalike destination, a\n * pattern the matcher cannot run and a path that redirects to itself are\n * refused, as the page refuses them.\n * - against what: the page's duplicate check (`findDuplicateRedirect`) and\n * chain-loop walk (`walkRedirectChain`) over the site's rules as the\n * import leaves them, row by row in file order, so a row is refused\n * exactly when saving it after the rows above would be refused.\n * - how many: a new rule is counted and created in one transaction against\n * the plan's `redirectsPerHost`, as the create route does; the dry run\n * holds the creates past what the plan leaves.\n * - provenance: `externalDestinationApprovedBy` is never read from a file.\n * A written rule whose destination is off the site carries the importing\n * member's uid, the same stamp the page and the route write and the serve\n * path requires; one whose destination is on the site has it removed.\n * The dry run says so for every such row, naming the host.\n * - afterwards: a created rule gets the route's `createdAt`, `updatedAt`,\n * `createdBy` and its \"Created redirect\" activity line; every written\n * from-path (and one an update moved away from) is announced to the site\n * cache, `/` for a regex rule, as the page announces a save.\n *\n * The dry run also warns, without refusing, where the page warns or a\n * person would want to know: a from-path that is a published page, a\n * destination that is itself redirected (a chain), and one that leads into a\n * loop other rules make.\n *\n * Reads skip soft-deleted rules (`deletedAt`), as the page does. Undo\n * deletes a rule the import created — outright rather than soft-deleted:\n * the rule did not exist before the import, and a soft-deleted document\n * would keep occupying a slot the plan's counter counts — and restores the\n * fields an update changed, stamp included.\n *=========================================*/\n\n/** The billing document a plan's entitlement and counter are read from. */\ntype OrgBilling = Parameters<typeof checkEntitlement>[0]\n\nexport interface RedirectsTransferDeps {\n firestore: FirebaseFirestore.Firestore\n /** Defaults to `Date.now`. */\n now?: () => number\n /** The site's owning workspace's billing document (`getOrgForHost`); `null` reads as the free plan. */\n loadOrg(hostId: string): Promise<OrgBilling | null>\n /**\n * Drops the site's cached pages at these addresses, best effort. Defaults\n * to the platform's site cache (`dropPluginSiteCache`), the announcement\n * the create route makes for a new rule.\n */\n announcePaths?(hostId: string, paths: readonly string[]): Promise<void>\n /** Writes the site activity line for a created rule, best effort. */\n logCreated?(hostId: string, actorUid: string, ruleId: string, resource: ResolvedPluginHostResource): Promise<void>\n}\n\n/** How long before the chunk's budget runs out a row is not started. */\nconst ROW_RESERVE_MS = 2_000\n\n/** The most rows one export page reads. */\nconst PAGE_SIZE_DEFAULT = 500\nconst PAGE_SIZE_MAX = 1_000\n\n/** Values one `in` query may name. */\nconst IN_QUERY_MAX = 30\n\n/** Documents one `getAll` reads. */\nconst GET_ALL_MAX = 100\n\n/** Days the hit count sums, as the redirects page does. */\nconst HIT_DAYS = 30\n\nconst DAY_MS = 24 * 60 * 60 * 1000\n\n/*==========================================\n * A RULE AS THE TRANSFER READS IT\n *=========================================*/\n\ntype StoredRule = Record<string, unknown>\n\n/** The rule's six writable fields, as written. */\ninterface RuleFields {\n source: string\n kind: string\n destination: string\n statusCode: number\n priority: number\n enabled: boolean\n}\n\nfunction text(value: unknown): string {\n return typeof value === 'string' ? value : ''\n}\n\n/** A stored time as ISO text, or `null`. */\nfunction isoOf(value: unknown): string | null {\n if (value === null || value === undefined) return null\n if (typeof (value as { toMillis?: unknown }).toMillis === 'function') {\n return new Date((value as { toMillis(): number }).toMillis()).toISOString()\n }\n if (value instanceof Date) return value.toISOString()\n if (typeof value === 'number' && Number.isFinite(value)) return new Date(value).toISOString()\n return null\n}\n\nfunction validStatusCode(value: unknown): value is RuleFields['statusCode'] {\n return (REDIRECT_STATUS_CODES as readonly number[]).includes(value as number)\n}\n\n/**\n * A stored rule's fields as the redirects page reads them into its editor: a\n * missing mode is exact, a missing priority 100, a status code outside the\n * four is 302 (as the serve path reads it), and a rule is on unless it says\n * `false`. The export, the dry run's \"before\" and undo all read this, so a\n * file exported and imported back is unchanged.\n */\nexport function redirectRuleValues(id: string, data: StoredRule): Record<string, unknown> {\n const priority = data['priority']\n return {\n [TRANSFER_ID_FIELD]: id,\n source: text(data['source']),\n kind: typeof data['kind'] === 'string' && data['kind'] ? data['kind'] : 'exact',\n destination: text(data['destination']),\n statusCode: validStatusCode(data['statusCode']) ? data['statusCode'] : 302,\n priority:\n priority !== null && priority !== undefined && Number.isFinite(Number(priority))\n ? Number(priority)\n : REDIRECT_DEFAULT_PRIORITY,\n enabled: data['enabled'] !== false,\n [REDIRECT_FIELD.approvedBy]:\n typeof data[REDIRECT_FIELD.approvedBy] === 'string' && data[REDIRECT_FIELD.approvedBy]\n ? data[REDIRECT_FIELD.approvedBy]\n : null,\n createdAt: isoOf(data['createdAt']),\n updatedAt: isoOf(data['updatedAt']),\n createdBy: typeof data['createdBy'] === 'string' ? data['createdBy'] : null,\n lastHitAt: isoOf(data['lastHitAt']),\n }\n}\n\n/** A rule as the whole-set checks read it: as stored, like the page's rows. */\nfunction ruleRow(id: string, data: StoredRule): RedirectRuleRow {\n return {\n $id: id,\n source: data['source'] as string,\n destination: data['destination'] as string,\n kind: data['kind'] as string,\n }\n}\n\nfunction isLive(data: StoredRule | undefined): data is StoredRule {\n return Boolean(data) && !data?.['deletedAt']\n}\n\n/**\n * The from-path as a rule of `kind` stores it: a pattern trimmed, a path\n * normalized (lowercase, no trailing slash, no query); `null` when a path\n * cannot be one.\n */\nfunction storedSource(kind: string, source: string): string | null {\n if (kind === 'regex') return source.trim() || null\n return normalizeRedirectSource(source)\n}\n\n/** What makes two rules one: their mode and their from-path, as stored. */\nfunction ruleKey(kind: string, source: string): string | null {\n const stored = storedSource(kind, source)\n return stored === null ? null : `${kind}\\u0000${stored}`\n}\n\n/** The address a rule answers at, for the site cache: a pattern names no one path, so `/`. */\nfunction announcedPath(rule: { kind?: string; source?: string }): string | null {\n const source = text(rule.source)\n if ((rule.kind ?? 'exact') === 'regex') return '/'\n return source.startsWith('/') ? source : null\n}\n\n/** The rule a row leaves: what the record held (or the defaults), with the row's changes. */\nfunction finalRule(\n before: Readonly<Record<string, unknown>> | null | undefined,\n diff: readonly TransferFieldChange[],\n): RuleFields {\n const values: Record<string, unknown> = { ...(before ?? {}) }\n for (const change of diff) values[change.fieldId] = change.after\n return withDefaults(values)\n}\n\n/**\n * The six fields with the page's defaults where a value is missing:\n * exact, 302, priority 100, on.\n */\nfunction withDefaults(values: Readonly<Record<string, unknown>>): RuleFields {\n const priority = values['priority']\n const kind = canonicalRedirectKind(values['kind'])\n return {\n source: text(values['source']),\n kind: isBlankTransferValue(values['kind']) ? 'exact' : (kind ?? String(values['kind'])),\n destination: text(values['destination']),\n statusCode: isBlankTransferValue(values['statusCode'])\n ? 302\n : (Number(values['statusCode']) as RuleFields['statusCode']),\n priority:\n priority !== null && priority !== undefined && Number.isFinite(Number(priority))\n ? Number(priority)\n : REDIRECT_DEFAULT_PRIORITY,\n enabled: values['enabled'] !== false,\n }\n}\n\n/** The site's own addresses, which a destination may always name. */\nfunction ownDomains(host: StoredRule): Array<string | null> {\n return [\n typeof host['cname'] === 'string' ? host['cname'] : null,\n typeof host['subdomain'] === 'string' && host['subdomain'] ? `${host['subdomain']}.${TENANT_APEX}` : null,\n ]\n}\n\n/**\n * Why the page would refuse to save this rule, or `null`: an unknown mode, a\n * from-path or pattern it cannot use, a destination it cannot use or that\n * wears another company's address, a status code it does not offer, or a\n * path redirected to itself.\n */\nfunction ruleProblem(rule: RuleFields, host: StoredRule): { detail: string; fieldId: string; value: string } | null {\n const problem = validateRedirectRule(\n { kind: rule.kind, source: rule.source, destination: rule.destination },\n { ownDomains: ownDomains(host) },\n )\n if (problem) {\n const fieldId =\n problem === 'Unknown match mode'\n ? REDIRECT_FIELD.kind\n : /destination/i.test(problem)\n ? REDIRECT_FIELD.destination\n : REDIRECT_FIELD.source\n return { detail: problem, fieldId, value: String((rule as unknown as Record<string, unknown>)[fieldId] ?? '') }\n }\n if (!validStatusCode(rule.statusCode)) {\n return {\n detail: 'Status codes are 301, 302, 307 or 308',\n fieldId: REDIRECT_FIELD.statusCode,\n value: String(rule.statusCode),\n }\n }\n if (rule.kind !== 'regex' && isSelfRedirect({ source: rule.source, destination: rule.destination })) {\n return { detail: 'That would redirect the path to itself', fieldId: REDIRECT_FIELD.destination, value: rule.destination }\n }\n return null\n}\n\n/** The rule's fields as stored: the page's normalization, and only what the create route's allow-list names. */\nfunction storedFields(rule: RuleFields, allowed: readonly string[]): Record<string, unknown> {\n const normalized: Record<string, unknown> = {\n source: rule.kind === 'regex' ? rule.source.trim() : (normalizeRedirectSource(rule.source) ?? rule.source),\n destination: normalizeRedirectDestination(rule.destination) ?? rule.destination,\n statusCode: rule.statusCode,\n kind: rule.kind,\n priority: rule.priority,\n enabled: rule.enabled,\n }\n return Object.fromEntries(Object.entries(normalized).filter(([key]) => allowed.includes(key)))\n}\n\nfunction hostnameOf(destination: string): string {\n try {\n return new URL(destination).hostname || destination\n } catch {\n return destination\n }\n}\n\n/*==========================================\n * THE SITE, AS A WRITE IS DECIDED AGAINST IT\n *=========================================*/\n\ninterface SiteState {\n hostId: string\n host: StoredRule\n org: OrgBilling | null\n declared: ResolvedPluginHostResource\n /** Why nothing may be written, or `null`. */\n refusal: string | null\n /** The plan's cap on rules on the site, `Infinity` for none. */\n limit: number\n}\n\nfunction requireHost(ctx: TransferResourceContext): string {\n if (!ctx.hostId) throw new Error('Redirects belong to a site; open the import from the site.')\n return ctx.hostId\n}\n\n/** The redirect kind's declaration, which the create route reads too. */\nfunction redirectDeclaration(): ResolvedPluginHostResource {\n const declared = pluginHostResource(REDIRECT_HOST_RESOURCE_KIND)\n if (!declared) throw new Error(`The \"${REDIRECT_HOST_RESOURCE_KIND}\" kind is not declared.`)\n return declared\n}\n\n/** Field ids → values, holding only `fieldIds`. */\nfunction pick(values: Readonly<Record<string, unknown>>, fieldIds: readonly string[]): Record<string, unknown> {\n const row: Record<string, unknown> = {}\n for (const fieldId of fieldIds) row[fieldId] = values[fieldId] ?? null\n return row\n}\n\n/** Each `size` items of `items`. */\nfunction slices<T>(items: readonly T[], size: number): T[][] {\n const out: T[][] = []\n for (let at = 0; at < items.length; at += size) out.push(items.slice(at, at + size))\n return out\n}\n\n/**\n * The plan with every create past `remaining` failed as `planLimit`, counted\n * after the rows the plugin refused — a refused row takes no slot.\n */\nfunction withCreateLimit(plan: TransferPlan, remaining: number, limit: number): TransferPlan {\n if (!Number.isFinite(remaining)) return plan\n let creates = 0\n const held: PlannedTransferRow[] = []\n const rows = plan.rows.map((row) => {\n if (row.verdict !== 'create') return row\n if (creates < remaining) {\n creates += 1\n return row\n }\n const failed: PlannedTransferRow = {\n ...row,\n verdict: 'fail',\n reason: 'planLimit',\n diff: [],\n warnings: row.warnings.includes('planLimit') ? row.warnings : [...row.warnings, 'planLimit'],\n }\n held.push(failed)\n return failed\n })\n if (!held.length) return plan\n const summary: TransferPlanSummary = { create: 0, update: 0, unchanged: 0, skip: 0, fail: 0, total: rows.length }\n for (const row of rows) summary[row.verdict] += 1\n const detail = `Your plan includes ${limit} redirects on this site`\n const prior = plan.warnings.find((entry) => entry.class === 'planLimit')\n const raised: TransferWarning = {\n class: 'planLimit',\n count: (prior?.count ?? 0) + held.length,\n rows: (prior?.rows ?? 0) + held.length,\n fieldIds: prior?.fieldIds ?? [],\n samples: [...(prior?.samples ?? []), ...held.map((row) => ({ row: row.index, detail }))].slice(0, 5),\n requiresAcknowledgement: ACKNOWLEDGED_WARNING_CLASSES.includes('planLimit'),\n }\n const warnings = TRANSFER_WARNING_CLASSES.flatMap((entry) =>\n entry === 'planLimit' ? [raised] : plan.warnings.filter((warning) => warning.class === entry),\n )\n return {\n rows,\n summary,\n warnings,\n acknowledgementsRequired: warnings.filter((entry) => entry.requiresAcknowledgement).map((entry) => entry.class),\n }\n}\n\n/*==========================================\n * MATCHING, DEFAULTS AND SAMENESS (AGL-3548)\n *=========================================*/\n\n/**\n * Each row's rule, as the page tells rules apart: a row the engine found by\n * its id keeps that rule; any other row is the rule of its mode (exact when\n * the file gives none) at its from-path as stored — so `/blog` names the\n * exact rule or the prefix rule beside it by the row's mode, never both.\n * Two rows naming one rule are both matched to it here, and the plan refuses\n * the later one, saying which row it repeats, rather than holding it back as\n * a duplicate. `existing` holds every live rule's values by id; running this\n * over its own outcomes changes nothing.\n */\nexport function redirectMatchOutcomes(\n rows: ReadonlyArray<Readonly<Record<string, unknown>>>,\n engine: readonly RowMatchOutcome[],\n existing: ReadonlyMap<string, Readonly<Record<string, unknown>>>,\n live: ReadonlyArray<{ id: string; data: StoredRule }>,\n): RowMatchOutcome[] {\n // Each live rule under its mode and stored from-path.\n const byKey = new Map<string, string[]>()\n for (const { id, data } of live) {\n const key = ruleKey(text(data['kind']) || 'exact', text(data['source']))\n if (key) byKey.set(key, [...(byKey.get(key) ?? []), id])\n }\n return rows.map((values, at): RowMatchOutcome => {\n const found = engine[at] ?? { kind: 'new' as const }\n const byId = found.kind !== 'new' && found.via.fieldId === TRANSFER_ID_FIELD\n const record = found.kind === 'matched' && byId ? existing.get(found.recordId) : undefined\n const rowKind = isBlankTransferValue(values['kind'])\n ? text(record?.['kind']) || 'exact'\n : canonicalRedirectKind(values['kind'])\n const source = isBlankTransferValue(values['source']) ? text(record?.['source']) : text(values['source'])\n const key = rowKind && source ? ruleKey(rowKind, source) : null\n if (byId || !key || !rowKind) return found\n const candidates = byKey.get(key) ?? []\n const via = { fieldId: REDIRECT_FIELD.source, value: storedSource(rowKind, source) as string }\n if (!candidates.length) return { kind: 'new' }\n return candidates.length === 1\n ? { kind: 'matched', recordId: candidates[0] as string, via }\n : { kind: 'ambiguous', recordIds: candidates, via }\n })\n}\n\n/*==========================================\n * THE RESOURCE\n *=========================================*/\n\n/**\n * The id a rule an import creates is written under: the job's row, so a\n * write retried after it landed and before the ledger recorded it finds its\n * own rule instead of making a second one. Without a job, a fresh resource id.\n */\nexport function importedRedirectId(jobId: string | undefined, row: number): string {\n return jobId ? `${jobId}-${row}` : createResourceUid()\n}\n\n/**\n * The redirects resource over `deps.firestore`: `hosts/{hostId}/redirects`,\n * with every hook the job engine and the export route call. See the block\n * above for what each write checks.\n */\nexport function createRedirectsTransferResource(deps: RedirectsTransferDeps): PluginTransferResource {\n const now = deps.now ?? (() => Date.now())\n const { firestore } = deps\n const announce =\n deps.announcePaths ??\n (async (hostId: string, paths: readonly string[]) => {\n await dropPluginSiteCache({\n hostIds: [hostId],\n paths: { [hostId]: [...paths] },\n reason: 'redirect rules were imported',\n })\n })\n\n const hostRef = (hostId: string) => firestore.collection('hosts').doc(hostId)\n const rulesOf = (hostId: string) => hostRef(hostId).collection('redirects')\n\n async function readSite(ctx: TransferResourceContext): Promise<SiteState> {\n const hostId = requireHost(ctx)\n const [snapshot, org] = await Promise.all([hostRef(hostId).get(), deps.loadOrg(hostId)])\n const host = (snapshot.exists ? snapshot.data() : null) ?? {}\n const declared = redirectDeclaration()\n const role = ctx.actorUid ? ((host['memberRoles'] ?? {}) as Record<string, unknown>)[ctx.actorUid] : undefined\n // The route's question, on the route's axis: a kind that is live the\n // moment it exists needs the publishing role, never just the write role.\n const roleOk = declared.requiresPublishRole ? hostRoleCanPublish(role) : hostRoleCanWrite(role)\n // A plan-less workspace resolves as the free plan, which has no redirects.\n const billing = org ?? {}\n let refusal: string | null = null\n if (!snapshot.exists) refusal = 'This site no longer exists.'\n else if (!roleOk) refusal = 'Importing redirects needs a publishing role on this site — ask an editor or admin'\n else if (declared.entitlement && !checkEntitlement(billing, declared.entitlement)) {\n refusal = 'URL redirects are not included in this workspace’s plan — see Billing'\n }\n const limit = declared.quotaKey\n ? checkQuota(billing, declared.quotaKey as Parameters<typeof checkQuota>[1], 0).limit\n : Number.POSITIVE_INFINITY\n return { hostId, host, org: billing, declared, refusal, limit }\n }\n\n /** Every rule document of the site, soft-deleted ones included. */\n async function readAllRules(hostId: string): Promise<Array<{ id: string; data: StoredRule }>> {\n const snapshot = await rulesOf(hostId).get()\n return snapshot.docs.map((doc) => ({ id: doc.id, data: doc.data() as StoredRule }))\n }\n\n async function readByIds(hostId: string, ids: readonly string[]): Promise<Map<string, StoredRule>> {\n const found = new Map<string, StoredRule>()\n for (const slice of slices([...new Set(ids)], GET_ALL_MAX)) {\n if (!slice.length) continue\n const snapshots = await firestore.getAll(...slice.map((id) => rulesOf(hostId).doc(id)))\n for (const snapshot of snapshots) {\n const data = snapshot.exists ? (snapshot.data() as StoredRule) : undefined\n if (isLive(data)) found.set(snapshot.id, data)\n }\n }\n return found\n }\n\n /** Each rule's sampled hits over the last thirty days, by its hit key. */\n async function readHits(hostId: string): Promise<Record<string, number>> {\n const today = now()\n const refs = Array.from({ length: HIT_DAYS }, (_, index) =>\n hostRef(hostId)\n .collection('analytics')\n .doc(new Date(today - index * DAY_MS).toISOString().slice(0, 10)),\n )\n const totals: Record<string, number> = {}\n for (const snapshot of await firestore.getAll(...refs)) {\n if (!snapshot.exists) continue\n const day = ((snapshot.data() as StoredRule)['redirects'] ?? {}) as Record<string, unknown>\n for (const [key, count] of Object.entries(day)) {\n const value = Number(count)\n if (Number.isFinite(value)) totals[key] = (totals[key] ?? 0) + value\n }\n }\n return totals\n }\n\n function exportRow(\n id: string,\n data: StoredRule,\n fieldIds: readonly string[],\n hits: Record<string, number> | null,\n ): Record<string, unknown> {\n const values = redirectRuleValues(id, data)\n if (hits) values[REDIRECT_FIELD.hits] = hits[redirectHitKey(id)] ?? 0\n return pick(values, fieldIds)\n }\n\n const resource: PluginTransferResource = {\n fields: () => redirectsTransferCatalog(),\n matchKeys: REDIRECTS_MATCH_KEYS,\n aliases: REDIRECTS_ALIAS_DICTIONARIES,\n defaultPolicy: REDIRECTS_DEFAULT_POLICY,\n valuesEqual: redirectValuesEqual,\n\n /*\n * Rows matched as the page tells rules apart (`redirectMatchOutcomes`),\n * over every live rule of the site — so the Matching step and the\n * Conflicts step show the rule the dry run will update.\n */\n async match(ctx, input): Promise<TransferMatchAnswer> {\n const hostId = requireHost(ctx)\n const live = (await readAllRules(hostId)).filter((entry) => isLive(entry.data))\n const existing = new Map(input.records)\n for (const { id, data } of live) existing.set(id, redirectRuleValues(id, data))\n const outcomes = redirectMatchOutcomes(input.rows, input.outcomes, existing, live)\n const records = new Map<string, Readonly<Record<string, unknown>>>()\n for (const outcome of outcomes) {\n const ids = outcome.kind === 'matched' ? [outcome.recordId] : outcome.kind === 'ambiguous' ? outcome.recordIds : []\n for (const id of ids) {\n const values = existing.get(id)\n if (values && !input.records.has(id)) records.set(id, values)\n }\n }\n return { outcomes, records }\n },\n\n /*\n * `filter` is not read: the redirects page lists every rule and has no\n * filter to export by. `scopeTokens` does not narrow either: rules are a\n * site's, carry no `visibleTo`, and the export route admits a reader to\n * a site's records only when they reach the site.\n */\n async count(ctx: TransferResourceContext, options: TransferReadOptions): Promise<number> {\n const hostId = requireHost(ctx)\n if (options.ids) return (await readByIds(hostId, options.ids)).size\n const [all, deleted] = await Promise.all([\n rulesOf(hostId).count().get(),\n rulesOf(hostId).where('deletedAt', '!=', null).count().get(),\n ])\n return Math.max(0, all.data().count - deleted.data().count)\n },\n\n async readPage(\n ctx: TransferResourceContext,\n cursor: string | null,\n fieldIds: readonly string[],\n options: TransferReadOptions = {},\n ): Promise<TransferReadPage> {\n const hostId = requireHost(ctx)\n const size = Math.min(PAGE_SIZE_MAX, Math.max(1, Math.floor(options.pageSize ?? PAGE_SIZE_DEFAULT)))\n const hits = fieldIds.includes(REDIRECT_FIELD.hits) ? await readHits(hostId) : null\n if (options.ids) {\n // The selection, in the order it was made; the cursor is how far into it.\n const start = Math.max(0, Number(cursor ?? 0) || 0)\n const ids = options.ids.slice(start, start + size)\n const found = await readByIds(hostId, ids)\n const rows = ids.flatMap((id) => {\n const data = found.get(id)\n return data ? [exportRow(id, data, fieldIds, hits)] : []\n })\n return { rows, next: start + size < options.ids.length ? String(start + size) : null }\n }\n // Ordered by document id, the one order every rule has: a rule with no\n // `source` still exports (the page sorts by source, in the browser).\n let query = rulesOf(hostId).orderBy(FieldPath.documentId()).limit(size)\n if (cursor) query = query.startAfter(cursor)\n const snapshot = await query.get()\n const rows = snapshot.docs.flatMap((doc) => {\n const data = doc.data() as StoredRule\n return isLive(data) ? [exportRow(doc.id, data, fieldIds, hits)] : []\n })\n const last = snapshot.docs[snapshot.docs.length - 1]\n return { rows, next: snapshot.docs.length === size && last ? last.id : null }\n },\n\n /*\n * By id, and by from-path: each value is read as the stored form of a\n * path (normalized) and of a pattern (trimmed), and a rule answers for it\n * under its own mode. The plan narrows a row's candidates to the row's\n * mode; this answers every rule the value could mean.\n */\n async lookup(ctx, requests): Promise<TransferLookupResult> {\n const hostId = requireHost(ctx)\n const lookup = new Map<string, string[]>()\n const records = new Map<string, Readonly<Record<string, unknown>>>()\n const file = (fieldId: string, value: string, id: string) => {\n const key = matchLookupKey(fieldId, value)\n const ids = lookup.get(key) ?? []\n if (!ids.includes(id)) ids.push(id)\n lookup.set(key, ids)\n }\n for (const request of requests) {\n if (request.fieldId === TRANSFER_ID_FIELD) {\n const found = await readByIds(hostId, request.values)\n for (const [id, data] of found) {\n file(TRANSFER_ID_FIELD, id, id)\n records.set(id, redirectRuleValues(id, data))\n }\n continue\n }\n if (request.fieldId !== REDIRECT_FIELD.source) continue\n const stored = new Set<string>()\n for (const value of request.values) {\n for (const form of [normalizeRedirectSource(value), value.trim()]) if (form) stored.add(form)\n }\n for (const slice of slices([...stored], IN_QUERY_MAX)) {\n const snapshot = await rulesOf(hostId).where('source', 'in', slice).get()\n for (const doc of snapshot.docs) {\n const data = doc.data() as StoredRule\n if (!isLive(data)) continue\n const kind = typeof data['kind'] === 'string' && data['kind'] ? data['kind'] : 'exact'\n const held = storedSource(kind, text(data['source']))\n for (const value of request.values) {\n if (held !== null && storedSource(kind, value) === held) {\n file(REDIRECT_FIELD.source, value, doc.id)\n records.set(doc.id, redirectRuleValues(doc.id, data))\n }\n }\n }\n }\n }\n return { lookup, records }\n },\n\n async plan(ctx, input: BuildTransferPlanInput): Promise<TransferPlan> {\n const site = await readSite(ctx)\n const documents = await readAllRules(site.hostId)\n const live = documents.filter((entry) => isLive(entry.data))\n const existing = new Map(input.existing)\n for (const { id, data } of live) existing.set(id, redirectRuleValues(id, data))\n\n // The resource's own matching (also the engine's `match` hook, so the\n // Matching and Conflicts steps showed these outcomes): run again over\n // the site as read here, which leaves outcomes it made unchanged.\n const matches = redirectMatchOutcomes(\n input.rows.map((row) => row.values),\n input.matches,\n existing,\n live,\n )\n\n // The row's values as the page would store them, so the review's\n // before → after compares like with like, and a new rule shows the\n // defaults it is created with.\n const rows = input.rows.map((row, at): TransferPlanRow => {\n const match = matches[at] as RowMatchOutcome\n const record = match.kind === 'matched' ? existing.get(match.recordId) : undefined\n const values: Record<string, unknown> = { ...row.values }\n const kind = canonicalRedirectKind(values['kind'])\n if (kind) values['kind'] = kind\n const sourceKind = kind ?? (isBlankTransferValue(values['kind']) ? text(record?.['kind']) || 'exact' : null)\n if (typeof values['source'] === 'string' && sourceKind) {\n values['source'] = storedSource(sourceKind, values['source']) ?? values['source'].trim()\n }\n if (typeof values['destination'] === 'string') {\n values['destination'] = normalizeRedirectDestination(values['destination']) ?? values['destination'].trim()\n }\n if (match.kind === 'new') {\n const defaults: Record<string, unknown> = {\n kind: 'exact',\n statusCode: 302,\n priority: REDIRECT_DEFAULT_PRIORITY,\n enabled: true,\n }\n for (const [fieldId, value] of Object.entries(defaults)) {\n if (isBlankTransferValue(values[fieldId])) values[fieldId] = value\n }\n }\n return { ...row, values }\n })\n\n const plan = buildTransferPlan({ ...input, rows, matches, existing })\n const findings: TransferResourceFinding[] = []\n const writing = plan.rows.filter((row) => row.verdict === 'create' || row.verdict === 'update')\n\n if (site.refusal) {\n for (const row of writing) findings.push({ row: row.index, detail: site.refusal, refuse: true })\n return withTransferResourceFindings(plan, findings)\n }\n\n // What the page refuses about a rule on its own.\n const accepted: Array<{ row: PlannedTransferRow; rule: RuleFields }> = []\n for (const row of writing) {\n const rule = finalRule(row.recordId ? existing.get(row.recordId) : null, row.diff)\n const problem = ruleProblem(rule, site.host)\n if (problem) {\n findings.push({ row: row.index, ...problem, refuse: true })\n continue\n }\n accepted.push({ row, rule })\n }\n\n // What the page refuses against the other rules, row by row in file\n // order over the site as the rows above leave it.\n const liveRows = new Map(live.map(({ id, data }) => [id, ruleRow(id, data)]))\n const touched = new Set(accepted.flatMap(({ row }) => (row.recordId ? [row.recordId] : [])))\n const ruleset: RedirectRuleRow[] = [...liveRows.values()].filter((rule) => !touched.has(rule.$id as string))\n const kept: Array<{ row: PlannedTransferRow; rule: RuleFields; candidate: Required<RedirectRuleRow> }> = []\n const keptByKey = new Map<string, number>()\n const keptByRecord = new Map<string, number>()\n for (const { row, rule } of accepted) {\n const candidate = {\n $id: row.recordId ?? `row:${row.index}`,\n source: rule.source,\n destination: rule.destination,\n kind: rule.kind,\n }\n const key = ruleKey(rule.kind, rule.source) as string\n const repeated = keptByKey.get(key) ?? (row.recordId ? keptByRecord.get(row.recordId) : undefined)\n let detail: string | null = null\n if (repeated !== undefined) detail = `Row ${repeated + 1} already redirects ${rule.source}`\n else if (findDuplicateRedirect(ruleset, candidate)) detail = `A rule for ${rule.source} already exists`\n else if (walkRedirectChain(ruleset, candidate).loop) {\n detail = 'That destination chains back to this rule — a redirect loop'\n }\n if (detail) {\n const fieldId = repeated !== undefined ? REDIRECT_FIELD.source : REDIRECT_FIELD.destination\n findings.push({ row: row.index, detail, fieldId, value: String(rule[fieldId]), refuse: true })\n // The rule it would have changed stays as it is.\n const current = row.recordId ? liveRows.get(row.recordId) : undefined\n if (current) ruleset.push(current)\n continue\n }\n ruleset.push(candidate)\n kept.push({ row, rule, candidate })\n keptByKey.set(key, row.index)\n if (row.recordId) keptByRecord.set(row.recordId, row.index)\n }\n\n // What a person should know about the rules that will be written, read\n // over the site as the whole import leaves it.\n for (const { row, rule, candidate } of kept) {\n const walk = walkRedirectChain(ruleset, candidate)\n const path = [rule.destination, ...walk.hops].join(' → ')\n if (walk.loop || walk.cycle) {\n findings.push({\n row: row.index,\n detail: `Leads into a redirect loop: ${path}`,\n fieldId: REDIRECT_FIELD.destination,\n value: rule.destination,\n })\n } else if (walk.hops.length) {\n findings.push({\n row: row.index,\n detail: `Chains through another rule: ${path}`,\n fieldId: REDIRECT_FIELD.destination,\n value: rule.destination,\n })\n }\n if (isExternalRedirectDestination(rule.destination)) {\n findings.push({\n row: row.index,\n detail: `Sends visitors to ${hostnameOf(rule.destination)}; importing approves it in your name`,\n fieldId: REDIRECT_FIELD.destination,\n value: rule.destination,\n })\n }\n if (redirectSourceIsLivePage((site.host as { screens?: Record<string, unknown> }).screens, rule.source)) {\n findings.push({\n row: row.index,\n detail: `${rule.source} is a published page — the redirect takes precedence`,\n fieldId: REDIRECT_FIELD.source,\n value: rule.source,\n })\n }\n }\n\n // The plan's counter counts every rule document, soft-deleted ones\n // included, as the create route counts them.\n const remaining = Math.max(0, site.limit - documents.length)\n return withCreateLimit(withTransferResourceFindings(plan, findings), remaining, site.limit)\n },\n\n async apply(ctx, chunk, writer: TransferApplyWriter): Promise<TransferApplyResult> {\n const site = await readSite(ctx)\n const actor = ctx.actorUid as string\n const allowed = site.declared.fields\n const results: TransferRowResult[] = []\n const undo: TransferUndoEntry[] = []\n const paths: string[] = []\n\n const fail = (row: PlannedTransferRow, message: string, reason?: TransferRowResult['reason']) => ({\n result: {\n row: row.index,\n outcome: 'failed' as const,\n ...(row.recordId ? { recordId: row.recordId } : {}),\n ...(reason ? { reason } : {}),\n message,\n },\n entry: undefined,\n })\n\n const approvalField = site.declared.externalDestination?.approvedByField ?? REDIRECT_FIELD.approvedBy\n const stampFor = (destination: unknown): string | null =>\n site.declared.externalDestination && isExternalRedirectDestination(String(destination ?? '')) ? actor : null\n\n const create = async (row: PlannedTransferRow) => {\n const rule = finalRule(null, row.diff)\n const problem = ruleProblem(rule, site.host)\n if (problem) return fail(row, problem.detail, 'resourceRule')\n const fields = storedFields(rule, allowed)\n const stamp = stampFor(fields['destination'])\n const ref = rulesOf(site.hostId).doc(importedRedirectId(ctx.jobId, row.index))\n const at = Timestamp.fromMillis(now())\n // Counted and created in one transaction, as the create route does,\n // so two imports (or an import and the page) cannot both take the\n // last slot.\n const outcome = await firestore.runTransaction(async (tx): Promise<{ refusal?: string; existed?: boolean }> => {\n if ((await tx.get(ref)).exists) return { existed: true }\n if (site.declared.quotaKey && Number.isFinite(site.limit)) {\n const used = (await tx.get(rulesOf(site.hostId).count())).data().count\n const quota = checkQuota(site.org, site.declared.quotaKey as Parameters<typeof checkQuota>[1], used)\n if (!quota.allowed) {\n return { refusal: `Your plan includes ${quota.limit} ${site.declared.label} — upgrade in Billing for more` }\n }\n }\n tx.create(ref, {\n ...fields,\n ...(stamp ? { [approvalField]: stamp } : {}),\n createdAt: at,\n updatedAt: at,\n createdBy: actor,\n })\n return {}\n })\n if (outcome.refusal) return fail(row, outcome.refusal, 'planLimit')\n const written: Record<string, unknown> = { ...fields, ...(stamp ? { [approvalField]: stamp } : {}) }\n if (!outcome.existed && deps.logCreated) {\n await deps.logCreated(site.hostId, actor, ref.id, site.declared).catch(() => undefined)\n }\n const path = announcedPath(fields)\n if (path) paths.push(path)\n const result: TransferRowResult = { row: row.index, outcome: 'created', recordId: ref.id }\n const entry: TransferUndoEntry = { row: row.index, recordId: ref.id, action: 'created', written }\n return { result, entry }\n }\n\n const update = async (row: PlannedTransferRow) => {\n const id = row.recordId as string\n const ref = rulesOf(site.hostId).doc(id)\n const snapshot = await ref.get()\n const data = snapshot.exists ? (snapshot.data() as StoredRule) : undefined\n if (!isLive(data)) return fail(row, 'This redirect was deleted after the dry run.', 'matchedRecordMissing')\n const current = redirectRuleValues(id, data)\n const rule = finalRule(current, row.diff)\n const problem = ruleProblem(rule, site.host)\n if (problem) return fail(row, problem.detail, 'resourceRule')\n const fields = storedFields(rule, allowed)\n const stamp = stampFor(fields['destination'])\n const previous: Record<string, unknown> = {}\n const written: Record<string, unknown> = {}\n for (const fieldId of REDIRECT_WRITABLE_FIELDS) {\n if (!(fieldId in fields) || transferValuesEqual(current[fieldId], fields[fieldId])) continue\n previous[fieldId] = current[fieldId] ?? null\n written[fieldId] = fields[fieldId]\n }\n if (!transferValuesEqual(current[approvalField], stamp)) {\n previous[approvalField] = current[approvalField] ?? null\n written[approvalField] = stamp\n }\n if (!Object.keys(written).length) {\n return { result: { row: row.index, outcome: 'unchanged' as const, recordId: id }, entry: undefined }\n }\n // The page's edit: every field the form owns, the stamp set or\n // removed, `updatedAt`, merged so `lastHitAt` and `deletedAt` stay.\n await ref.set(\n { ...fields, [approvalField]: stamp ?? FieldValue.delete(), updatedAt: Timestamp.fromMillis(now()) },\n { merge: true },\n )\n for (const rulePath of [announcedPath(fields), announcedPath({ kind: text(data['kind']), source: text(data['source']) })]) {\n if (rulePath) paths.push(rulePath)\n }\n const result: TransferRowResult = { row: row.index, outcome: 'updated', recordId: id }\n const entry: TransferUndoEntry = { row: row.index, recordId: id, action: 'updated', previous, written }\n return { result, entry }\n }\n\n for (const row of chunk.rows) {\n const before = await writer.alreadyApplied(row.index)\n if (before) {\n results.push(before)\n continue\n }\n if (writer.timeLeftMs() < ROW_RESERVE_MS) break\n const outcome = site.refusal\n ? fail(row, site.refusal, 'resourceRule')\n : row.verdict === 'create'\n ? await create(row)\n : await update(row)\n await writer.markApplied(outcome.result, outcome.entry)\n results.push(outcome.result)\n if (outcome.entry) undo.push(outcome.entry)\n }\n\n if (paths.length) await announce(site.hostId, [...new Set(paths)]).catch(() => undefined)\n return { results, undo }\n },\n\n async revert(ctx, snapshot, decisions?: TransferRevertDecisions): Promise<TransferRevertResult> {\n const site = await readSite(ctx)\n // Undo writes rules too, so it needs the same role; a lapsed plan does\n // not stop it, since a rule the plan no longer covers is not served.\n const role = ctx.actorUid ? ((site.host['memberRoles'] ?? {}) as Record<string, unknown>)[ctx.actorUid] : undefined\n if (!hostRoleCanPublish(role)) {\n throw new Error('Undoing a redirect import needs a publishing role on this site — ask an editor or admin')\n }\n const approvalField = site.declared.externalDestination?.approvedByField ?? REDIRECT_FIELD.approvedBy\n const done: TransferUndoStep[] = []\n const conflicts: TransferUndoStep[] = []\n const paths: string[] = []\n for (const entry of snapshot.entries) {\n const ref = rulesOf(site.hostId).doc(entry.recordId)\n const stored = await ref.get()\n const data = stored.exists ? (stored.data() as StoredRule) : undefined\n const current = isLive(data) ? redirectRuleValues(entry.recordId, data) : null\n const step = planTransferUndo(entry, current)\n if (step.action === 'conflict' && decisions?.[entry.recordId] !== 'revert') {\n if (decisions?.[entry.recordId] === 'keep') {\n done.push({ action: 'nothing', recordId: entry.recordId, why: 'alreadyReverted' })\n } else conflicts.push(step)\n continue\n }\n const before = current ? announcedPath({ kind: String(current['kind']), source: String(current['source']) }) : null\n if (step.action === 'delete' || (step.action === 'conflict' && entry.action === 'created')) {\n await ref.delete()\n if (before) paths.push(before)\n } else if ((step.action === 'restore' || step.action === 'conflict') && current) {\n const restored = { ...current, ...step.values }\n const patch: Record<string, unknown> = {}\n for (const [fieldId, value] of Object.entries(step.values)) {\n patch[fieldId] = value === null || value === undefined ? FieldValue.delete() : value\n }\n // A destination on the site never keeps an approval.\n if (!isExternalRedirectDestination(text(restored['destination']))) patch[approvalField] = FieldValue.delete()\n patch['updatedAt'] = Timestamp.fromMillis(now())\n await ref.set(patch, { merge: true })\n const after = announcedPath({ kind: String(restored['kind']), source: String(restored['source']) })\n for (const path of [before, after]) if (path) paths.push(path)\n }\n done.push(step)\n }\n if (paths.length) await announce(site.hostId, [...new Set(paths)]).catch(() => undefined)\n return { done, conflicts }\n },\n }\n return resource\n}\n"],"names":["createResourceUid","TENANT_APEX","hostRoleCanPublish","hostRoleCanWrite","checkEntitlement","checkQuota","ACKNOWLEDGED_WARNING_CLASSES","TRANSFER_ID_FIELD","TRANSFER_WARNING_CLASSES","buildTransferPlan","isBlankTransferValue","matchLookupKey","planTransferUndo","transferValuesEqual","withTransferResourceFindings","pluginHostResource","dropPluginSiteCache","FieldPath","FieldValue","Timestamp","REDIRECT_DEFAULT_PRIORITY","REDIRECT_STATUS_CODES","findDuplicateRedirect","isExternalRedirectDestination","isSelfRedirect","normalizeRedirectDestination","normalizeRedirectSource","redirectHitKey","redirectSourceIsLivePage","validateRedirectRule","walkRedirectChain","REDIRECTS_ALIAS_DICTIONARIES","REDIRECTS_DEFAULT_POLICY","REDIRECTS_MATCH_KEYS","REDIRECT_FIELD","REDIRECT_HOST_RESOURCE_KIND","REDIRECT_WRITABLE_FIELDS","canonicalRedirectKind","redirectValuesEqual","redirectsTransferCatalog","ROW_RESERVE_MS","PAGE_SIZE_DEFAULT","PAGE_SIZE_MAX","IN_QUERY_MAX","GET_ALL_MAX","HIT_DAYS","DAY_MS","text","value","isoOf","undefined","toMillis","Date","toISOString","Number","isFinite","validStatusCode","includes","redirectRuleValues","id","data","priority","source","kind","destination","statusCode","enabled","approvedBy","createdAt","updatedAt","createdBy","lastHitAt","ruleRow","$id","isLive","Boolean","storedSource","trim","ruleKey","stored","announcedPath","rule","startsWith","finalRule","before","diff","values","change","fieldId","after","withDefaults","String","ownDomains","host","ruleProblem","problem","test","detail","storedFields","allowed","normalized","Object","fromEntries","entries","filter","key","hostnameOf","URL","hostname","requireHost","ctx","hostId","Error","redirectDeclaration","declared","pick","fieldIds","row","slices","items","size","out","at","length","push","slice","withCreateLimit","plan","remaining","limit","creates","held","rows","map","verdict","failed","reason","warnings","summary","create","update","unchanged","skip","fail","total","prior","find","entry","class","raised","count","samples","index","requiresAcknowledgement","flatMap","warning","acknowledgementsRequired","redirectMatchOutcomes","engine","existing","live","byKey","Map","set","get","found","byId","via","record","recordId","rowKind","candidates","recordIds","importedRedirectId","jobId","createRedirectsTransferResource","deps","now","firestore","announce","announcePaths","paths","hostIds","hostRef","collection","doc","rulesOf","readSite","snapshot","org","Promise","all","loadOrg","exists","role","actorUid","roleOk","requiresPublishRole","billing","refusal","entitlement","quotaKey","POSITIVE_INFINITY","readAllRules","docs","readByIds","ids","Set","snapshots","getAll","readHits","today","refs","Array","from","_","totals","day","exportRow","hits","resource","fields","matchKeys","aliases","defaultPolicy","valuesEqual","match","input","records","outcomes","outcome","has","options","deleted","where","Math","max","readPage","cursor","min","floor","pageSize","start","next","query","orderBy","documentId","startAfter","last","lookup","requests","file","request","form","add","site","documents","matches","sourceKind","defaults","findings","writing","refuse","accepted","liveRows","touched","ruleset","kept","keptByKey","keptByRecord","candidate","repeated","loop","current","walk","path","hops","join","cycle","screens","apply","chunk","writer","actor","results","undo","message","result","approvalField","externalDestination","approvedByField","stampFor","stamp","ref","fromMillis","runTransaction","tx","existed","used","quota","label","written","logCreated","catch","action","previous","keys","delete","merge","rulePath","alreadyApplied","timeLeftMs","markApplied","revert","decisions","done","conflicts","step","why","restored","patch"],"mappings":"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"}