payload-plugin-urls 0.9.2 → 0.9.4

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.
package/README.md CHANGED
@@ -81,10 +81,10 @@ which are merged into the generated relationship field. Collection `rootPage` va
81
81
  ### Root-pages global (`overrides`)
82
82
 
83
83
  `overrides` is an optional `Partial<GlobalConfig>` merged into the generated `root-pages` global
84
- after the plugin's defaults. Use it for **`label`**, **`access`**, extra **`hooks`**, **`admin`**, and
85
- other global options. Hook arrays are **concatenated**: the plugin's hooks run first, then yours.
86
- The **`fields`** key in `overrides` is ignored so the plugin keeps control of the relationship
87
- fields; customize those per field with `rootPages.fields[fieldName].overrides` instead.
84
+ after the plugin's defaults. Use it for **`label`**, **`access`**, extra **`hooks`**, **`admin`**,
85
+ and other global options. Hook arrays are **concatenated**: the plugin's hooks run first, then
86
+ yours. The **`fields`** key in `overrides` is ignored so the plugin keeps control of the
87
+ relationship fields; customize those per field with `rootPages.fields[fieldName].overrides` instead.
88
88
 
89
89
  ### Other options
90
90
 
@@ -101,12 +101,19 @@ Categorized collections can choose how their prefix is built:
101
101
 
102
102
  Each configured collection receives a hidden localized `populatedUrl` field and a `beforeChange`
103
103
  hook that recalculates it. The plugin also installs an `update-urls` workflow and queues URL updates
104
- when page, category, or root page relationships change.
104
+ when page, category, or root page relationships change. By default it then calls
105
+ `payload.jobs.runByID` on that job so the workflow runs in the same request (set
106
+ `delayJobsRun: true` to enqueue only and rely on your job runner or cron). Bulk
107
+ writes from the workflow use `req.context.disableRevalidate` (with `disablePopulateUrl` and
108
+ `disableUrlUpdates`) so cache plugins such as **`payload-plugin-cache`** skip per-row invalidation;
109
+ revalidate tags like sitemap yourself after large migrations if needed.
105
110
 
106
111
  ## Exports
107
112
 
108
113
  The package default export is the same function as `payloadPluginUrls`. Import runtime helpers and
109
- TypeScript types from `payload-plugin-urls`.
114
+ TypeScript types from `payload-plugin-urls`. Import the Next.js App Router client `CmsLink` from the
115
+ [`payload-plugin-urls/next`](#nextjs-exports-payload-plugin-urlsnext) submodule (optional peer
116
+ dependency on `next` and React).
110
117
 
111
118
  ### `payloadPluginUrls`
112
119
 
@@ -170,8 +177,8 @@ interface ResolvePopulatedUrlArgs {
170
177
 
171
178
  ### `getDocumentLink`
172
179
 
173
- Builds a site path from a populated relationship. Reads `populatedUrl` from the related document when
174
- present; otherwise derives segments from plugin options and document shape. Throws if
180
+ Builds a site path from a populated relationship. Reads `populatedUrl` from the related document
181
+ when present; otherwise derives segments from plugin options and document shape. Throws if
175
182
  `reference.value` is a plain id string instead of an expanded doc.
176
183
 
177
184
  ```ts
@@ -209,6 +216,63 @@ interface GetDocumentLink {
209
216
  }
210
217
  ```
211
218
 
219
+ ### Next.js exports (`payload-plugin-urls/next`)
220
+
221
+ Client `CmsLink` for Payload-style link fields: resolves internal paths with
222
+ [`getDocumentLink`](#getdocumentlink), highlights the active destination with `usePathname`, handles
223
+ same-document `#hash` targets with configurable scroll offset (`hashScrollYOffset`), resets scroll
224
+ near the viewport top on client navigations (unless opening a new tab or modifier-click), and
225
+ renders **`disabled`** links as plain `span` elements instead of anchors.
226
+
227
+ Requires optional peer dependencies `next`, `react`, and `react-dom`.
228
+
229
+ ```tsx
230
+ "use client"
231
+
232
+ import type { ReactNode } from "react"
233
+ import type { PayloadPluginUrlsOptions, UrlDoc } from "payload-plugin-urls"
234
+ import { CmsLink } from "payload-plugin-urls/next"
235
+
236
+ const urlPluginOptions = {} satisfies PayloadPluginUrlsOptions
237
+
238
+ interface CmsRelationship {
239
+ relationTo: string
240
+ value: UrlDoc | string
241
+ }
242
+
243
+ export function NavLinkDemo(props: {
244
+ locale: string
245
+ siteUrl: string
246
+ type?: string | null
247
+ url?: string | null
248
+ reference?: CmsRelationship | null
249
+ newTab?: boolean | null
250
+ /** Resolve localized labels yourself; pass the result as children. */
251
+ children: ReactNode
252
+ }) {
253
+ const { locale, siteUrl, type, url, reference, newTab, children } = props
254
+
255
+ return (
256
+ <CmsLink
257
+ siteUrl={siteUrl}
258
+ urls={{ locale, options: urlPluginOptions }}
259
+ className="text-primary underline"
260
+ type={type ?? undefined}
261
+ url={url ?? undefined}
262
+ reference={reference && typeof reference.value === "object" ? reference : undefined}
263
+ newTab={newTab ?? undefined}
264
+ >
265
+ {children}
266
+ </CmsLink>
267
+ )
268
+ }
269
+ ```
270
+
271
+ - **`siteUrl`** — Public site base (`https://example.com`-style origin is enough); used with `URL`
272
+ and `usePathname` for same-origin and active-route checks.
273
+ - **`urls`** — `locale`, `options` (your plugin config), optional `baseUrl`, optional
274
+ `urlPrefixStrategy` (same meanings as [`getDocumentLink`](#getdocumentlink)).
275
+
212
276
  ### `getDocumentLinkBySlugs`
213
277
 
214
278
  Joins URL segments with an optional locale or `baseUrl` prefix. Lower-level helper used when you
@@ -270,7 +334,11 @@ the root-pages global changes. Used internally and available for custom workflow
270
334
 
271
335
  ```ts
272
336
  interface GetRootPageChangeSources {
273
- (current: RootPagesDoc, previous: RootPagesDoc | undefined, options: PayloadPluginUrlsOptions): UrlUpdateSource[]
337
+ (
338
+ current: RootPagesDoc,
339
+ previous: RootPagesDoc | undefined,
340
+ options: PayloadPluginUrlsOptions,
341
+ ): UrlUpdateSource[]
274
342
  }
275
343
  ```
276
344
 
@@ -324,6 +392,11 @@ interface PayloadPluginUrlsOptions {
324
392
  label?: LabelFunction | StaticLabel
325
393
  fields?: Record<string, RootPageFieldOptions>
326
394
  }
395
+ /**
396
+ * When `true`, only queue `update-urls`; when omitted or `false`, run the job immediately after
397
+ * queue (default).
398
+ */
399
+ delayJobsRun?: boolean
327
400
  }
328
401
  ```
329
402
 
@@ -0,0 +1,2 @@
1
+ var l=e=>e.replace(/\/$/,"").replace(/^\/?/,"/");function c(e){return(e?.at(-1)?.url??"").replace(/(^\/)|(\/$)/g,"")}function b(e,t){return{...t||{},...p(e)}}function x(e){let{populatedUrl:t,...n}=e;return n}function L(e){if(!(!e||typeof e!="object"||!("id"in e)))return typeof e.id=="string"?e.id:void 0}function C(e){if(typeof e=="string")return e;if(!(!e||typeof e!="object"||!("id"in e)))return typeof e.id=="string"?e.id:void 0}function k(e){return l(`/${e??""}`.replace(/\/+/g,"/"))}function w(e,t){if(!e||typeof e!="object"||!(t in e))return;let n=e;return typeof n[t]=="string"?n[t]:void 0}function D(e){return e._status==="draft"}function T(e){return e&&typeof e=="object"&&!Array.isArray(e)?e:{}}function h(e){let t=new Set;return e.filter(n=>{let o=f(n);return t.has(o)?!1:(t.add(o),!0)})}function f(e){switch(e.type){case"category":case"collection":case"page":return`${e.type}:${e.collection}:${e.id??""}`;case"rootPages":return`rootPages:${JSON.stringify(e.current)}:${JSON.stringify(e.previous)}`}}function p(e){return Object.fromEntries(Object.entries(e).filter(([,t])=>t!==void 0))}function i(e,t){let r={...y(t)??{defaultLocale:"en",locales:["en"]},...e.locales};return{...e,field:{name:"populatedUrl",...e.field},locales:{defaultLocale:r.defaultLocale??r.locales[0]??"en",locales:r.locales.length?r.locales:[r.defaultLocale??"en"]},rootPages:{slug:"root-pages",...e.rootPages,fields:e.rootPages?.fields??{indexPage:{isHomepage:!0,relationTo:"pages"}}}}}function u(e,t){return e.collections[t]}function P(e){return Object.entries(e.collections)}function S(e,t){return P(e).filter(([,n])=>n.category?.collection===t).map(([n])=>n)}function R(e){let t=i(e);return Object.keys(t.rootPages.fields)}function $(e){let t=i(e).rootPages.fields;return(Object.entries(t).find(([,o])=>o.isHomepage)??Object.entries(t).find(([o])=>o==="indexPage"))?.[0]??Object.keys(t)[0]??"indexPage"}function z(e,t){return i(e).rootPages.fields[t]}function y(e){let t=e?.localization||void 0,n=t?.locales?.map(o=>typeof o=="string"?o:o.code).filter(o=>!!o);if(n?.length)return{defaultLocale:t?.defaultLocale??n[0]??"en",locales:n}}function I(e,{baseUrl:t,locale:n,options:o,urlPrefixStrategy:r}){if(typeof e.value=="string")throw new Error("Reference value is a string");if(e.value.populatedUrl)return l(e.value.populatedUrl);let a=i(o),s=u(a,e.relationTo),g=s?.routeCollection??e.relationTo,d=U(s,e.value,r??s?.prefixStrategy);return m(d,{baseUrl:t,collection:g,locale:n,options:a})}function m(e,{baseUrl:t,locale:n,options:o}){let r=i(o),s=[...(t||(n===r.locales?.defaultLocale?"":n)).split("/"),...e].filter(Boolean);return l(`/${s.join("/")}`)}function E(e,t,n){let o=i(n).locales?.defaultLocale;return t===o?l(e):l(`/${t}${e}`)}function U(e,t,n){return e?.category?n==="rootPage"?[t.slug??""]:[O(t),t.slug??""]:e?.breadcrumbs?[c(t.breadcrumbs)||t.slug||""]:[t.slug??""]}function O(e){let t=e.categories;if(!Array.isArray(t)||t.length===0)return"";let o=t[0];if(!o||typeof o!="object"||typeof o=="string")return"";let r=o;return c(r.breadcrumbs)||(r.slug??"").replace(/(^\/)|(\/$)/g,"")}export{l as a,c as b,b as c,x as d,L as e,C as f,k as g,w as h,D as i,T as j,h as k,i as l,u as m,P as n,S as o,R as p,$ as q,z as r,I as s,m as t,E as u};
2
+ //# sourceMappingURL=chunk-OKNQKSNQ.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/utils.ts","../src/options.ts","../src/link.ts"],"sourcesContent":["import type { Breadcrumb, UrlDoc, UrlUpdateSource } from \"./types\"\n\nconst withoutTrailingSlash = (path: string) => path.replace(/\\/$/, \"\").replace(/^\\/?/, \"/\")\n\nfunction getBreadcrumbsUrl(breadcrumbs: Breadcrumb[] | null | undefined) {\n const lastItem = breadcrumbs?.at(-1)\n const url = lastItem?.url ?? \"\"\n return url.replace(/(^\\/)|(\\/$)/g, \"\")\n}\n\nfunction mergeDoc<T extends object>(data: Partial<T>, originalDoc?: Partial<T>) {\n return {\n ...(originalDoc || {}),\n ...withoutUndefinedValues(data),\n } as T\n}\n\nfunction withoutPopulatedUrl<T extends object>(doc: T) {\n const { populatedUrl: _populatedUrl, ...rest } = doc as T & { populatedUrl?: unknown }\n return rest\n}\n\nfunction getDocumentId(doc: unknown) {\n if (!doc || typeof doc !== \"object\" || !(\"id\" in doc)) {\n return undefined\n }\n\n return typeof doc.id === \"string\" ? doc.id : undefined\n}\n\nfunction getRelationId(value: unknown) {\n if (typeof value === \"string\") {\n return value\n }\n\n if (!value || typeof value !== \"object\" || !(\"id\" in value)) {\n return undefined\n }\n\n return typeof value.id === \"string\" ? value.id : undefined\n}\n\nfunction normalizePath(path: string | undefined) {\n return withoutTrailingSlash(`/${path ?? \"\"}`.replace(/\\/+/g, \"/\"))\n}\n\nfunction getStringValue(value: unknown, key: \"populatedUrl\" | \"slug\") {\n if (!value || typeof value !== \"object\" || !(key in value)) {\n return undefined\n }\n\n const record = value as Record<\"populatedUrl\" | \"slug\", unknown>\n return typeof record[key] === \"string\" ? record[key] : undefined\n}\n\nfunction isDraftDoc(doc: UrlDoc) {\n return doc._status === \"draft\"\n}\n\nfunction getRecord(value: unknown) {\n return value && typeof value === \"object\" && !Array.isArray(value)\n ? (value as Record<string, unknown>)\n : {}\n}\n\nfunction dedupeSources<T extends UrlUpdateSource>(sources: T[]) {\n const seen = new Set<string>()\n\n return sources.filter((source) => {\n const key = sourceKey(source)\n if (seen.has(key)) {\n return false\n }\n seen.add(key)\n return true\n })\n}\n\nfunction sourceKey(source: UrlUpdateSource) {\n switch (source.type) {\n case \"category\":\n case \"collection\":\n case \"page\":\n return `${source.type}:${source.collection}:${source.id ?? \"\"}`\n case \"rootPages\":\n return `rootPages:${JSON.stringify(source.current)}:${JSON.stringify(source.previous)}`\n }\n}\n\nfunction withoutUndefinedValues<T extends object>(value: Partial<T>) {\n return Object.fromEntries(\n Object.entries(value).filter(([, entry]) => entry !== undefined),\n ) as Partial<T>\n}\n\nexport {\n getBreadcrumbsUrl,\n getRecord,\n dedupeSources,\n isDraftDoc,\n getStringValue,\n normalizePath,\n getRelationId,\n getDocumentId,\n withoutPopulatedUrl,\n mergeDoc,\n withoutTrailingSlash,\n}\n","import type {\n PayloadPluginConfig,\n PayloadPluginUrlsOptions,\n RootPageFieldOptions,\n UrlCollectionOptions,\n} from \"./types\"\n\nexport type NormalizedPayloadPluginUrlsOptions = PayloadPluginUrlsOptions & {\n collections: Record<string, UrlCollectionOptions>\n locales: {\n defaultLocale: string\n locales: string[]\n }\n rootPages: {\n slug: string\n label?: unknown\n fields: Record<string, RootPageFieldOptions>\n }\n}\n\nexport function normalizeOptions(\n options: PayloadPluginUrlsOptions,\n config?: PayloadPluginConfig,\n): NormalizedPayloadPluginUrlsOptions {\n const configLocales = getConfigLocales(config)\n const fallbackLocales = configLocales ?? { defaultLocale: \"en\", locales: [\"en\"] }\n const locales = {\n ...fallbackLocales,\n ...options.locales,\n }\n\n return {\n ...options,\n field: {\n name: \"populatedUrl\",\n ...options.field,\n },\n locales: {\n defaultLocale: locales.defaultLocale ?? locales.locales[0] ?? \"en\",\n locales: locales.locales.length ? locales.locales : [locales.defaultLocale ?? \"en\"],\n },\n rootPages: {\n slug: \"root-pages\",\n ...options.rootPages,\n fields: options.rootPages?.fields ?? {\n indexPage: {\n isHomepage: true,\n relationTo: \"pages\",\n },\n },\n },\n }\n}\n\nexport function getCollectionOptions(options: PayloadPluginUrlsOptions, collection: string) {\n return options.collections[collection]\n}\n\nexport function getCollectionEntries(options: PayloadPluginUrlsOptions) {\n return Object.entries(options.collections)\n}\n\nexport function getCollectionsForCategory(\n options: PayloadPluginUrlsOptions,\n categoryCollection: string,\n) {\n return getCollectionEntries(options)\n .filter(\n ([, collectionOptions]) => collectionOptions.category?.collection === categoryCollection,\n )\n .map(([collection]) => collection)\n}\n\nexport function getRootPageFieldNames(options: PayloadPluginUrlsOptions) {\n const normalizedOptions = normalizeOptions(options)\n return Object.keys(normalizedOptions.rootPages.fields)\n}\n\nexport function getHomepageRootPageField(options: PayloadPluginUrlsOptions) {\n const fields = normalizeOptions(options).rootPages.fields\n const homepageEntry =\n Object.entries(fields).find(([, field]) => field.isHomepage) ??\n Object.entries(fields).find(([fieldName]) => fieldName === \"indexPage\")\n\n return homepageEntry?.[0] ?? Object.keys(fields)[0] ?? \"indexPage\"\n}\n\nexport function getRootPageFieldOptions(options: PayloadPluginUrlsOptions, fieldName: string) {\n return normalizeOptions(options).rootPages.fields[fieldName]\n}\n\nfunction getConfigLocales(config: PayloadPluginConfig | undefined) {\n const localization = config?.localization || undefined\n const locales = localization?.locales\n ?.map((locale) => (typeof locale === \"string\" ? locale : locale.code))\n .filter((locale): locale is string => Boolean(locale))\n\n if (!locales?.length) {\n return undefined\n }\n\n return {\n defaultLocale: localization?.defaultLocale ?? locales[0] ?? \"en\",\n locales,\n }\n}\n","import { getCollectionOptions, normalizeOptions } from \"./options\"\nimport { getBreadcrumbsUrl, withoutTrailingSlash } from \"./utils\"\n\nimport type {\n GetDocumentLinkArgs,\n GetDocumentLinkContext,\n Locale,\n PayloadPluginUrlsOptions,\n UrlCollectionOptions,\n UrlDoc,\n UrlPrefixStrategy,\n} from \"./types\"\n\nexport function getDocumentLink(\n reference: GetDocumentLinkArgs,\n { baseUrl, locale, options, urlPrefixStrategy }: GetDocumentLinkContext,\n) {\n if (typeof reference.value === \"string\") {\n throw new Error(\"Reference value is a string\")\n }\n\n if (reference.value.populatedUrl) {\n return withoutTrailingSlash(reference.value.populatedUrl)\n }\n\n const normalizedOptions = normalizeOptions(options)\n const collectionOptions = getCollectionOptions(normalizedOptions, reference.relationTo)\n const routeCollection = collectionOptions?.routeCollection ?? reference.relationTo\n const slugs = getSlugsForCollection(\n collectionOptions,\n reference.value,\n urlPrefixStrategy ?? collectionOptions?.prefixStrategy,\n )\n\n return getDocumentLinkBySlugs(slugs, {\n baseUrl,\n collection: routeCollection,\n locale,\n options: normalizedOptions,\n })\n}\n\nexport function getDocumentLinkBySlugs(\n slugs: string[],\n {\n baseUrl,\n locale,\n options,\n }: {\n baseUrl?: string\n collection: string\n locale: Locale\n options: PayloadPluginUrlsOptions\n },\n) {\n const normalizedOptions = normalizeOptions(options)\n const prefix = baseUrl || (locale === normalizedOptions.locales?.defaultLocale ? \"\" : locale)\n const segments = [...prefix.split(\"/\"), ...slugs].filter(Boolean)\n return withoutTrailingSlash(`/${segments.join(\"/\")}`)\n}\n\nexport function withLocalePrefix(path: string, locale: Locale, options: PayloadPluginUrlsOptions) {\n const defaultLocale = normalizeOptions(options).locales?.defaultLocale\n if (locale === defaultLocale) {\n return withoutTrailingSlash(path)\n }\n return withoutTrailingSlash(`/${locale}${path}`)\n}\n\nfunction getSlugsForCollection(\n collectionOptions: UrlCollectionOptions | undefined,\n doc: UrlDoc,\n strategy?: UrlPrefixStrategy,\n) {\n if (collectionOptions?.category) {\n return strategy === \"rootPage\"\n ? [doc.slug ?? \"\"]\n : [firstRelatedCategoryPath(doc), doc.slug ?? \"\"]\n }\n\n if (collectionOptions?.breadcrumbs) {\n return [getBreadcrumbsUrl(doc.breadcrumbs) || doc.slug || \"\"]\n }\n\n return [doc.slug ?? \"\"]\n}\n\nfunction firstRelatedCategoryPath(doc: UrlDoc) {\n const categories = doc.categories\n if (!Array.isArray(categories) || categories.length === 0) {\n return \"\"\n }\n\n const categoryItems = categories as unknown[]\n const first = categoryItems[0]\n if (!first || typeof first !== \"object\" || typeof first === \"string\") {\n return \"\"\n }\n\n const categoryDoc = first as UrlDoc\n return (\n getBreadcrumbsUrl(categoryDoc.breadcrumbs) ||\n (categoryDoc.slug ?? \"\").replace(/(^\\/)|(\\/$)/g, \"\")\n )\n}\n"],"mappings":"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","names":["withoutTrailingSlash","path","getBreadcrumbsUrl","breadcrumbs","mergeDoc","data","originalDoc","withoutUndefinedValues","withoutPopulatedUrl","doc","_populatedUrl","rest","getDocumentId","getRelationId","value","normalizePath","getStringValue","key","record","isDraftDoc","getRecord","dedupeSources","sources","seen","source","sourceKey","entry","normalizeOptions","options","config","locales","getConfigLocales","getCollectionOptions","collection","getCollectionEntries","getCollectionsForCategory","categoryCollection","collectionOptions","getRootPageFieldNames","normalizedOptions","getHomepageRootPageField","fields","field","fieldName","getRootPageFieldOptions","localization","locale","getDocumentLink","reference","baseUrl","locale","options","urlPrefixStrategy","withoutTrailingSlash","normalizedOptions","normalizeOptions","collectionOptions","getCollectionOptions","routeCollection","slugs","getSlugsForCollection","getDocumentLinkBySlugs","segments","withLocalePrefix","path","defaultLocale","doc","strategy","firstRelatedCategoryPath","getBreadcrumbsUrl","categories","first","categoryDoc"]}
@@ -1 +1 @@
1
- {"version":3,"file":"hooks.d.ts","sourceRoot":"","sources":["../src/hooks.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,wBAAwB,EAAwB,MAAM,SAAS,CAAA;AAC7E,OAAO,KAAK,EACV,yBAAyB,EACzB,0BAA0B,EAC1B,qBAAqB,EACtB,MAAM,SAAS,CAAA;AAEhB,wBAAgB,qBAAqB,CACnC,OAAO,EAAE,wBAAwB,GAChC,0BAA0B,CAqC5B;AAED,wBAAgB,6BAA6B,CAC3C,OAAO,EAAE,wBAAwB,GAChC,yBAAyB,CA0C3B;AAED,wBAAgB,4BAA4B,CAC1C,OAAO,EAAE,wBAAwB,GAChC,qBAAqB,CAuBvB"}
1
+ {"version":3,"file":"hooks.d.ts","sourceRoot":"","sources":["../src/hooks.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,wBAAwB,EAAyC,MAAM,SAAS,CAAA;AAC9F,OAAO,KAAK,EACV,yBAAyB,EACzB,0BAA0B,EAC1B,qBAAqB,EAGtB,MAAM,SAAS,CAAA;AAuChB,wBAAgB,qBAAqB,CACnC,OAAO,EAAE,wBAAwB,GAChC,0BAA0B,CAqC5B;AAED,wBAAgB,6BAA6B,CAC3C,OAAO,EAAE,wBAAwB,GAChC,yBAAyB,CA6C3B;AAED,wBAAgB,4BAA4B,CAC1C,OAAO,EAAE,wBAAwB,GAChC,qBAAqB,CAyBvB"}
package/dist/index.cjs CHANGED
@@ -1,2 +1,2 @@
1
- "use strict";var H=Object.defineProperty;var oo=Object.getOwnPropertyDescriptor;var eo=Object.getOwnPropertyNames;var to=Object.prototype.hasOwnProperty;var no=(o,e)=>{for(var t in e)H(o,t,{get:e[t],enumerable:!0})},ro=(o,e,t,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let r of eo(e))!to.call(o,r)&&r!==t&&H(o,r,{get:()=>e[r],enumerable:!(n=oo(e,r))||n.enumerable});return o};var lo=o=>ro(H({},"__esModule",{value:!0}),o);var Oo={};no(Oo,{default:()=>$,getBreadcrumbsUrl:()=>g,getDocumentLink:()=>U,getDocumentLinkBySlugs:()=>G,getRootPageChangeSources:()=>z,hasUrlPathChanged:()=>F,payloadPluginUrls:()=>$,populatedUrlField:()=>L,resolvePopulatedUrl:()=>y,withLocalePrefix:()=>k,withoutTrailingSlash:()=>d});module.exports=lo(Oo);var d=o=>o.replace(/\/$/,"").replace(/^\/?/,"/");function g(o){return(o?.at(-1)?.url??"").replace(/(^\/)|(\/$)/g,"")}function B(o,e){return{...e||{},...ao(o)}}function T(o){let{populatedUrl:e,...t}=o;return t}function N(o){if(!(!o||typeof o!="object"||!("id"in o)))return typeof o.id=="string"?o.id:void 0}function O(o){if(typeof o=="string")return o;if(!(!o||typeof o!="object"||!("id"in o)))return typeof o.id=="string"?o.id:void 0}function h(o){return d(`/${o??""}`.replace(/\/+/g,"/"))}function C(o,e){if(!o||typeof o!="object"||!(e in o))return;let t=o;return typeof t[e]=="string"?t[e]:void 0}function w(o){return o._status==="draft"}function _(o){return o&&typeof o=="object"&&!Array.isArray(o)?o:{}}function E(o){let e=new Set;return o.filter(t=>{let n=io(t);return e.has(n)?!1:(e.add(n),!0)})}function io(o){switch(o.type){case"category":case"collection":case"page":return`${o.type}:${o.collection}:${o.id??""}`;case"rootPages":return`rootPages:${JSON.stringify(o.current)}:${JSON.stringify(o.previous)}`}}function ao(o){return Object.fromEntries(Object.entries(o).filter(([,e])=>e!==void 0))}function L(o={collections:{}}){return{name:o.field?.name??"populatedUrl",type:"text",label:!1,localized:!0,...o.field?.overrides??{},admin:{hidden:!0,..._(o.field?.overrides?.admin)}}}function c(o,e){let r={...so(e)??{defaultLocale:"en",locales:["en"]},...o.locales};return{...o,field:{name:"populatedUrl",...o.field},locales:{defaultLocale:r.defaultLocale??r.locales[0]??"en",locales:r.locales.length?r.locales:[r.defaultLocale??"en"]},rootPages:{slug:"root-pages",...o.rootPages,fields:o.rootPages?.fields??{indexPage:{isHomepage:!0,relationTo:"pages"}}}}}function p(o,e){return o.collections[e]}function j(o){return Object.entries(o.collections)}function R(o,e){return j(o).filter(([,t])=>t.category?.collection===e).map(([t])=>t)}function D(o){let e=c(o);return Object.keys(e.rootPages.fields)}function x(o){let e=c(o).rootPages.fields;return(Object.entries(e).find(([,n])=>n.isHomepage)??Object.entries(e).find(([n])=>n==="indexPage"))?.[0]??Object.keys(e)[0]??"indexPage"}function m(o,e){return c(o).rootPages.fields[e]}function so(o){let e=o?.localization||void 0,t=e?.locales?.map(n=>typeof n=="string"?n:n.code).filter(n=>!!n);if(t?.length)return{defaultLocale:e?.defaultLocale??t[0]??"en",locales:t}}function U(o,{baseUrl:e,locale:t,options:n,urlPrefixStrategy:r}){if(typeof o.value=="string")throw new Error("Reference value is a string");if(o.value.populatedUrl)return d(o.value.populatedUrl);let l=c(n),a=p(l,o.relationTo),i=a?.routeCollection??o.relationTo,s=co(a,o.value,r??a?.prefixStrategy);return G(s,{baseUrl:e,collection:i,locale:t,options:l})}function G(o,{baseUrl:e,locale:t,options:n}){let r=c(n),a=[...(e||(t===r.locales?.defaultLocale?"":t)).split("/"),...o].filter(Boolean);return d(`/${a.join("/")}`)}function k(o,e,t){let n=c(t).locales?.defaultLocale;return e===n?d(o):d(`/${e}${o}`)}function co(o,e,t){return o?.category?t==="rootPage"?[e.slug??""]:[uo(e),e.slug??""]:o?.breadcrumbs?[g(e.breadcrumbs)||e.slug||""]:[e.slug??""]}function uo(o){let e=o.categories;if(!Array.isArray(e)||e.length===0)return"";let n=e[0];if(!n||typeof n!="object"||typeof n=="string")return"";let r=n;return g(r.breadcrumbs)||(r.slug??"").replace(/(^\/)|(\/$)/g,"")}async function y({collection:o,data:e,locale:t,options:n,originalDoc:r,payload:l,rootPages:a}){let i=c(n),s=p(i,o);if(!s)return;let u=B(e,r),f=x(i);if(s.breadcrumbs&&!s.rootPage){let P=await W({field:f,locale:t,payload:l,rootPages:a}),Z=N(P);if(u.id&&Z===u.id)return k("/",t,i);let S=h(g(u.breadcrumbs)),A=h(g(P?.breadcrumbs)),q=A&&S.startsWith(`${A}/`)?h(S.slice(A.length)):S;return k(q||`/${u.slug??""}`,t,i)}let b=await go({collectionOptions:s,locale:t,options:i,payload:l,rootPages:a});if(s.category){let P=await po({categories:u[s.category.field??"categories"],collection:s.category.collection,locale:t,payload:l});return U({relationTo:o,value:{...T(u),[s.category.field??"categories"]:P,categories:P}},{baseUrl:b,locale:t,options:i})}return U({relationTo:o,value:T(u)},{baseUrl:b,locale:t,options:i})}async function go({collectionOptions:o,locale:e,options:t,payload:n,rootPages:r}){if(!o.rootPage)return;let l=o.rootPage,i=m(t,l)?.relationTo??"pages",s=await W({collection:i,field:l,locale:e,payload:n,rootPages:r});if(s)return typeof s.populatedUrl=="string"&&s.populatedUrl?V(s.populatedUrl,e,t):i!=="pages"?V(U({relationTo:i,value:s},{locale:e,options:t}),e,t):y({collection:i,data:{},locale:e,options:t,originalDoc:s,payload:n,rootPages:r})}function V(o,e,t){let n=c(t);return e===n.locales.defaultLocale||o===`/${e}`||o.startsWith(`/${e}/`)?o:k(o,e,n)}async function W({collection:o="pages",field:e,locale:t,payload:n,rootPages:r}){let l=r[e];return l?typeof l!="string"?l:await n?.findByID?.({collection:o,id:l,depth:0,locale:t,select:{id:!0,slug:!0,populatedUrl:!0,breadcrumbs:!0}}):void 0}async function po({categories:o,collection:e,locale:t,payload:n}){return Array.isArray(o)?Promise.all(o.map(r=>typeof r!="string"?Promise.resolve(r):n?.findByID?.({collection:e,id:r,depth:2,locale:t})??Promise.resolve(r))):[]}function M(o){return async({job:e,req:t})=>{let n=c(o),r=e.input?.sources??[];for(let l of n.locales?.locales??[]){let a=await t.payload.findGlobal?.({slug:n.rootPages?.slug??"root-pages",depth:2,locale:l});if(a)for(let i of fo(r,n))switch(i.type){case"category":await v({collection:i.collection,locale:l,options:n,payload:t.payload,rootPages:a});for(let s of R(n,i.collection))await v({collection:s,locale:l,options:n,payload:t.payload,rootPages:a});break;case"collection":case"page":await v({collection:i.collection,locale:l,options:n,payload:t.payload,rootPages:a});break;case"rootPages":break}}}}function F(o,e){let t=C(o,"populatedUrl"),n=C(e,"populatedUrl");return t&&n?t!==n:C(o,"slug")!==C(e,"slug")}function z(o,e,t){let n=c(t),r=[],l=x(n),a=m(n,l)?.relationTo??"pages",i=O(o[l]),s=O(e?.[l]);i!==s&&(i&&r.push({type:"page",collection:a,id:i}),s&&r.push({type:"page",collection:a,id:s}));for(let[u,f]of j(n)){if(!f.rootPage)continue;let b=O(o[f.rootPage]),P=O(e?.[f.rootPage]);b!==P&&r.push({type:"collection",collection:u})}return E(r)}function I(o,e){let t={};for(let n of D(e))t[n]=o?.[n];return t}function fo(o,e){return o.flatMap(t=>t.type!=="rootPages"?[t]:z(t.current,t.previous,e))}async function v({collection:o,locale:e,options:t,payload:n,rootPages:r}){let l=1;for(;;){let a=await n.find?.({collection:o,depth:2,draft:!1,limit:100,locale:e,overrideAccess:!0,page:l,pagination:!0});if(!a)return;for(let i of a.docs){let s=i;if(!s.id||w(s))continue;let u=await y({collection:o,data:{},locale:e,options:t,originalDoc:s,payload:n,rootPages:r});!u||s.populatedUrl===u||await n.update?.({collection:o,id:s.id,locale:e,overrideAccess:!0,data:{[t.field?.name??"populatedUrl"]:u},context:{disablePopulateUrl:!0,disableUrlUpdates:!0}})}if(!a.nextPage)return;l=a.nextPage}}function J(o){return async({collection:e,context:t,data:n={},originalDoc:r,req:l})=>{let a=l.locale;if(!a||a==="all"||t?.disablePopulateUrl||l.context?.disablePopulateUrl)return n;let i=await l.payload.findGlobal?.({slug:c(o).rootPages?.slug??"root-pages",depth:2,locale:a});if(!i)return n;let s=await y({collection:e?.slug??"",data:n,locale:a,options:o,originalDoc:r,payload:l.payload,rootPages:i});return s&&(n[o.field?.name??"populatedUrl"]=s),n}}function K(o){return async({collection:e,doc:t,previousDoc:n,req:r})=>{let l=t,a=n;if(r.context?.disableUrlUpdates||!l||w(l)||!F(l,a))return l;let i=p(o,e?.slug??"");if(!i)return l;let s=e?.slug??"",f=R(o,s).length>0?{type:"category",collection:s,id:l.id}:{type:i.breadcrumbs&&!i.rootPage?"page":"collection",collection:s,id:l.id};return await r.payload.jobs?.queue?.({workflow:"update-urls",input:{sources:[f]}}),l}}function Q(o){return async({doc:e,previousDoc:t,req:n})=>{let r=e,l=t;return n.context?.disableUrlUpdates||await n.payload.jobs?.queue?.({workflow:"update-urls",input:{sources:[{type:"rootPages",current:I(r,o),previous:I(l,o)}]}}),r}}var $=o=>o?e=>{let t=c(o,e),n=(e.collections??[]).map(r=>Po(r,t));return{...e,collections:n,globals:[...e.globals??[],yo(t)],jobs:{...e.jobs??{},workflows:[...e.jobs?.workflows??[],{slug:"update-urls",handler:M(t)}]}}}:e=>e;function Po(o,e){if(!p(e,o.slug))return o;let n=e.field?.name??"populatedUrl",r=o.fields.some(a=>"name"in a&&a.name===n)?o.fields:[...o.fields,L(e)],l=o.hooks??{};return{...o,defaultPopulate:{...o.defaultPopulate??{},[n]:!0},fields:r,hooks:{...l,beforeChange:[...l.beforeChange??[],J(e)],afterChange:[...l.afterChange??[],K(e)]}}}function yo(o){let e=c(o).rootPages,t={slug:e?.slug??"root-pages",label:e?.label??"Root pages",fields:D(o).map(r=>mo(r,o)),hooks:{afterChange:[Q(o)]}},n=o.overrides;return n?ko(t,n):t}function mo(o,e){let t=m(e,o),n=t?.overrides??{},{name:r,type:l,hasMany:a,relationTo:i,...s}=n;return{name:o,type:"relationship",relationTo:t?.relationTo??"pages",hasMany:!1,admin:{width:"50%"},...s}}function X(o){if(!Array.isArray(o))return[];let e=[];for(let t of o)e.push(t);return e}function Uo(o,e){if(!e)return o;if(!o)return e;let t=o,n=e,r={...t};for(let l of Object.keys(n)){let a=t[l],i=n[l];Array.isArray(a)||Array.isArray(i)?r[l]=[...X(a),...X(i)]:i!==void 0&&(r[l]=i)}return r}function Y(o,e){return e?o?{...o,...e}:e:o}function ko(o,e){let{hooks:t,access:n,admin:r,fields:l,...a}=e,i={...o,...a};return n&&(i.access=Y(o.access,n)),r&&(i.admin=Y(o.admin,r)),(t||o.hooks)&&(i.hooks=Uo(o.hooks,t)),i}0&&(module.exports={getBreadcrumbsUrl,getDocumentLink,getDocumentLinkBySlugs,getRootPageChangeSources,hasUrlPathChanged,payloadPluginUrls,populatedUrlField,resolvePopulatedUrl,withLocalePrefix,withoutTrailingSlash});
1
+ "use strict";var z=Object.defineProperty;var to=Object.getOwnPropertyDescriptor;var no=Object.getOwnPropertyNames;var ro=Object.prototype.hasOwnProperty;var io=(o,e)=>{for(var t in e)z(o,t,{get:e[t],enumerable:!0})},lo=(o,e,t,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let r of no(e))!ro.call(o,r)&&r!==t&&z(o,r,{get:()=>e[r],enumerable:!(n=to(e,r))||n.enumerable});return o};var ao=o=>lo(z({},"__esModule",{value:!0}),o);var wo={};io(wo,{default:()=>$,getBreadcrumbsUrl:()=>y,getDocumentLink:()=>O,getDocumentLinkBySlugs:()=>G,getRootPageChangeSources:()=>v,hasUrlPathChanged:()=>h,payloadPluginUrls:()=>$,populatedUrlField:()=>S,resolvePopulatedUrl:()=>m,withLocalePrefix:()=>b,withoutTrailingSlash:()=>P});module.exports=ao(wo);var P=o=>o.replace(/\/$/,"").replace(/^\/?/,"/");function y(o){return(o?.at(-1)?.url??"").replace(/(^\/)|(\/$)/g,"")}function N(o,e){return{...e||{},...co(o)}}function I(o){let{populatedUrl:e,...t}=o;return t}function E(o){if(!(!o||typeof o!="object"||!("id"in o)))return typeof o.id=="string"?o.id:void 0}function U(o){if(typeof o=="string")return o;if(!(!o||typeof o!="object"||!("id"in o)))return typeof o.id=="string"?o.id:void 0}function L(o){return P(`/${o??""}`.replace(/\/+/g,"/"))}function w(o,e){if(!o||typeof o!="object"||!(e in o))return;let t=o;return typeof t[e]=="string"?t[e]:void 0}function x(o){return o._status==="draft"}function W(o){return o&&typeof o=="object"&&!Array.isArray(o)?o:{}}function _(o){let e=new Set;return o.filter(t=>{let n=so(t);return e.has(n)?!1:(e.add(n),!0)})}function so(o){switch(o.type){case"category":case"collection":case"page":return`${o.type}:${o.collection}:${o.id??""}`;case"rootPages":return`rootPages:${JSON.stringify(o.current)}:${JSON.stringify(o.previous)}`}}function co(o){return Object.fromEntries(Object.entries(o).filter(([,e])=>e!==void 0))}function S(o={collections:{}}){return{name:o.field?.name??"populatedUrl",type:"text",label:!1,localized:!0,...o.field?.overrides??{},admin:{hidden:!0,...W(o.field?.overrides?.admin)}}}function c(o,e){let r={...uo(e)??{defaultLocale:"en",locales:["en"]},...o.locales};return{...o,field:{name:"populatedUrl",...o.field},locales:{defaultLocale:r.defaultLocale??r.locales[0]??"en",locales:r.locales.length?r.locales:[r.defaultLocale??"en"]},rootPages:{slug:"root-pages",...o.rootPages,fields:o.rootPages?.fields??{indexPage:{isHomepage:!0,relationTo:"pages"}}}}}function p(o,e){return o.collections[e]}function F(o){return Object.entries(o.collections)}function R(o,e){return F(o).filter(([,t])=>t.category?.collection===e).map(([t])=>t)}function A(o){let e=c(o);return Object.keys(e.rootPages.fields)}function H(o){let e=c(o).rootPages.fields;return(Object.entries(e).find(([,n])=>n.isHomepage)??Object.entries(e).find(([n])=>n==="indexPage"))?.[0]??Object.keys(e)[0]??"indexPage"}function k(o,e){return c(o).rootPages.fields[e]}function uo(o){let e=o?.localization||void 0,t=e?.locales?.map(n=>typeof n=="string"?n:n.code).filter(n=>!!n);if(t?.length)return{defaultLocale:e?.defaultLocale??t[0]??"en",locales:t}}function O(o,{baseUrl:e,locale:t,options:n,urlPrefixStrategy:r}){if(typeof o.value=="string")throw new Error("Reference value is a string");if(o.value.populatedUrl)return P(o.value.populatedUrl);let i=c(n),l=p(i,o.relationTo),a=l?.routeCollection??o.relationTo,s=go(l,o.value,r??l?.prefixStrategy);return G(s,{baseUrl:e,collection:a,locale:t,options:i})}function G(o,{baseUrl:e,locale:t,options:n}){let r=c(n),l=[...(e||(t===r.locales?.defaultLocale?"":t)).split("/"),...o].filter(Boolean);return P(`/${l.join("/")}`)}function b(o,e,t){let n=c(t).locales?.defaultLocale;return e===n?P(o):P(`/${e}${o}`)}function go(o,e,t){return o?.category?t==="rootPage"?[e.slug??""]:[po(e),e.slug??""]:o?.breadcrumbs?[y(e.breadcrumbs)||e.slug||""]:[e.slug??""]}function po(o){let e=o.categories;if(!Array.isArray(e)||e.length===0)return"";let n=e[0];if(!n||typeof n!="object"||typeof n=="string")return"";let r=n;return y(r.breadcrumbs)||(r.slug??"").replace(/(^\/)|(\/$)/g,"")}async function m({collection:o,data:e,locale:t,options:n,originalDoc:r,payload:i,rootPages:l}){let a=c(n),s=p(a,o);if(!s)return;let u=N(e,r),d=H(a);if(s.breadcrumbs&&!s.rootPage){let f=await J({field:d,locale:t,payload:i,rootPages:l}),T=E(f);if(u.id&&T===u.id)return b("/",t,a);let C=L(y(u.breadcrumbs)),j=L(y(f?.breadcrumbs)),eo=j&&C.startsWith(`${j}/`)?L(C.slice(j.length)):C;return b(eo||`/${u.slug??""}`,t,a)}let g=await fo({collectionOptions:s,locale:t,options:a,payload:i,rootPages:l});if(s.category){let f=await Po({categories:u[s.category.field??"categories"],collection:s.category.collection,locale:t,payload:i});return O({relationTo:o,value:{...I(u),[s.category.field??"categories"]:f,categories:f}},{baseUrl:g,locale:t,options:a})}return O({relationTo:o,value:I(u)},{baseUrl:g,locale:t,options:a})}async function fo({collectionOptions:o,locale:e,options:t,payload:n,rootPages:r}){if(!o.rootPage)return;let i=o.rootPage,a=k(t,i)?.relationTo??"pages",s=await J({collection:a,field:i,locale:e,payload:n,rootPages:r});if(s)return typeof s.populatedUrl=="string"&&s.populatedUrl?V(s.populatedUrl,e,t):a!=="pages"?V(O({relationTo:a,value:s},{locale:e,options:t}),e,t):m({collection:a,data:{},locale:e,options:t,originalDoc:s,payload:n,rootPages:r})}function V(o,e,t){let n=c(t);return e===n.locales.defaultLocale||o===`/${e}`||o.startsWith(`/${e}/`)?o:b(o,e,n)}async function J({collection:o="pages",field:e,locale:t,payload:n,rootPages:r}){let i=r[e];return i?typeof i!="string"?i:await n?.findByID?.({collection:o,id:i,depth:0,locale:t,select:{id:!0,slug:!0,populatedUrl:!0,breadcrumbs:!0}}):void 0}async function Po({categories:o,collection:e,locale:t,payload:n}){return Array.isArray(o)?Promise.all(o.map(r=>typeof r!="string"?Promise.resolve(r):n?.findByID?.({collection:e,id:r,depth:2,locale:t})??Promise.resolve(r))):[]}function M(o){return async({job:e,req:t})=>{let n=c(o),r=e.input?.sources??[];for(let i of n.locales?.locales??[]){let l=await t.payload.findGlobal?.({slug:n.rootPages?.slug??"root-pages",depth:2,locale:i});if(l)for(let a of yo(r,n))switch(a.type){case"category":await D({collection:a.collection,locale:i,options:n,payload:t.payload,rootPages:l});for(let s of R(n,a.collection))await D({collection:s,locale:i,options:n,payload:t.payload,rootPages:l});break;case"collection":await D({collection:a.collection,locale:i,options:n,payload:t.payload,rootPages:l});break;case"page":{await D({collection:a.collection,locale:i,options:n,payload:t.payload,rootPages:l});let s=a.id==null?"":String(a.id);if(!s)break;let u=Uo(mo(s,l,n),n),d=new Set;for(let g of u)await K({collection:g,locale:i,options:n,payload:t.payload,rootPages:l,visited:d});break}case"rootPages":break}}}}function h(o,e){let t=w(o,"populatedUrl"),n=w(e,"populatedUrl");return t&&n?t!==n:w(o,"slug")!==w(e,"slug")}function v(o,e,t){let n=c(t),r=[],i=H(n),l=k(n,i)?.relationTo??"pages",a=U(o[i]),s=U(e?.[i]);a!==s?(a&&r.push({type:"page",collection:l,id:a}),s&&r.push({type:"page",collection:l,id:s})):a&&h(o[i],e?.[i])&&r.push({type:"page",collection:l,id:a});for(let[u,d]of F(n)){if(!d.rootPage)continue;let g=U(o[d.rootPage]),f=U(e?.[d.rootPage]),T=g!==f,C=!!g&&g===f&&h(o[d.rootPage],e?.[d.rootPage]);(T||C)&&r.push({type:"collection",collection:u})}return _(r)}function B(o,e){let t={};for(let n of A(e))t[n]=o?.[n];return t}function yo(o,e){return o.flatMap(t=>t.type!=="rootPages"?[t]:v(t.current,t.previous,e))}function mo(o,e,t){let n=[];for(let[r,i]of F(t)){let l=i.rootPage;l&&U(e[l])===o&&n.push(r)}return n}function Uo(o,e){let t=new Set(o);return o.filter(n=>{let r=p(e,n)?.category?.collection;return!r||!t.has(r)})}async function K({collection:o,locale:e,options:t,payload:n,rootPages:r,visited:i}){if(!i.has(o)){i.add(o),await D({collection:o,locale:e,options:t,payload:n,rootPages:r});for(let l of R(t,o))await K({collection:l,locale:e,options:t,payload:n,rootPages:r,visited:i})}}async function D({collection:o,locale:e,options:t,payload:n,rootPages:r}){let i=1;for(;;){let l=await n.find?.({collection:o,depth:2,draft:!1,limit:100,locale:e,overrideAccess:!0,page:i,pagination:!0});if(!l)return;for(let a of l.docs){let s=a;if(!s.id||x(s))continue;let u=await m({collection:o,data:{},locale:e,options:t,originalDoc:s,payload:n,rootPages:r});!u||s.populatedUrl===u||await n.update?.({collection:o,id:s.id,locale:e,overrideAccess:!0,data:{[t.field?.name??"populatedUrl"]:u},context:{disablePopulateUrl:!0,disableUrlUpdates:!0,disableRevalidate:!0}})}if(!l.nextPage)return;i=l.nextPage}}async function Q({input:o,payload:e,req:t,runImmediately:n}){let r=e.jobs;if(!r?.queue)return;let i=await r.queue({workflow:"update-urls",input:o,req:t});if(!n||typeof r.runByID!="function")return;let l=i&&typeof i=="object"&&"id"in i&&i.id!=null?i.id:void 0;l!==void 0&&await r.runByID({id:l,req:t})}function X(o){return async({collection:e,context:t,data:n={},originalDoc:r,req:i})=>{let l=i.locale;if(!l||l==="all"||t?.disablePopulateUrl||i.context?.disablePopulateUrl)return n;let a=await i.payload.findGlobal?.({slug:c(o).rootPages?.slug??"root-pages",depth:2,locale:l});if(!a)return n;let s=await m({collection:e?.slug??"",data:n,locale:l,options:o,originalDoc:r,payload:i.payload,rootPages:a});return s&&(n[o.field?.name??"populatedUrl"]=s),n}}function Y(o){return async({collection:e,doc:t,previousDoc:n,req:r})=>{let i=t,l=n;if(r.context?.disableUrlUpdates||!i||x(i)||!h(i,l))return i;let a=p(o,e?.slug??"");if(!a)return i;let s=e?.slug??"",u=R(o,s).length>0,d=i.id==null?void 0:String(i.id),g=u?{type:"category",collection:s,id:d}:{type:a.breadcrumbs&&!a.rootPage?"page":"collection",collection:s,id:d};return await Q({input:{sources:[g]},payload:r.payload,req:r,runImmediately:c(o).delayJobsRun!==!0}),i}}function Z(o){return async({doc:e,previousDoc:t,req:n})=>{let r=e,i=t;return n.context?.disableUrlUpdates||await Q({input:{sources:[{type:"rootPages",current:B(r,o),previous:B(i,o)}]},payload:n.payload,req:n,runImmediately:c(o).delayJobsRun!==!0}),r}}var $=o=>o?e=>{let t=c(o,e),n=(e.collections??[]).map(r=>ko(r,t));return{...e,collections:n,globals:[...e.globals??[],Oo(t)],jobs:{...e.jobs??{},workflows:[...e.jobs?.workflows??[],{slug:"update-urls",handler:M(t)}]}}}:e=>e;function ko(o,e){if(!p(e,o.slug))return o;let n=e.field?.name??"populatedUrl",r=o.fields.some(l=>"name"in l&&l.name===n)?o.fields:[...o.fields,S(e)],i=o.hooks??{};return{...o,defaultPopulate:{...o.defaultPopulate??{},[n]:!0},fields:r,hooks:{...i,beforeChange:[...i.beforeChange??[],X(e)],afterChange:[...i.afterChange??[],Y(e)]}}}function Oo(o){let e=c(o).rootPages,t={slug:e?.slug??"root-pages",label:e?.label??"Root pages",fields:A(o).map(r=>bo(r,o)),hooks:{afterChange:[Z(o)]}},n=o.overrides;return n?Co(t,n):t}function bo(o,e){let t=k(e,o),n=t?.overrides??{},{name:r,type:i,hasMany:l,relationTo:a,...s}=n;return{name:o,type:"relationship",relationTo:t?.relationTo??"pages",hasMany:!1,admin:{width:"50%"},...s}}function q(o){if(!Array.isArray(o))return[];let e=[];for(let t of o)e.push(t);return e}function ho(o,e){if(!e)return o;if(!o)return e;let t=o,n=e,r={...t};for(let i of Object.keys(n)){let l=t[i],a=n[i];Array.isArray(l)||Array.isArray(a)?r[i]=[...q(l),...q(a)]:a!==void 0&&(r[i]=a)}return r}function oo(o,e){return e?o?{...o,...e}:e:o}function Co(o,e){let{hooks:t,access:n,admin:r,fields:i,...l}=e,a={...o,...l};return n&&(a.access=oo(o.access,n)),r&&(a.admin=oo(o.admin,r)),(t||o.hooks)&&(a.hooks=ho(o.hooks,t)),a}0&&(module.exports={getBreadcrumbsUrl,getDocumentLink,getDocumentLinkBySlugs,getRootPageChangeSources,hasUrlPathChanged,payloadPluginUrls,populatedUrlField,resolvePopulatedUrl,withLocalePrefix,withoutTrailingSlash});
2
2
  //# sourceMappingURL=index.cjs.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts","../src/utils.ts","../src/field.ts","../src/options.ts","../src/link.ts","../src/resolver.ts","../src/update-urls.ts","../src/hooks.ts","../src/plugin.ts"],"sourcesContent":["export { populatedUrlField } from \"./field\"\nexport { getDocumentLink, getDocumentLinkBySlugs, withLocalePrefix } from \"./link\"\nexport { payloadPluginUrls } from \"./plugin\"\nexport { resolvePopulatedUrl } from \"./resolver\"\nexport { getRootPageChangeSources, hasUrlPathChanged } from \"./update-urls\"\nexport { getBreadcrumbsUrl, withoutTrailingSlash } from \"./utils\"\n\nexport type {\n Breadcrumb,\n CollectionConfigLike,\n FieldLike,\n GetDocumentLinkArgs,\n GetDocumentLinkContext,\n GlobalConfigLike,\n Hook,\n HookArgs,\n Locale,\n PayloadLike,\n PayloadPlugin,\n PayloadPluginConfig,\n PayloadPluginUrlsOptions,\n ResolvePopulatedUrlArgs,\n RootPageFieldOptions,\n RootPagesDoc,\n UrlCollectionOptions,\n UrlDoc,\n UrlPrefixStrategy,\n UrlUpdateSource,\n WorkflowLike,\n} from \"./types\"\n\nexport { payloadPluginUrls as default } from \"./plugin\"\n","import type { Breadcrumb, UrlDoc, UrlUpdateSource } from \"./types\"\n\nconst withoutTrailingSlash = (path: string) => path.replace(/\\/$/, \"\").replace(/^\\/?/, \"/\")\n\nfunction getBreadcrumbsUrl(breadcrumbs: Breadcrumb[] | null | undefined) {\n const lastItem = breadcrumbs?.at(-1)\n const url = lastItem?.url ?? \"\"\n return url.replace(/(^\\/)|(\\/$)/g, \"\")\n}\n\nfunction mergeDoc<T extends object>(data: Partial<T>, originalDoc?: Partial<T>) {\n return {\n ...(originalDoc || {}),\n ...withoutUndefinedValues(data),\n } as T\n}\n\nfunction withoutPopulatedUrl<T extends object>(doc: T) {\n const { populatedUrl: _populatedUrl, ...rest } = doc as T & { populatedUrl?: unknown }\n return rest\n}\n\nfunction getDocumentId(doc: unknown) {\n if (!doc || typeof doc !== \"object\" || !(\"id\" in doc)) {\n return undefined\n }\n\n return typeof doc.id === \"string\" ? doc.id : undefined\n}\n\nfunction getRelationId(value: unknown) {\n if (typeof value === \"string\") {\n return value\n }\n\n if (!value || typeof value !== \"object\" || !(\"id\" in value)) {\n return undefined\n }\n\n return typeof value.id === \"string\" ? value.id : undefined\n}\n\nfunction normalizePath(path: string | undefined) {\n return withoutTrailingSlash(`/${path ?? \"\"}`.replace(/\\/+/g, \"/\"))\n}\n\nfunction getStringValue(value: unknown, key: \"populatedUrl\" | \"slug\") {\n if (!value || typeof value !== \"object\" || !(key in value)) {\n return undefined\n }\n\n const record = value as Record<\"populatedUrl\" | \"slug\", unknown>\n return typeof record[key] === \"string\" ? record[key] : undefined\n}\n\nfunction isDraftDoc(doc: UrlDoc) {\n return doc._status === \"draft\"\n}\n\nfunction getRecord(value: unknown) {\n return value && typeof value === \"object\" && !Array.isArray(value)\n ? (value as Record<string, unknown>)\n : {}\n}\n\nfunction dedupeSources<T extends UrlUpdateSource>(sources: T[]) {\n const seen = new Set<string>()\n\n return sources.filter((source) => {\n const key = sourceKey(source)\n if (seen.has(key)) {\n return false\n }\n seen.add(key)\n return true\n })\n}\n\nfunction sourceKey(source: UrlUpdateSource) {\n switch (source.type) {\n case \"category\":\n case \"collection\":\n case \"page\":\n return `${source.type}:${source.collection}:${source.id ?? \"\"}`\n case \"rootPages\":\n return `rootPages:${JSON.stringify(source.current)}:${JSON.stringify(source.previous)}`\n }\n}\n\nfunction withoutUndefinedValues<T extends object>(value: Partial<T>) {\n return Object.fromEntries(\n Object.entries(value).filter(([, entry]) => entry !== undefined),\n ) as Partial<T>\n}\n\nexport {\n getBreadcrumbsUrl,\n getRecord,\n dedupeSources,\n isDraftDoc,\n getStringValue,\n normalizePath,\n getRelationId,\n getDocumentId,\n withoutPopulatedUrl,\n mergeDoc,\n withoutTrailingSlash,\n}\n","import { getRecord } from \"./utils\"\n\nimport type { PayloadPluginUrlsOptions } from \"./types\"\nimport type { Field } from \"payload\"\n\nexport function populatedUrlField(options: PayloadPluginUrlsOptions = { collections: {} }): Field {\n const fieldName = options.field?.name ?? \"populatedUrl\"\n\n return {\n name: fieldName,\n type: \"text\",\n label: false,\n localized: true,\n ...(options.field?.overrides ?? {}),\n admin: {\n hidden: true,\n ...getRecord(options.field?.overrides?.admin),\n },\n } as Field\n}\n","import type {\n PayloadPluginConfig,\n PayloadPluginUrlsOptions,\n RootPageFieldOptions,\n UrlCollectionOptions,\n} from \"./types\"\n\nexport type NormalizedPayloadPluginUrlsOptions = PayloadPluginUrlsOptions & {\n collections: Record<string, UrlCollectionOptions>\n locales: {\n defaultLocale: string\n locales: string[]\n }\n rootPages: {\n slug: string\n label?: unknown\n fields: Record<string, RootPageFieldOptions>\n }\n}\n\nexport function normalizeOptions(\n options: PayloadPluginUrlsOptions,\n config?: PayloadPluginConfig,\n): NormalizedPayloadPluginUrlsOptions {\n const configLocales = getConfigLocales(config)\n const fallbackLocales = configLocales ?? { defaultLocale: \"en\", locales: [\"en\"] }\n const locales = {\n ...fallbackLocales,\n ...options.locales,\n }\n\n return {\n ...options,\n field: {\n name: \"populatedUrl\",\n ...options.field,\n },\n locales: {\n defaultLocale: locales.defaultLocale ?? locales.locales[0] ?? \"en\",\n locales: locales.locales.length ? locales.locales : [locales.defaultLocale ?? \"en\"],\n },\n rootPages: {\n slug: \"root-pages\",\n ...options.rootPages,\n fields: options.rootPages?.fields ?? {\n indexPage: {\n isHomepage: true,\n relationTo: \"pages\",\n },\n },\n },\n }\n}\n\nexport function getCollectionOptions(options: PayloadPluginUrlsOptions, collection: string) {\n return options.collections[collection]\n}\n\nexport function getCollectionEntries(options: PayloadPluginUrlsOptions) {\n return Object.entries(options.collections)\n}\n\nexport function getCollectionsForCategory(\n options: PayloadPluginUrlsOptions,\n categoryCollection: string,\n) {\n return getCollectionEntries(options)\n .filter(\n ([, collectionOptions]) => collectionOptions.category?.collection === categoryCollection,\n )\n .map(([collection]) => collection)\n}\n\nexport function getRootPageFieldNames(options: PayloadPluginUrlsOptions) {\n const normalizedOptions = normalizeOptions(options)\n return Object.keys(normalizedOptions.rootPages.fields)\n}\n\nexport function getHomepageRootPageField(options: PayloadPluginUrlsOptions) {\n const fields = normalizeOptions(options).rootPages.fields\n const homepageEntry =\n Object.entries(fields).find(([, field]) => field.isHomepage) ??\n Object.entries(fields).find(([fieldName]) => fieldName === \"indexPage\")\n\n return homepageEntry?.[0] ?? Object.keys(fields)[0] ?? \"indexPage\"\n}\n\nexport function getRootPageFieldOptions(options: PayloadPluginUrlsOptions, fieldName: string) {\n return normalizeOptions(options).rootPages.fields[fieldName]\n}\n\nfunction getConfigLocales(config: PayloadPluginConfig | undefined) {\n const localization = config?.localization || undefined\n const locales = localization?.locales\n ?.map((locale) => (typeof locale === \"string\" ? locale : locale.code))\n .filter((locale): locale is string => Boolean(locale))\n\n if (!locales?.length) {\n return undefined\n }\n\n return {\n defaultLocale: localization?.defaultLocale ?? locales[0] ?? \"en\",\n locales,\n }\n}\n","import { getCollectionOptions, normalizeOptions } from \"./options\"\nimport { getBreadcrumbsUrl, withoutTrailingSlash } from \"./utils\"\n\nimport type {\n GetDocumentLinkArgs,\n GetDocumentLinkContext,\n Locale,\n PayloadPluginUrlsOptions,\n UrlCollectionOptions,\n UrlDoc,\n UrlPrefixStrategy,\n} from \"./types\"\n\nexport function getDocumentLink(\n reference: GetDocumentLinkArgs,\n { baseUrl, locale, options, urlPrefixStrategy }: GetDocumentLinkContext,\n) {\n if (typeof reference.value === \"string\") {\n throw new Error(\"Reference value is a string\")\n }\n\n if (reference.value.populatedUrl) {\n return withoutTrailingSlash(reference.value.populatedUrl)\n }\n\n const normalizedOptions = normalizeOptions(options)\n const collectionOptions = getCollectionOptions(normalizedOptions, reference.relationTo)\n const routeCollection = collectionOptions?.routeCollection ?? reference.relationTo\n const slugs = getSlugsForCollection(\n collectionOptions,\n reference.value,\n urlPrefixStrategy ?? collectionOptions?.prefixStrategy,\n )\n\n return getDocumentLinkBySlugs(slugs, {\n baseUrl,\n collection: routeCollection,\n locale,\n options: normalizedOptions,\n })\n}\n\nexport function getDocumentLinkBySlugs(\n slugs: string[],\n {\n baseUrl,\n locale,\n options,\n }: {\n baseUrl?: string\n collection: string\n locale: Locale\n options: PayloadPluginUrlsOptions\n },\n) {\n const normalizedOptions = normalizeOptions(options)\n const prefix = baseUrl || (locale === normalizedOptions.locales?.defaultLocale ? \"\" : locale)\n const segments = [...prefix.split(\"/\"), ...slugs].filter(Boolean)\n return withoutTrailingSlash(`/${segments.join(\"/\")}`)\n}\n\nexport function withLocalePrefix(path: string, locale: Locale, options: PayloadPluginUrlsOptions) {\n const defaultLocale = normalizeOptions(options).locales?.defaultLocale\n if (locale === defaultLocale) {\n return withoutTrailingSlash(path)\n }\n return withoutTrailingSlash(`/${locale}${path}`)\n}\n\nfunction getSlugsForCollection(\n collectionOptions: UrlCollectionOptions | undefined,\n doc: UrlDoc,\n strategy?: UrlPrefixStrategy,\n) {\n if (collectionOptions?.category) {\n return strategy === \"rootPage\"\n ? [doc.slug ?? \"\"]\n : [firstRelatedCategoryPath(doc), doc.slug ?? \"\"]\n }\n\n if (collectionOptions?.breadcrumbs) {\n return [getBreadcrumbsUrl(doc.breadcrumbs) || doc.slug || \"\"]\n }\n\n return [doc.slug ?? \"\"]\n}\n\nfunction firstRelatedCategoryPath(doc: UrlDoc) {\n const categories = doc.categories\n if (!Array.isArray(categories) || categories.length === 0) {\n return \"\"\n }\n\n const categoryItems = categories as unknown[]\n const first = categoryItems[0]\n if (!first || typeof first !== \"object\" || typeof first === \"string\") {\n return \"\"\n }\n\n const categoryDoc = first as UrlDoc\n return (\n getBreadcrumbsUrl(categoryDoc.breadcrumbs) ||\n (categoryDoc.slug ?? \"\").replace(/(^\\/)|(\\/$)/g, \"\")\n )\n}\n","import { getDocumentLink, withLocalePrefix } from \"./link\"\nimport {\n getCollectionOptions,\n getHomepageRootPageField,\n getRootPageFieldOptions,\n normalizeOptions,\n} from \"./options\"\nimport {\n getBreadcrumbsUrl,\n getDocumentId,\n mergeDoc,\n normalizePath,\n withoutPopulatedUrl,\n} from \"./utils\"\n\nimport type {\n Locale,\n PayloadLike,\n PayloadPluginUrlsOptions,\n ResolvePopulatedUrlArgs,\n RootPagesDoc,\n UrlCollectionOptions,\n UrlDoc,\n} from \"./types\"\n\nexport async function resolvePopulatedUrl({\n collection,\n data,\n locale,\n options,\n originalDoc,\n payload,\n rootPages,\n}: ResolvePopulatedUrlArgs): Promise<string | undefined> {\n const normalizedOptions = normalizeOptions(options)\n const collectionOptions = getCollectionOptions(normalizedOptions, collection)\n if (!collectionOptions) {\n return undefined\n }\n\n const doc = mergeDoc(data, originalDoc)\n const homepageField = getHomepageRootPageField(normalizedOptions)\n\n if (collectionOptions.breadcrumbs && !collectionOptions.rootPage) {\n const homepage = await getRootPageDoc({\n field: homepageField,\n locale,\n payload,\n rootPages,\n })\n const homepageId = getDocumentId(homepage)\n\n if (doc.id && homepageId === doc.id) {\n return withLocalePrefix(\"/\", locale, normalizedOptions)\n }\n\n const breadcrumbsPath = normalizePath(getBreadcrumbsUrl(doc.breadcrumbs))\n const homepagePath = normalizePath(getBreadcrumbsUrl(homepage?.breadcrumbs))\n const pagePath =\n homepagePath && breadcrumbsPath.startsWith(`${homepagePath}/`)\n ? normalizePath(breadcrumbsPath.slice(homepagePath.length))\n : breadcrumbsPath\n\n return withLocalePrefix(pagePath || `/${doc.slug ?? \"\"}`, locale, normalizedOptions)\n }\n\n const rootPageUrl: string | undefined = await getRootPageUrl({\n collectionOptions,\n locale,\n options: normalizedOptions,\n payload,\n rootPages,\n })\n\n if (collectionOptions.category) {\n const categories = await resolveCategories({\n categories: doc[collectionOptions.category.field ?? \"categories\"],\n collection: collectionOptions.category.collection,\n locale,\n payload,\n })\n\n return getDocumentLink(\n {\n relationTo: collection,\n value: {\n ...withoutPopulatedUrl(doc),\n [collectionOptions.category.field ?? \"categories\"]: categories,\n categories,\n },\n },\n {\n baseUrl: rootPageUrl,\n locale,\n options: normalizedOptions,\n },\n )\n }\n\n return getDocumentLink(\n {\n relationTo: collection,\n value: withoutPopulatedUrl(doc),\n },\n {\n baseUrl: rootPageUrl,\n locale,\n options: normalizedOptions,\n },\n )\n}\n\nasync function getRootPageUrl({\n collectionOptions,\n locale,\n options,\n payload,\n rootPages,\n}: {\n collectionOptions: UrlCollectionOptions\n locale: Locale\n options: PayloadPluginUrlsOptions\n payload?: PayloadLike\n rootPages: RootPagesDoc\n}): Promise<string | undefined> {\n if (!collectionOptions.rootPage) {\n return undefined\n }\n\n const rootPageField = collectionOptions.rootPage\n const rootPageFieldOptions = getRootPageFieldOptions(options, rootPageField)\n const relationTo = rootPageFieldOptions?.relationTo ?? \"pages\"\n const rootPage = await getRootPageDoc({\n collection: relationTo,\n field: rootPageField,\n locale,\n payload,\n rootPages,\n })\n\n if (!rootPage) {\n return undefined\n }\n\n if (typeof rootPage.populatedUrl === \"string\" && rootPage.populatedUrl) {\n return withLocalePrefixIfNeeded(rootPage.populatedUrl, locale, options)\n }\n\n if (relationTo !== \"pages\") {\n return withLocalePrefixIfNeeded(\n getDocumentLink(\n {\n relationTo,\n value: rootPage,\n },\n {\n locale,\n options,\n },\n ),\n locale,\n options,\n )\n }\n\n return resolvePopulatedUrl({\n collection: relationTo,\n data: {},\n locale,\n options,\n originalDoc: rootPage,\n payload,\n rootPages,\n })\n}\n\nfunction withLocalePrefixIfNeeded(path: string, locale: Locale, options: PayloadPluginUrlsOptions) {\n const normalizedOptions = normalizeOptions(options)\n if (\n locale === normalizedOptions.locales.defaultLocale ||\n path === `/${locale}` ||\n path.startsWith(`/${locale}/`)\n ) {\n return path\n }\n\n return withLocalePrefix(path, locale, normalizedOptions)\n}\n\nasync function getRootPageDoc({\n collection = \"pages\",\n field,\n locale,\n payload,\n rootPages,\n}: {\n collection?: string\n field: string\n locale: Locale\n payload?: PayloadLike\n rootPages: RootPagesDoc\n}) {\n const page = rootPages[field]\n\n if (!page) {\n return undefined\n }\n\n if (typeof page !== \"string\") {\n return page\n }\n\n const found = await payload?.findByID?.({\n collection,\n id: page,\n depth: 0,\n locale,\n select: {\n id: true,\n slug: true,\n populatedUrl: true,\n breadcrumbs: true,\n },\n })\n return found as UrlDoc | undefined\n}\n\nasync function resolveCategories({\n categories,\n collection,\n locale,\n payload,\n}: {\n categories: unknown\n collection: string\n locale: Locale\n payload?: PayloadLike\n}) {\n if (!Array.isArray(categories)) {\n return []\n }\n\n return Promise.all(\n categories.map((category) => {\n if (typeof category !== \"string\") {\n return Promise.resolve(category)\n }\n\n return (\n payload?.findByID?.({\n collection,\n id: category,\n depth: 2,\n locale,\n }) ?? Promise.resolve(category)\n )\n }),\n )\n}\n","import {\n getCollectionEntries,\n getCollectionsForCategory,\n getHomepageRootPageField,\n getRootPageFieldNames,\n getRootPageFieldOptions,\n normalizeOptions,\n} from \"./options\"\nimport { resolvePopulatedUrl } from \"./resolver\"\nimport { dedupeSources, getRelationId, getStringValue, isDraftDoc } from \"./utils\"\n\nimport type {\n Locale,\n PayloadLike,\n PayloadPluginUrlsOptions,\n RootPagesDoc,\n UrlDoc,\n UrlUpdateSource,\n} from \"./types\"\n\nexport function createUpdateUrlsHandler(options: PayloadPluginUrlsOptions) {\n return async ({\n job,\n req,\n }: {\n job: {\n input?: {\n sources?: UrlUpdateSource[] | null\n }\n }\n req: {\n payload: PayloadLike\n }\n }) => {\n const normalizedOptions = normalizeOptions(options)\n const sources = job.input?.sources ?? []\n\n for (const locale of normalizedOptions.locales?.locales ?? []) {\n const rootPages = await req.payload.findGlobal?.({\n slug: normalizedOptions.rootPages?.slug ?? \"root-pages\",\n depth: 2,\n locale,\n })\n if (!rootPages) {\n continue\n }\n\n for (const source of expandSources(sources, normalizedOptions)) {\n switch (source.type) {\n case \"category\":\n await updateCollectionDocuments({\n collection: source.collection,\n locale,\n options: normalizedOptions,\n payload: req.payload,\n rootPages,\n })\n for (const collection of getCollectionsForCategory(\n normalizedOptions,\n source.collection,\n )) {\n await updateCollectionDocuments({\n collection,\n locale,\n options: normalizedOptions,\n payload: req.payload,\n rootPages,\n })\n }\n break\n case \"collection\":\n case \"page\":\n await updateCollectionDocuments({\n collection: source.collection,\n locale,\n options: normalizedOptions,\n payload: req.payload,\n rootPages,\n })\n break\n case \"rootPages\":\n break\n }\n }\n }\n }\n}\n\nexport function hasUrlPathChanged(doc: unknown, previousDoc: unknown) {\n const docUrl = getStringValue(doc, \"populatedUrl\")\n const previousUrl = getStringValue(previousDoc, \"populatedUrl\")\n\n if (docUrl && previousUrl) {\n return docUrl !== previousUrl\n }\n\n return getStringValue(doc, \"slug\") !== getStringValue(previousDoc, \"slug\")\n}\n\nexport function getRootPageChangeSources(\n current: RootPagesDoc,\n previous: RootPagesDoc | undefined,\n options: PayloadPluginUrlsOptions,\n): UrlUpdateSource[] {\n const normalizedOptions = normalizeOptions(options)\n const sources: UrlUpdateSource[] = []\n const indexPageField = getHomepageRootPageField(normalizedOptions)\n const indexPageCollection =\n getRootPageFieldOptions(normalizedOptions, indexPageField)?.relationTo ?? \"pages\"\n const currentIndexPageId = getRelationId(current[indexPageField])\n const previousIndexPageId = getRelationId(previous?.[indexPageField])\n\n if (currentIndexPageId !== previousIndexPageId) {\n if (currentIndexPageId) {\n sources.push({ type: \"page\", collection: indexPageCollection, id: currentIndexPageId })\n }\n if (previousIndexPageId) {\n sources.push({ type: \"page\", collection: indexPageCollection, id: previousIndexPageId })\n }\n }\n\n for (const [collection, collectionOptions] of getCollectionEntries(normalizedOptions)) {\n if (!collectionOptions.rootPage) {\n continue\n }\n\n const currentRootPageId = getRelationId(current[collectionOptions.rootPage])\n const previousRootPageId = getRelationId(previous?.[collectionOptions.rootPage])\n if (currentRootPageId !== previousRootPageId) {\n sources.push({ type: \"collection\", collection })\n }\n }\n\n return dedupeSources(sources)\n}\n\nexport function getRootPageSnapshot(\n rootPages: UrlDoc | undefined,\n options: PayloadPluginUrlsOptions,\n) {\n const snapshot: RootPagesDoc = {}\n\n for (const fieldName of getRootPageFieldNames(options)) {\n snapshot[fieldName] = rootPages?.[fieldName] as RootPagesDoc[string]\n }\n\n return snapshot\n}\n\nfunction expandSources(sources: UrlUpdateSource[], options: PayloadPluginUrlsOptions) {\n return sources.flatMap((source) => {\n if (source.type !== \"rootPages\") {\n return [source]\n }\n\n return getRootPageChangeSources(source.current, source.previous, options)\n })\n}\n\nasync function updateCollectionDocuments({\n collection,\n locale,\n options,\n payload,\n rootPages,\n}: {\n collection: string\n locale: Locale\n options: PayloadPluginUrlsOptions\n payload: PayloadLike\n rootPages: RootPagesDoc\n}) {\n let page = 1\n\n for (;;) {\n const result = await payload.find?.({\n collection,\n depth: 2,\n draft: false,\n limit: 100,\n locale,\n overrideAccess: true,\n page,\n pagination: true,\n })\n\n if (!result) {\n return\n }\n\n for (const doc of result.docs) {\n const urlDoc = doc as UrlDoc\n if (!urlDoc.id || isDraftDoc(urlDoc)) {\n continue\n }\n\n const populatedUrlValue = await resolvePopulatedUrl({\n collection,\n data: {},\n locale,\n options,\n originalDoc: urlDoc,\n payload,\n rootPages,\n })\n\n if (!populatedUrlValue || urlDoc.populatedUrl === populatedUrlValue) {\n continue\n }\n\n await payload.update?.({\n collection,\n id: urlDoc.id,\n locale,\n overrideAccess: true,\n data: {\n [options.field?.name ?? \"populatedUrl\"]: populatedUrlValue,\n },\n context: {\n disablePopulateUrl: true,\n disableUrlUpdates: true,\n },\n })\n }\n\n if (!result.nextPage) {\n return\n }\n\n page = result.nextPage\n }\n}\n","import { getCollectionOptions, getCollectionsForCategory, normalizeOptions } from \"./options\"\nimport { resolvePopulatedUrl } from \"./resolver\"\nimport { getRootPageSnapshot, hasUrlPathChanged } from \"./update-urls\"\nimport { isDraftDoc } from \"./utils\"\n\nimport type { PayloadPluginUrlsOptions, RootPagesDoc, UrlDoc } from \"./types\"\nimport type {\n CollectionAfterChangeHook,\n CollectionBeforeChangeHook,\n GlobalAfterChangeHook,\n} from \"payload\"\n\nexport function createPopulateUrlHook(\n options: PayloadPluginUrlsOptions,\n): CollectionBeforeChangeHook {\n return async ({ collection, context, data = {}, originalDoc, req }) => {\n const locale = req.locale\n if (\n !locale ||\n locale === \"all\" ||\n context?.disablePopulateUrl ||\n req.context?.disablePopulateUrl\n ) {\n return data\n }\n\n const rootPages = await req.payload.findGlobal?.({\n slug: normalizeOptions(options).rootPages?.slug ?? \"root-pages\",\n depth: 2,\n locale,\n })\n if (!rootPages) {\n return data\n }\n\n const populatedUrlValue = await resolvePopulatedUrl({\n collection: collection?.slug ?? \"\",\n data: data as UrlDoc,\n locale,\n options,\n originalDoc: originalDoc as UrlDoc | undefined,\n payload: req.payload,\n rootPages: rootPages as RootPagesDoc,\n })\n\n if (populatedUrlValue) {\n data[options.field?.name ?? \"populatedUrl\"] = populatedUrlValue\n }\n\n return data\n }\n}\n\nexport function createCollectionUrlUpdateHook(\n options: PayloadPluginUrlsOptions,\n): CollectionAfterChangeHook {\n return async ({ collection, doc, previousDoc, req }) => {\n const urlDoc = doc as UrlDoc | undefined\n const previousUrlDoc = previousDoc as UrlDoc | undefined\n if (\n req.context?.disableUrlUpdates ||\n !urlDoc ||\n isDraftDoc(urlDoc) ||\n !hasUrlPathChanged(urlDoc, previousUrlDoc)\n ) {\n return urlDoc\n }\n\n const collectionOptions = getCollectionOptions(options, collection?.slug ?? \"\")\n if (!collectionOptions) {\n return urlDoc\n }\n\n const collectionSlug = collection?.slug ?? \"\"\n const isCategoryCollection = getCollectionsForCategory(options, collectionSlug).length > 0\n const source = isCategoryCollection\n ? {\n type: \"category\",\n collection: collectionSlug,\n id: urlDoc.id,\n }\n : {\n type:\n collectionOptions.breadcrumbs && !collectionOptions.rootPage ? \"page\" : \"collection\",\n collection: collectionSlug,\n id: urlDoc.id,\n }\n\n await req.payload.jobs?.queue?.({\n workflow: \"update-urls\",\n input: {\n sources: [source],\n },\n })\n\n return urlDoc\n }\n}\n\nexport function createRootPagesUrlUpdateHook(\n options: PayloadPluginUrlsOptions,\n): GlobalAfterChangeHook {\n return async ({ doc, previousDoc, req }) => {\n const rootPagesDoc = doc as RootPagesDoc\n const previousRootPagesDoc = previousDoc as RootPagesDoc | undefined\n if (req.context?.disableUrlUpdates) {\n return rootPagesDoc\n }\n\n await req.payload.jobs?.queue?.({\n workflow: \"update-urls\",\n input: {\n sources: [\n {\n type: \"rootPages\",\n current: getRootPageSnapshot(rootPagesDoc, options),\n previous: getRootPageSnapshot(previousRootPagesDoc, options),\n },\n ],\n },\n })\n\n return rootPagesDoc\n }\n}\n","import { populatedUrlField } from \"./field\"\nimport {\n createCollectionUrlUpdateHook,\n createPopulateUrlHook,\n createRootPagesUrlUpdateHook,\n} from \"./hooks\"\nimport {\n getCollectionOptions,\n getRootPageFieldNames,\n getRootPageFieldOptions,\n normalizeOptions,\n} from \"./options\"\nimport { createUpdateUrlsHandler } from \"./update-urls\"\n\nimport type {\n CollectionConfigLike,\n FieldLike,\n GlobalConfigLike,\n PayloadPlugin,\n PayloadPluginUrlsOptions,\n WorkflowLike,\n} from \"./types\"\nimport type { GlobalConfig } from \"payload\"\n\nexport const payloadPluginUrls = (options?: PayloadPluginUrlsOptions): PayloadPlugin => {\n if (!options) {\n return (config) => config\n }\n\n return (config) => {\n const normalizedOptions = normalizeOptions(options, config)\n const collections = (config.collections ?? []).map((collection) =>\n applyUrlCollectionConfig(collection, normalizedOptions),\n )\n\n return {\n ...config,\n collections,\n globals: [...(config.globals ?? []), createRootPagesGlobal(normalizedOptions)],\n jobs: {\n ...(config.jobs ?? {}),\n workflows: [\n ...(config.jobs?.workflows ?? []),\n {\n slug: \"update-urls\",\n handler: createUpdateUrlsHandler(normalizedOptions),\n } as WorkflowLike,\n ],\n },\n } as ReturnType<PayloadPlugin>\n }\n}\n\nfunction applyUrlCollectionConfig(\n collection: CollectionConfigLike,\n options: PayloadPluginUrlsOptions,\n) {\n const collectionOptions = getCollectionOptions(options, collection.slug)\n if (!collectionOptions) {\n return collection\n }\n\n const fieldName = options.field?.name ?? \"populatedUrl\"\n const fields = collection.fields.some((field) => \"name\" in field && field.name === fieldName)\n ? collection.fields\n : [...collection.fields, populatedUrlField(options)]\n const hooks = collection.hooks ?? {}\n\n return {\n ...collection,\n defaultPopulate: {\n ...(collection.defaultPopulate ?? {}),\n [fieldName]: true,\n },\n fields,\n hooks: {\n ...hooks,\n beforeChange: [...(hooks.beforeChange ?? []), createPopulateUrlHook(options)],\n afterChange: [...(hooks.afterChange ?? []), createCollectionUrlUpdateHook(options)],\n },\n } as CollectionConfigLike\n}\n\nfunction createRootPagesGlobal(options: PayloadPluginUrlsOptions): GlobalConfigLike {\n const rootPagesOptions = normalizeOptions(options).rootPages\n\n const base = {\n slug: rootPagesOptions?.slug ?? \"root-pages\",\n label: rootPagesOptions?.label ?? \"Root pages\",\n fields: getRootPageFieldNames(options).map((fieldName) =>\n createRootPageField(fieldName, options),\n ),\n hooks: {\n afterChange: [createRootPagesUrlUpdateHook(options)],\n },\n } satisfies GlobalConfigLike\n\n const partial = options.overrides\n return partial ? mergeGlobalConfigOverride(base, partial) : base\n}\n\nfunction createRootPageField(fieldName: string, options: PayloadPluginUrlsOptions): FieldLike {\n const fieldOptions = getRootPageFieldOptions(options, fieldName)\n const overrides = (fieldOptions?.overrides ?? {}) as Record<string, unknown>\n const {\n name: _name,\n type: _type,\n hasMany: _hasMany,\n relationTo: _relationTo,\n ...override\n } = overrides\n\n return {\n name: fieldName,\n type: \"relationship\",\n relationTo: fieldOptions?.relationTo ?? \"pages\",\n hasMany: false,\n admin: {\n width: \"50%\",\n },\n ...override,\n } as FieldLike\n}\n\nfunction unknownArrayFrom(value: unknown): unknown[] {\n if (!Array.isArray(value)) {\n return []\n }\n const out: unknown[] = []\n for (const item of value) {\n out.push(item)\n }\n return out\n}\n\nfunction mergeHooks<H extends Record<string, unknown> | undefined>(base: H, extra: H): H {\n if (!extra) {\n return base\n }\n if (!base) {\n return extra\n }\n const a = base\n const b = extra\n const out = { ...a }\n for (const key of Object.keys(b)) {\n const av = a[key]\n const bv = b[key]\n if (Array.isArray(av) || Array.isArray(bv)) {\n out[key] = [...unknownArrayFrom(av), ...unknownArrayFrom(bv)]\n } else if (bv !== undefined) {\n out[key] = bv\n }\n }\n return out as H\n}\n\nfunction mergeRecord(\n base: Record<string, unknown> | undefined,\n extra: Record<string, unknown> | undefined,\n): Record<string, unknown> | undefined {\n if (!extra) {\n return base\n }\n if (!base) {\n return extra\n }\n return { ...base, ...extra }\n}\n\nfunction mergeGlobalConfigOverride(\n global: GlobalConfigLike,\n override: Partial<GlobalConfig>,\n): GlobalConfigLike {\n const { hooks: oHooks, access: oAccess, admin: oAdmin, fields: _fields, ...rest } = override\n\n const merged: GlobalConfigLike = {\n ...global,\n ...rest,\n }\n\n if (oAccess) {\n merged.access = mergeRecord(\n global.access as Record<string, unknown> | undefined,\n oAccess as Record<string, unknown>,\n ) as GlobalConfig[\"access\"]\n }\n\n if (oAdmin) {\n merged.admin = mergeRecord(\n global.admin as Record<string, unknown> | undefined,\n oAdmin as Record<string, unknown>,\n ) as GlobalConfig[\"admin\"]\n }\n\n if (oHooks || global.hooks) {\n merged.hooks = mergeHooks(global.hooks, oHooks)\n }\n\n return merged\n}\n"],"mappings":"mbAAA,IAAAA,GAAA,GAAAC,GAAAD,GAAA,aAAAE,EAAA,sBAAAC,EAAA,oBAAAC,EAAA,2BAAAC,EAAA,6BAAAC,EAAA,sBAAAC,EAAA,sBAAAL,EAAA,sBAAAM,EAAA,wBAAAC,EAAA,qBAAAC,EAAA,yBAAAC,IAAA,eAAAC,GAAAZ,ICEA,IAAMa,EAAwBC,GAAiBA,EAAK,QAAQ,MAAO,EAAE,EAAE,QAAQ,OAAQ,GAAG,EAE1F,SAASC,EAAkBC,EAA8C,CAGvE,OAFiBA,GAAa,GAAG,EAAE,GACb,KAAO,IAClB,QAAQ,eAAgB,EAAE,CACvC,CAEA,SAASC,EAA2BC,EAAkBC,EAA0B,CAC9E,MAAO,CACL,GAAIA,GAAe,CAAC,EACpB,GAAGC,GAAuBF,CAAI,CAChC,CACF,CAEA,SAASG,EAAsCC,EAAQ,CACrD,GAAM,CAAE,aAAcC,EAAe,GAAGC,CAAK,EAAIF,EACjD,OAAOE,CACT,CAEA,SAASC,EAAcH,EAAc,CACnC,GAAI,GAACA,GAAO,OAAOA,GAAQ,UAAY,EAAE,OAAQA,IAIjD,OAAO,OAAOA,EAAI,IAAO,SAAWA,EAAI,GAAK,MAC/C,CAEA,SAASI,EAAcC,EAAgB,CACrC,GAAI,OAAOA,GAAU,SACnB,OAAOA,EAGT,GAAI,GAACA,GAAS,OAAOA,GAAU,UAAY,EAAE,OAAQA,IAIrD,OAAO,OAAOA,EAAM,IAAO,SAAWA,EAAM,GAAK,MACnD,CAEA,SAASC,EAAcd,EAA0B,CAC/C,OAAOD,EAAqB,IAAIC,GAAQ,EAAE,GAAG,QAAQ,OAAQ,GAAG,CAAC,CACnE,CAEA,SAASe,EAAeF,EAAgBG,EAA8B,CACpE,GAAI,CAACH,GAAS,OAAOA,GAAU,UAAY,EAAEG,KAAOH,GAClD,OAGF,IAAMI,EAASJ,EACf,OAAO,OAAOI,EAAOD,CAAG,GAAM,SAAWC,EAAOD,CAAG,EAAI,MACzD,CAEA,SAASE,EAAWV,EAAa,CAC/B,OAAOA,EAAI,UAAY,OACzB,CAEA,SAASW,EAAUN,EAAgB,CACjC,OAAOA,GAAS,OAAOA,GAAU,UAAY,CAAC,MAAM,QAAQA,CAAK,EAC5DA,EACD,CAAC,CACP,CAEA,SAASO,EAAyCC,EAAc,CAC9D,IAAMC,EAAO,IAAI,IAEjB,OAAOD,EAAQ,OAAQE,GAAW,CAChC,IAAMP,EAAMQ,GAAUD,CAAM,EAC5B,OAAID,EAAK,IAAIN,CAAG,EACP,IAETM,EAAK,IAAIN,CAAG,EACL,GACT,CAAC,CACH,CAEA,SAASQ,GAAUD,EAAyB,CAC1C,OAAQA,EAAO,KAAM,CACnB,IAAK,WACL,IAAK,aACL,IAAK,OACH,MAAO,GAAGA,EAAO,IAAI,IAAIA,EAAO,UAAU,IAAIA,EAAO,IAAM,EAAE,GAC/D,IAAK,YACH,MAAO,aAAa,KAAK,UAAUA,EAAO,OAAO,CAAC,IAAI,KAAK,UAAUA,EAAO,QAAQ,CAAC,EACzF,CACF,CAEA,SAASjB,GAAyCO,EAAmB,CACnE,OAAO,OAAO,YACZ,OAAO,QAAQA,CAAK,EAAE,OAAO,CAAC,CAAC,CAAEY,CAAK,IAAMA,IAAU,MAAS,CACjE,CACF,CCxFO,SAASC,EAAkBC,EAAoC,CAAE,YAAa,CAAC,CAAE,EAAU,CAGhG,MAAO,CACL,KAHgBA,EAAQ,OAAO,MAAQ,eAIvC,KAAM,OACN,MAAO,GACP,UAAW,GACX,GAAIA,EAAQ,OAAO,WAAa,CAAC,EACjC,MAAO,CACL,OAAQ,GACR,GAAGC,EAAUD,EAAQ,OAAO,WAAW,KAAK,CAC9C,CACF,CACF,CCCO,SAASE,EACdC,EACAC,EACoC,CAGpC,IAAMC,EAAU,CACd,GAHoBC,GAAiBF,CAAM,GACJ,CAAE,cAAe,KAAM,QAAS,CAAC,IAAI,CAAE,EAG9E,GAAGD,EAAQ,OACb,EAEA,MAAO,CACL,GAAGA,EACH,MAAO,CACL,KAAM,eACN,GAAGA,EAAQ,KACb,EACA,QAAS,CACP,cAAeE,EAAQ,eAAiBA,EAAQ,QAAQ,CAAC,GAAK,KAC9D,QAASA,EAAQ,QAAQ,OAASA,EAAQ,QAAU,CAACA,EAAQ,eAAiB,IAAI,CACpF,EACA,UAAW,CACT,KAAM,aACN,GAAGF,EAAQ,UACX,OAAQA,EAAQ,WAAW,QAAU,CACnC,UAAW,CACT,WAAY,GACZ,WAAY,OACd,CACF,CACF,CACF,CACF,CAEO,SAASI,EAAqBJ,EAAmCK,EAAoB,CAC1F,OAAOL,EAAQ,YAAYK,CAAU,CACvC,CAEO,SAASC,EAAqBN,EAAmC,CACtE,OAAO,OAAO,QAAQA,EAAQ,WAAW,CAC3C,CAEO,SAASO,EACdP,EACAQ,EACA,CACA,OAAOF,EAAqBN,CAAO,EAChC,OACC,CAAC,CAAC,CAAES,CAAiB,IAAMA,EAAkB,UAAU,aAAeD,CACxE,EACC,IAAI,CAAC,CAACH,CAAU,IAAMA,CAAU,CACrC,CAEO,SAASK,EAAsBV,EAAmC,CACvE,IAAMW,EAAoBZ,EAAiBC,CAAO,EAClD,OAAO,OAAO,KAAKW,EAAkB,UAAU,MAAM,CACvD,CAEO,SAASC,EAAyBZ,EAAmC,CAC1E,IAAMa,EAASd,EAAiBC,CAAO,EAAE,UAAU,OAKnD,OAHE,OAAO,QAAQa,CAAM,EAAE,KAAK,CAAC,CAAC,CAAEC,CAAK,IAAMA,EAAM,UAAU,GAC3D,OAAO,QAAQD,CAAM,EAAE,KAAK,CAAC,CAACE,CAAS,IAAMA,IAAc,WAAW,KAEjD,CAAC,GAAK,OAAO,KAAKF,CAAM,EAAE,CAAC,GAAK,WACzD,CAEO,SAASG,EAAwBhB,EAAmCe,EAAmB,CAC5F,OAAOhB,EAAiBC,CAAO,EAAE,UAAU,OAAOe,CAAS,CAC7D,CAEA,SAASZ,GAAiBF,EAAyC,CACjE,IAAMgB,EAAehB,GAAQ,cAAgB,OACvCC,EAAUe,GAAc,SAC1B,IAAKC,GAAY,OAAOA,GAAW,SAAWA,EAASA,EAAO,IAAK,EACpE,OAAQA,GAA6B,EAAQA,CAAO,EAEvD,GAAKhB,GAAS,OAId,MAAO,CACL,cAAee,GAAc,eAAiBf,EAAQ,CAAC,GAAK,KAC5D,QAAAA,CACF,CACF,CC5FO,SAASiB,EACdC,EACA,CAAE,QAAAC,EAAS,OAAAC,EAAQ,QAAAC,EAAS,kBAAAC,CAAkB,EAC9C,CACA,GAAI,OAAOJ,EAAU,OAAU,SAC7B,MAAM,IAAI,MAAM,6BAA6B,EAG/C,GAAIA,EAAU,MAAM,aAClB,OAAOK,EAAqBL,EAAU,MAAM,YAAY,EAG1D,IAAMM,EAAoBC,EAAiBJ,CAAO,EAC5CK,EAAoBC,EAAqBH,EAAmBN,EAAU,UAAU,EAChFU,EAAkBF,GAAmB,iBAAmBR,EAAU,WAClEW,EAAQC,GACZJ,EACAR,EAAU,MACVI,GAAqBI,GAAmB,cAC1C,EAEA,OAAOK,EAAuBF,EAAO,CACnC,QAAAV,EACA,WAAYS,EACZ,OAAAR,EACA,QAASI,CACX,CAAC,CACH,CAEO,SAASO,EACdF,EACA,CACE,QAAAV,EACA,OAAAC,EACA,QAAAC,CACF,EAMA,CACA,IAAMG,EAAoBC,EAAiBJ,CAAO,EAE5CW,EAAW,CAAC,IADHb,IAAYC,IAAWI,EAAkB,SAAS,cAAgB,GAAKJ,IAC1D,MAAM,GAAG,EAAG,GAAGS,CAAK,EAAE,OAAO,OAAO,EAChE,OAAON,EAAqB,IAAIS,EAAS,KAAK,GAAG,CAAC,EAAE,CACtD,CAEO,SAASC,EAAiBC,EAAcd,EAAgBC,EAAmC,CAChG,IAAMc,EAAgBV,EAAiBJ,CAAO,EAAE,SAAS,cACzD,OAAID,IAAWe,EACNZ,EAAqBW,CAAI,EAE3BX,EAAqB,IAAIH,CAAM,GAAGc,CAAI,EAAE,CACjD,CAEA,SAASJ,GACPJ,EACAU,EACAC,EACA,CACA,OAAIX,GAAmB,SACdW,IAAa,WAChB,CAACD,EAAI,MAAQ,EAAE,EACf,CAACE,GAAyBF,CAAG,EAAGA,EAAI,MAAQ,EAAE,EAGhDV,GAAmB,YACd,CAACa,EAAkBH,EAAI,WAAW,GAAKA,EAAI,MAAQ,EAAE,EAGvD,CAACA,EAAI,MAAQ,EAAE,CACxB,CAEA,SAASE,GAAyBF,EAAa,CAC7C,IAAMI,EAAaJ,EAAI,WACvB,GAAI,CAAC,MAAM,QAAQI,CAAU,GAAKA,EAAW,SAAW,EACtD,MAAO,GAIT,IAAMC,EADgBD,EACM,CAAC,EAC7B,GAAI,CAACC,GAAS,OAAOA,GAAU,UAAY,OAAOA,GAAU,SAC1D,MAAO,GAGT,IAAMC,EAAcD,EACpB,OACEF,EAAkBG,EAAY,WAAW,IACxCA,EAAY,MAAQ,IAAI,QAAQ,eAAgB,EAAE,CAEvD,CC/EA,eAAsBC,EAAoB,CACxC,WAAAC,EACA,KAAAC,EACA,OAAAC,EACA,QAAAC,EACA,YAAAC,EACA,QAAAC,EACA,UAAAC,CACF,EAAyD,CACvD,IAAMC,EAAoBC,EAAiBL,CAAO,EAC5CM,EAAoBC,EAAqBH,EAAmBP,CAAU,EAC5E,GAAI,CAACS,EACH,OAGF,IAAME,EAAMC,EAASX,EAAMG,CAAW,EAChCS,EAAgBC,EAAyBP,CAAiB,EAEhE,GAAIE,EAAkB,aAAe,CAACA,EAAkB,SAAU,CAChE,IAAMM,EAAW,MAAMC,EAAe,CACpC,MAAOH,EACP,OAAAX,EACA,QAAAG,EACA,UAAAC,CACF,CAAC,EACKW,EAAaC,EAAcH,CAAQ,EAEzC,GAAIJ,EAAI,IAAMM,IAAeN,EAAI,GAC/B,OAAOQ,EAAiB,IAAKjB,EAAQK,CAAiB,EAGxD,IAAMa,EAAkBC,EAAcC,EAAkBX,EAAI,WAAW,CAAC,EAClEY,EAAeF,EAAcC,EAAkBP,GAAU,WAAW,CAAC,EACrES,EACJD,GAAgBH,EAAgB,WAAW,GAAGG,CAAY,GAAG,EACzDF,EAAcD,EAAgB,MAAMG,EAAa,MAAM,CAAC,EACxDH,EAEN,OAAOD,EAAiBK,GAAY,IAAIb,EAAI,MAAQ,EAAE,GAAIT,EAAQK,CAAiB,CACrF,CAEA,IAAMkB,EAAkC,MAAMC,GAAe,CAC3D,kBAAAjB,EACA,OAAAP,EACA,QAASK,EACT,QAAAF,EACA,UAAAC,CACF,CAAC,EAED,GAAIG,EAAkB,SAAU,CAC9B,IAAMkB,EAAa,MAAMC,GAAkB,CACzC,WAAYjB,EAAIF,EAAkB,SAAS,OAAS,YAAY,EAChE,WAAYA,EAAkB,SAAS,WACvC,OAAAP,EACA,QAAAG,CACF,CAAC,EAED,OAAOwB,EACL,CACE,WAAY7B,EACZ,MAAO,CACL,GAAG8B,EAAoBnB,CAAG,EAC1B,CAACF,EAAkB,SAAS,OAAS,YAAY,EAAGkB,EACpD,WAAAA,CACF,CACF,EACA,CACE,QAASF,EACT,OAAAvB,EACA,QAASK,CACX,CACF,CACF,CAEA,OAAOsB,EACL,CACE,WAAY7B,EACZ,MAAO8B,EAAoBnB,CAAG,CAChC,EACA,CACE,QAASc,EACT,OAAAvB,EACA,QAASK,CACX,CACF,CACF,CAEA,eAAemB,GAAe,CAC5B,kBAAAjB,EACA,OAAAP,EACA,QAAAC,EACA,QAAAE,EACA,UAAAC,CACF,EAMgC,CAC9B,GAAI,CAACG,EAAkB,SACrB,OAGF,IAAMsB,EAAgBtB,EAAkB,SAElCuB,EADuBC,EAAwB9B,EAAS4B,CAAa,GAClC,YAAc,QACjDG,EAAW,MAAMlB,EAAe,CACpC,WAAYgB,EACZ,MAAOD,EACP,OAAA7B,EACA,QAAAG,EACA,UAAAC,CACF,CAAC,EAED,GAAK4B,EAIL,OAAI,OAAOA,EAAS,cAAiB,UAAYA,EAAS,aACjDC,EAAyBD,EAAS,aAAchC,EAAQC,CAAO,EAGpE6B,IAAe,QACVG,EACLN,EACE,CACE,WAAAG,EACA,MAAOE,CACT,EACA,CACE,OAAAhC,EACA,QAAAC,CACF,CACF,EACAD,EACAC,CACF,EAGKJ,EAAoB,CACzB,WAAYiC,EACZ,KAAM,CAAC,EACP,OAAA9B,EACA,QAAAC,EACA,YAAa+B,EACb,QAAA7B,EACA,UAAAC,CACF,CAAC,CACH,CAEA,SAAS6B,EAAyBC,EAAclC,EAAgBC,EAAmC,CACjG,IAAMI,EAAoBC,EAAiBL,CAAO,EAClD,OACED,IAAWK,EAAkB,QAAQ,eACrC6B,IAAS,IAAIlC,CAAM,IACnBkC,EAAK,WAAW,IAAIlC,CAAM,GAAG,EAEtBkC,EAGFjB,EAAiBiB,EAAMlC,EAAQK,CAAiB,CACzD,CAEA,eAAeS,EAAe,CAC5B,WAAAhB,EAAa,QACb,MAAAqC,EACA,OAAAnC,EACA,QAAAG,EACA,UAAAC,CACF,EAMG,CACD,IAAMgC,EAAOhC,EAAU+B,CAAK,EAE5B,OAAKC,EAID,OAAOA,GAAS,SACXA,EAGK,MAAMjC,GAAS,WAAW,CACtC,WAAAL,EACA,GAAIsC,EACJ,MAAO,EACP,OAAApC,EACA,OAAQ,CACN,GAAI,GACJ,KAAM,GACN,aAAc,GACd,YAAa,EACf,CACF,CAAC,EAlBC,MAoBJ,CAEA,eAAe0B,GAAkB,CAC/B,WAAAD,EACA,WAAA3B,EACA,OAAAE,EACA,QAAAG,CACF,EAKG,CACD,OAAK,MAAM,QAAQsB,CAAU,EAItB,QAAQ,IACbA,EAAW,IAAKY,GACV,OAAOA,GAAa,SACf,QAAQ,QAAQA,CAAQ,EAI/BlC,GAAS,WAAW,CAClB,WAAAL,EACA,GAAIuC,EACJ,MAAO,EACP,OAAArC,CACF,CAAC,GAAK,QAAQ,QAAQqC,CAAQ,CAEjC,CACH,EAlBS,CAAC,CAmBZ,CC9OO,SAASC,EAAwBC,EAAmC,CACzE,MAAO,OAAO,CACZ,IAAAC,EACA,IAAAC,CACF,IASM,CACJ,IAAMC,EAAoBC,EAAiBJ,CAAO,EAC5CK,EAAUJ,EAAI,OAAO,SAAW,CAAC,EAEvC,QAAWK,KAAUH,EAAkB,SAAS,SAAW,CAAC,EAAG,CAC7D,IAAMI,EAAY,MAAML,EAAI,QAAQ,aAAa,CAC/C,KAAMC,EAAkB,WAAW,MAAQ,aAC3C,MAAO,EACP,OAAAG,CACF,CAAC,EACD,GAAKC,EAIL,QAAWC,KAAUC,GAAcJ,EAASF,CAAiB,EAC3D,OAAQK,EAAO,KAAM,CACnB,IAAK,WACH,MAAME,EAA0B,CAC9B,WAAYF,EAAO,WACnB,OAAAF,EACA,QAASH,EACT,QAASD,EAAI,QACb,UAAAK,CACF,CAAC,EACD,QAAWI,KAAcC,EACvBT,EACAK,EAAO,UACT,EACE,MAAME,EAA0B,CAC9B,WAAAC,EACA,OAAAL,EACA,QAASH,EACT,QAASD,EAAI,QACb,UAAAK,CACF,CAAC,EAEH,MACF,IAAK,aACL,IAAK,OACH,MAAMG,EAA0B,CAC9B,WAAYF,EAAO,WACnB,OAAAF,EACA,QAASH,EACT,QAASD,EAAI,QACb,UAAAK,CACF,CAAC,EACD,MACF,IAAK,YACH,KACJ,CAEJ,CACF,CACF,CAEO,SAASM,EAAkBC,EAAcC,EAAsB,CACpE,IAAMC,EAASC,EAAeH,EAAK,cAAc,EAC3CI,EAAcD,EAAeF,EAAa,cAAc,EAE9D,OAAIC,GAAUE,EACLF,IAAWE,EAGbD,EAAeH,EAAK,MAAM,IAAMG,EAAeF,EAAa,MAAM,CAC3E,CAEO,SAASI,EACdC,EACAC,EACArB,EACmB,CACnB,IAAMG,EAAoBC,EAAiBJ,CAAO,EAC5CK,EAA6B,CAAC,EAC9BiB,EAAiBC,EAAyBpB,CAAiB,EAC3DqB,EACJC,EAAwBtB,EAAmBmB,CAAc,GAAG,YAAc,QACtEI,EAAqBC,EAAcP,EAAQE,CAAc,CAAC,EAC1DM,EAAsBD,EAAcN,IAAWC,CAAc,CAAC,EAEhEI,IAAuBE,IACrBF,GACFrB,EAAQ,KAAK,CAAE,KAAM,OAAQ,WAAYmB,EAAqB,GAAIE,CAAmB,CAAC,EAEpFE,GACFvB,EAAQ,KAAK,CAAE,KAAM,OAAQ,WAAYmB,EAAqB,GAAII,CAAoB,CAAC,GAI3F,OAAW,CAACjB,EAAYkB,CAAiB,IAAKC,EAAqB3B,CAAiB,EAAG,CACrF,GAAI,CAAC0B,EAAkB,SACrB,SAGF,IAAME,EAAoBJ,EAAcP,EAAQS,EAAkB,QAAQ,CAAC,EACrEG,EAAqBL,EAAcN,IAAWQ,EAAkB,QAAQ,CAAC,EAC3EE,IAAsBC,GACxB3B,EAAQ,KAAK,CAAE,KAAM,aAAc,WAAAM,CAAW,CAAC,CAEnD,CAEA,OAAOsB,EAAc5B,CAAO,CAC9B,CAEO,SAAS6B,EACd3B,EACAP,EACA,CACA,IAAMmC,EAAyB,CAAC,EAEhC,QAAWC,KAAaC,EAAsBrC,CAAO,EACnDmC,EAASC,CAAS,EAAI7B,IAAY6B,CAAS,EAG7C,OAAOD,CACT,CAEA,SAAS1B,GAAcJ,EAA4BL,EAAmC,CACpF,OAAOK,EAAQ,QAASG,GAClBA,EAAO,OAAS,YACX,CAACA,CAAM,EAGTW,EAAyBX,EAAO,QAASA,EAAO,SAAUR,CAAO,CACzE,CACH,CAEA,eAAeU,EAA0B,CACvC,WAAAC,EACA,OAAAL,EACA,QAAAN,EACA,QAAAsC,EACA,UAAA/B,CACF,EAMG,CACD,IAAIgC,EAAO,EAEX,OAAS,CACP,IAAMC,EAAS,MAAMF,EAAQ,OAAO,CAClC,WAAA3B,EACA,MAAO,EACP,MAAO,GACP,MAAO,IACP,OAAAL,EACA,eAAgB,GAChB,KAAAiC,EACA,WAAY,EACd,CAAC,EAED,GAAI,CAACC,EACH,OAGF,QAAW1B,KAAO0B,EAAO,KAAM,CAC7B,IAAMC,EAAS3B,EACf,GAAI,CAAC2B,EAAO,IAAMC,EAAWD,CAAM,EACjC,SAGF,IAAME,EAAoB,MAAMC,EAAoB,CAClD,WAAAjC,EACA,KAAM,CAAC,EACP,OAAAL,EACA,QAAAN,EACA,YAAayC,EACb,QAAAH,EACA,UAAA/B,CACF,CAAC,EAEG,CAACoC,GAAqBF,EAAO,eAAiBE,GAIlD,MAAML,EAAQ,SAAS,CACrB,WAAA3B,EACA,GAAI8B,EAAO,GACX,OAAAnC,EACA,eAAgB,GAChB,KAAM,CACJ,CAACN,EAAQ,OAAO,MAAQ,cAAc,EAAG2C,CAC3C,EACA,QAAS,CACP,mBAAoB,GACpB,kBAAmB,EACrB,CACF,CAAC,CACH,CAEA,GAAI,CAACH,EAAO,SACV,OAGFD,EAAOC,EAAO,QAChB,CACF,CC3NO,SAASK,EACdC,EAC4B,CAC5B,MAAO,OAAO,CAAE,WAAAC,EAAY,QAAAC,EAAS,KAAAC,EAAO,CAAC,EAAG,YAAAC,EAAa,IAAAC,CAAI,IAAM,CACrE,IAAMC,EAASD,EAAI,OACnB,GACE,CAACC,GACDA,IAAW,OACXJ,GAAS,oBACTG,EAAI,SAAS,mBAEb,OAAOF,EAGT,IAAMI,EAAY,MAAMF,EAAI,QAAQ,aAAa,CAC/C,KAAMG,EAAiBR,CAAO,EAAE,WAAW,MAAQ,aACnD,MAAO,EACP,OAAAM,CACF,CAAC,EACD,GAAI,CAACC,EACH,OAAOJ,EAGT,IAAMM,EAAoB,MAAMC,EAAoB,CAClD,WAAYT,GAAY,MAAQ,GAChC,KAAME,EACN,OAAAG,EACA,QAAAN,EACA,YAAaI,EACb,QAASC,EAAI,QACb,UAAWE,CACb,CAAC,EAED,OAAIE,IACFN,EAAKH,EAAQ,OAAO,MAAQ,cAAc,EAAIS,GAGzCN,CACT,CACF,CAEO,SAASQ,EACdX,EAC2B,CAC3B,MAAO,OAAO,CAAE,WAAAC,EAAY,IAAAW,EAAK,YAAAC,EAAa,IAAAR,CAAI,IAAM,CACtD,IAAMS,EAASF,EACTG,EAAiBF,EACvB,GACER,EAAI,SAAS,mBACb,CAACS,GACDE,EAAWF,CAAM,GACjB,CAACG,EAAkBH,EAAQC,CAAc,EAEzC,OAAOD,EAGT,IAAMI,EAAoBC,EAAqBnB,EAASC,GAAY,MAAQ,EAAE,EAC9E,GAAI,CAACiB,EACH,OAAOJ,EAGT,IAAMM,EAAiBnB,GAAY,MAAQ,GAErCoB,EADuBC,EAA0BtB,EAASoB,CAAc,EAAE,OAAS,EAErF,CACE,KAAM,WACN,WAAYA,EACZ,GAAIN,EAAO,EACb,EACA,CACE,KACEI,EAAkB,aAAe,CAACA,EAAkB,SAAW,OAAS,aAC1E,WAAYE,EACZ,GAAIN,EAAO,EACb,EAEJ,aAAMT,EAAI,QAAQ,MAAM,QAAQ,CAC9B,SAAU,cACV,MAAO,CACL,QAAS,CAACgB,CAAM,CAClB,CACF,CAAC,EAEMP,CACT,CACF,CAEO,SAASS,EACdvB,EACuB,CACvB,MAAO,OAAO,CAAE,IAAAY,EAAK,YAAAC,EAAa,IAAAR,CAAI,IAAM,CAC1C,IAAMmB,EAAeZ,EACfa,EAAuBZ,EAC7B,OAAIR,EAAI,SAAS,mBAIjB,MAAMA,EAAI,QAAQ,MAAM,QAAQ,CAC9B,SAAU,cACV,MAAO,CACL,QAAS,CACP,CACE,KAAM,YACN,QAASqB,EAAoBF,EAAcxB,CAAO,EAClD,SAAU0B,EAAoBD,EAAsBzB,CAAO,CAC7D,CACF,CACF,CACF,CAAC,EAEMwB,CACT,CACF,CCpGO,IAAMG,EAAqBC,GAC3BA,EAIGC,GAAW,CACjB,IAAMC,EAAoBC,EAAiBH,EAASC,CAAM,EACpDG,GAAeH,EAAO,aAAe,CAAC,GAAG,IAAKI,GAClDC,GAAyBD,EAAYH,CAAiB,CACxD,EAEA,MAAO,CACL,GAAGD,EACH,YAAAG,EACA,QAAS,CAAC,GAAIH,EAAO,SAAW,CAAC,EAAIM,GAAsBL,CAAiB,CAAC,EAC7E,KAAM,CACJ,GAAID,EAAO,MAAQ,CAAC,EACpB,UAAW,CACT,GAAIA,EAAO,MAAM,WAAa,CAAC,EAC/B,CACE,KAAM,cACN,QAASO,EAAwBN,CAAiB,CACpD,CACF,CACF,CACF,CACF,EAxBUD,GAAWA,EA2BvB,SAASK,GACPD,EACAL,EACA,CAEA,GAAI,CADsBS,EAAqBT,EAASK,EAAW,IAAI,EAErE,OAAOA,EAGT,IAAMK,EAAYV,EAAQ,OAAO,MAAQ,eACnCW,EAASN,EAAW,OAAO,KAAMO,GAAU,SAAUA,GAASA,EAAM,OAASF,CAAS,EACxFL,EAAW,OACX,CAAC,GAAGA,EAAW,OAAQQ,EAAkBb,CAAO,CAAC,EAC/Cc,EAAQT,EAAW,OAAS,CAAC,EAEnC,MAAO,CACL,GAAGA,EACH,gBAAiB,CACf,GAAIA,EAAW,iBAAmB,CAAC,EACnC,CAACK,CAAS,EAAG,EACf,EACA,OAAAC,EACA,MAAO,CACL,GAAGG,EACH,aAAc,CAAC,GAAIA,EAAM,cAAgB,CAAC,EAAIC,EAAsBf,CAAO,CAAC,EAC5E,YAAa,CAAC,GAAIc,EAAM,aAAe,CAAC,EAAIE,EAA8BhB,CAAO,CAAC,CACpF,CACF,CACF,CAEA,SAASO,GAAsBP,EAAqD,CAClF,IAAMiB,EAAmBd,EAAiBH,CAAO,EAAE,UAE7CkB,EAAO,CACX,KAAMD,GAAkB,MAAQ,aAChC,MAAOA,GAAkB,OAAS,aAClC,OAAQE,EAAsBnB,CAAO,EAAE,IAAKU,GAC1CU,GAAoBV,EAAWV,CAAO,CACxC,EACA,MAAO,CACL,YAAa,CAACqB,EAA6BrB,CAAO,CAAC,CACrD,CACF,EAEMsB,EAAUtB,EAAQ,UACxB,OAAOsB,EAAUC,GAA0BL,EAAMI,CAAO,EAAIJ,CAC9D,CAEA,SAASE,GAAoBV,EAAmBV,EAA8C,CAC5F,IAAMwB,EAAeC,EAAwBzB,EAASU,CAAS,EACzDgB,EAAaF,GAAc,WAAa,CAAC,EACzC,CACJ,KAAMG,EACN,KAAMC,EACN,QAASC,EACT,WAAYC,EACZ,GAAGC,CACL,EAAIL,EAEJ,MAAO,CACL,KAAMhB,EACN,KAAM,eACN,WAAYc,GAAc,YAAc,QACxC,QAAS,GACT,MAAO,CACL,MAAO,KACT,EACA,GAAGO,CACL,CACF,CAEA,SAASC,EAAiBC,EAA2B,CACnD,GAAI,CAAC,MAAM,QAAQA,CAAK,EACtB,MAAO,CAAC,EAEV,IAAMC,EAAiB,CAAC,EACxB,QAAWC,KAAQF,EACjBC,EAAI,KAAKC,CAAI,EAEf,OAAOD,CACT,CAEA,SAASE,GAA0DlB,EAASmB,EAAa,CACvF,GAAI,CAACA,EACH,OAAOnB,EAET,GAAI,CAACA,EACH,OAAOmB,EAET,IAAMC,EAAIpB,EACJqB,EAAIF,EACJH,EAAM,CAAE,GAAGI,CAAE,EACnB,QAAWE,KAAO,OAAO,KAAKD,CAAC,EAAG,CAChC,IAAME,EAAKH,EAAEE,CAAG,EACVE,EAAKH,EAAEC,CAAG,EACZ,MAAM,QAAQC,CAAE,GAAK,MAAM,QAAQC,CAAE,EACvCR,EAAIM,CAAG,EAAI,CAAC,GAAGR,EAAiBS,CAAE,EAAG,GAAGT,EAAiBU,CAAE,CAAC,EACnDA,IAAO,SAChBR,EAAIM,CAAG,EAAIE,EAEf,CACA,OAAOR,CACT,CAEA,SAASS,EACPzB,EACAmB,EACqC,CACrC,OAAKA,EAGAnB,EAGE,CAAE,GAAGA,EAAM,GAAGmB,CAAM,EAFlBA,EAHAnB,CAMX,CAEA,SAASK,GACPqB,EACAb,EACkB,CAClB,GAAM,CAAE,MAAOc,EAAQ,OAAQC,EAAS,MAAOC,EAAQ,OAAQC,EAAS,GAAGC,CAAK,EAAIlB,EAE9EmB,EAA2B,CAC/B,GAAGN,EACH,GAAGK,CACL,EAEA,OAAIH,IACFI,EAAO,OAASP,EACdC,EAAO,OACPE,CACF,GAGEC,IACFG,EAAO,MAAQP,EACbC,EAAO,MACPG,CACF,IAGEF,GAAUD,EAAO,SACnBM,EAAO,MAAQd,GAAWQ,EAAO,MAAOC,CAAM,GAGzCK,CACT","names":["index_exports","__export","payloadPluginUrls","getBreadcrumbsUrl","getDocumentLink","getDocumentLinkBySlugs","getRootPageChangeSources","hasUrlPathChanged","populatedUrlField","resolvePopulatedUrl","withLocalePrefix","withoutTrailingSlash","__toCommonJS","withoutTrailingSlash","path","getBreadcrumbsUrl","breadcrumbs","mergeDoc","data","originalDoc","withoutUndefinedValues","withoutPopulatedUrl","doc","_populatedUrl","rest","getDocumentId","getRelationId","value","normalizePath","getStringValue","key","record","isDraftDoc","getRecord","dedupeSources","sources","seen","source","sourceKey","entry","populatedUrlField","options","getRecord","normalizeOptions","options","config","locales","getConfigLocales","getCollectionOptions","collection","getCollectionEntries","getCollectionsForCategory","categoryCollection","collectionOptions","getRootPageFieldNames","normalizedOptions","getHomepageRootPageField","fields","field","fieldName","getRootPageFieldOptions","localization","locale","getDocumentLink","reference","baseUrl","locale","options","urlPrefixStrategy","withoutTrailingSlash","normalizedOptions","normalizeOptions","collectionOptions","getCollectionOptions","routeCollection","slugs","getSlugsForCollection","getDocumentLinkBySlugs","segments","withLocalePrefix","path","defaultLocale","doc","strategy","firstRelatedCategoryPath","getBreadcrumbsUrl","categories","first","categoryDoc","resolvePopulatedUrl","collection","data","locale","options","originalDoc","payload","rootPages","normalizedOptions","normalizeOptions","collectionOptions","getCollectionOptions","doc","mergeDoc","homepageField","getHomepageRootPageField","homepage","getRootPageDoc","homepageId","getDocumentId","withLocalePrefix","breadcrumbsPath","normalizePath","getBreadcrumbsUrl","homepagePath","pagePath","rootPageUrl","getRootPageUrl","categories","resolveCategories","getDocumentLink","withoutPopulatedUrl","rootPageField","relationTo","getRootPageFieldOptions","rootPage","withLocalePrefixIfNeeded","path","field","page","category","createUpdateUrlsHandler","options","job","req","normalizedOptions","normalizeOptions","sources","locale","rootPages","source","expandSources","updateCollectionDocuments","collection","getCollectionsForCategory","hasUrlPathChanged","doc","previousDoc","docUrl","getStringValue","previousUrl","getRootPageChangeSources","current","previous","indexPageField","getHomepageRootPageField","indexPageCollection","getRootPageFieldOptions","currentIndexPageId","getRelationId","previousIndexPageId","collectionOptions","getCollectionEntries","currentRootPageId","previousRootPageId","dedupeSources","getRootPageSnapshot","snapshot","fieldName","getRootPageFieldNames","payload","page","result","urlDoc","isDraftDoc","populatedUrlValue","resolvePopulatedUrl","createPopulateUrlHook","options","collection","context","data","originalDoc","req","locale","rootPages","normalizeOptions","populatedUrlValue","resolvePopulatedUrl","createCollectionUrlUpdateHook","doc","previousDoc","urlDoc","previousUrlDoc","isDraftDoc","hasUrlPathChanged","collectionOptions","getCollectionOptions","collectionSlug","source","getCollectionsForCategory","createRootPagesUrlUpdateHook","rootPagesDoc","previousRootPagesDoc","getRootPageSnapshot","payloadPluginUrls","options","config","normalizedOptions","normalizeOptions","collections","collection","applyUrlCollectionConfig","createRootPagesGlobal","createUpdateUrlsHandler","getCollectionOptions","fieldName","fields","field","populatedUrlField","hooks","createPopulateUrlHook","createCollectionUrlUpdateHook","rootPagesOptions","base","getRootPageFieldNames","createRootPageField","createRootPagesUrlUpdateHook","partial","mergeGlobalConfigOverride","fieldOptions","getRootPageFieldOptions","overrides","_name","_type","_hasMany","_relationTo","override","unknownArrayFrom","value","out","item","mergeHooks","extra","a","b","key","av","bv","mergeRecord","global","oHooks","oAccess","oAdmin","_fields","rest","merged"]}
1
+ {"version":3,"sources":["../src/index.ts","../src/utils.ts","../src/field.ts","../src/options.ts","../src/link.ts","../src/resolver.ts","../src/update-urls.ts","../src/hooks.ts","../src/plugin.ts"],"sourcesContent":["export { populatedUrlField } from \"./field\"\nexport { getDocumentLink, getDocumentLinkBySlugs, withLocalePrefix } from \"./link\"\nexport { payloadPluginUrls } from \"./plugin\"\nexport { resolvePopulatedUrl } from \"./resolver\"\nexport { getRootPageChangeSources, hasUrlPathChanged } from \"./update-urls\"\nexport { getBreadcrumbsUrl, withoutTrailingSlash } from \"./utils\"\n\nexport type {\n Breadcrumb,\n CollectionConfigLike,\n FieldLike,\n GetDocumentLinkArgs,\n GetDocumentLinkContext,\n GlobalConfigLike,\n Hook,\n HookArgs,\n Locale,\n PayloadLike,\n PayloadPlugin,\n PayloadPluginConfig,\n PayloadPluginUrlsOptions,\n ResolvePopulatedUrlArgs,\n RootPageFieldOptions,\n RootPagesDoc,\n UrlCollectionOptions,\n UrlDoc,\n UrlPrefixStrategy,\n UrlUpdateSource,\n WorkflowLike,\n} from \"./types\"\n\nexport { payloadPluginUrls as default } from \"./plugin\"\n","import type { Breadcrumb, UrlDoc, UrlUpdateSource } from \"./types\"\n\nconst withoutTrailingSlash = (path: string) => path.replace(/\\/$/, \"\").replace(/^\\/?/, \"/\")\n\nfunction getBreadcrumbsUrl(breadcrumbs: Breadcrumb[] | null | undefined) {\n const lastItem = breadcrumbs?.at(-1)\n const url = lastItem?.url ?? \"\"\n return url.replace(/(^\\/)|(\\/$)/g, \"\")\n}\n\nfunction mergeDoc<T extends object>(data: Partial<T>, originalDoc?: Partial<T>) {\n return {\n ...(originalDoc || {}),\n ...withoutUndefinedValues(data),\n } as T\n}\n\nfunction withoutPopulatedUrl<T extends object>(doc: T) {\n const { populatedUrl: _populatedUrl, ...rest } = doc as T & { populatedUrl?: unknown }\n return rest\n}\n\nfunction getDocumentId(doc: unknown) {\n if (!doc || typeof doc !== \"object\" || !(\"id\" in doc)) {\n return undefined\n }\n\n return typeof doc.id === \"string\" ? doc.id : undefined\n}\n\nfunction getRelationId(value: unknown) {\n if (typeof value === \"string\") {\n return value\n }\n\n if (!value || typeof value !== \"object\" || !(\"id\" in value)) {\n return undefined\n }\n\n return typeof value.id === \"string\" ? value.id : undefined\n}\n\nfunction normalizePath(path: string | undefined) {\n return withoutTrailingSlash(`/${path ?? \"\"}`.replace(/\\/+/g, \"/\"))\n}\n\nfunction getStringValue(value: unknown, key: \"populatedUrl\" | \"slug\") {\n if (!value || typeof value !== \"object\" || !(key in value)) {\n return undefined\n }\n\n const record = value as Record<\"populatedUrl\" | \"slug\", unknown>\n return typeof record[key] === \"string\" ? record[key] : undefined\n}\n\nfunction isDraftDoc(doc: UrlDoc) {\n return doc._status === \"draft\"\n}\n\nfunction getRecord(value: unknown) {\n return value && typeof value === \"object\" && !Array.isArray(value)\n ? (value as Record<string, unknown>)\n : {}\n}\n\nfunction dedupeSources<T extends UrlUpdateSource>(sources: T[]) {\n const seen = new Set<string>()\n\n return sources.filter((source) => {\n const key = sourceKey(source)\n if (seen.has(key)) {\n return false\n }\n seen.add(key)\n return true\n })\n}\n\nfunction sourceKey(source: UrlUpdateSource) {\n switch (source.type) {\n case \"category\":\n case \"collection\":\n case \"page\":\n return `${source.type}:${source.collection}:${source.id ?? \"\"}`\n case \"rootPages\":\n return `rootPages:${JSON.stringify(source.current)}:${JSON.stringify(source.previous)}`\n }\n}\n\nfunction withoutUndefinedValues<T extends object>(value: Partial<T>) {\n return Object.fromEntries(\n Object.entries(value).filter(([, entry]) => entry !== undefined),\n ) as Partial<T>\n}\n\nexport {\n getBreadcrumbsUrl,\n getRecord,\n dedupeSources,\n isDraftDoc,\n getStringValue,\n normalizePath,\n getRelationId,\n getDocumentId,\n withoutPopulatedUrl,\n mergeDoc,\n withoutTrailingSlash,\n}\n","import { getRecord } from \"./utils\"\n\nimport type { PayloadPluginUrlsOptions } from \"./types\"\nimport type { Field } from \"payload\"\n\nexport function populatedUrlField(options: PayloadPluginUrlsOptions = { collections: {} }): Field {\n const fieldName = options.field?.name ?? \"populatedUrl\"\n\n return {\n name: fieldName,\n type: \"text\",\n label: false,\n localized: true,\n ...(options.field?.overrides ?? {}),\n admin: {\n hidden: true,\n ...getRecord(options.field?.overrides?.admin),\n },\n } as Field\n}\n","import type {\n PayloadPluginConfig,\n PayloadPluginUrlsOptions,\n RootPageFieldOptions,\n UrlCollectionOptions,\n} from \"./types\"\n\nexport type NormalizedPayloadPluginUrlsOptions = PayloadPluginUrlsOptions & {\n collections: Record<string, UrlCollectionOptions>\n locales: {\n defaultLocale: string\n locales: string[]\n }\n rootPages: {\n slug: string\n label?: unknown\n fields: Record<string, RootPageFieldOptions>\n }\n}\n\nexport function normalizeOptions(\n options: PayloadPluginUrlsOptions,\n config?: PayloadPluginConfig,\n): NormalizedPayloadPluginUrlsOptions {\n const configLocales = getConfigLocales(config)\n const fallbackLocales = configLocales ?? { defaultLocale: \"en\", locales: [\"en\"] }\n const locales = {\n ...fallbackLocales,\n ...options.locales,\n }\n\n return {\n ...options,\n field: {\n name: \"populatedUrl\",\n ...options.field,\n },\n locales: {\n defaultLocale: locales.defaultLocale ?? locales.locales[0] ?? \"en\",\n locales: locales.locales.length ? locales.locales : [locales.defaultLocale ?? \"en\"],\n },\n rootPages: {\n slug: \"root-pages\",\n ...options.rootPages,\n fields: options.rootPages?.fields ?? {\n indexPage: {\n isHomepage: true,\n relationTo: \"pages\",\n },\n },\n },\n }\n}\n\nexport function getCollectionOptions(options: PayloadPluginUrlsOptions, collection: string) {\n return options.collections[collection]\n}\n\nexport function getCollectionEntries(options: PayloadPluginUrlsOptions) {\n return Object.entries(options.collections)\n}\n\nexport function getCollectionsForCategory(\n options: PayloadPluginUrlsOptions,\n categoryCollection: string,\n) {\n return getCollectionEntries(options)\n .filter(\n ([, collectionOptions]) => collectionOptions.category?.collection === categoryCollection,\n )\n .map(([collection]) => collection)\n}\n\nexport function getRootPageFieldNames(options: PayloadPluginUrlsOptions) {\n const normalizedOptions = normalizeOptions(options)\n return Object.keys(normalizedOptions.rootPages.fields)\n}\n\nexport function getHomepageRootPageField(options: PayloadPluginUrlsOptions) {\n const fields = normalizeOptions(options).rootPages.fields\n const homepageEntry =\n Object.entries(fields).find(([, field]) => field.isHomepage) ??\n Object.entries(fields).find(([fieldName]) => fieldName === \"indexPage\")\n\n return homepageEntry?.[0] ?? Object.keys(fields)[0] ?? \"indexPage\"\n}\n\nexport function getRootPageFieldOptions(options: PayloadPluginUrlsOptions, fieldName: string) {\n return normalizeOptions(options).rootPages.fields[fieldName]\n}\n\nfunction getConfigLocales(config: PayloadPluginConfig | undefined) {\n const localization = config?.localization || undefined\n const locales = localization?.locales\n ?.map((locale) => (typeof locale === \"string\" ? locale : locale.code))\n .filter((locale): locale is string => Boolean(locale))\n\n if (!locales?.length) {\n return undefined\n }\n\n return {\n defaultLocale: localization?.defaultLocale ?? locales[0] ?? \"en\",\n locales,\n }\n}\n","import { getCollectionOptions, normalizeOptions } from \"./options\"\nimport { getBreadcrumbsUrl, withoutTrailingSlash } from \"./utils\"\n\nimport type {\n GetDocumentLinkArgs,\n GetDocumentLinkContext,\n Locale,\n PayloadPluginUrlsOptions,\n UrlCollectionOptions,\n UrlDoc,\n UrlPrefixStrategy,\n} from \"./types\"\n\nexport function getDocumentLink(\n reference: GetDocumentLinkArgs,\n { baseUrl, locale, options, urlPrefixStrategy }: GetDocumentLinkContext,\n) {\n if (typeof reference.value === \"string\") {\n throw new Error(\"Reference value is a string\")\n }\n\n if (reference.value.populatedUrl) {\n return withoutTrailingSlash(reference.value.populatedUrl)\n }\n\n const normalizedOptions = normalizeOptions(options)\n const collectionOptions = getCollectionOptions(normalizedOptions, reference.relationTo)\n const routeCollection = collectionOptions?.routeCollection ?? reference.relationTo\n const slugs = getSlugsForCollection(\n collectionOptions,\n reference.value,\n urlPrefixStrategy ?? collectionOptions?.prefixStrategy,\n )\n\n return getDocumentLinkBySlugs(slugs, {\n baseUrl,\n collection: routeCollection,\n locale,\n options: normalizedOptions,\n })\n}\n\nexport function getDocumentLinkBySlugs(\n slugs: string[],\n {\n baseUrl,\n locale,\n options,\n }: {\n baseUrl?: string\n collection: string\n locale: Locale\n options: PayloadPluginUrlsOptions\n },\n) {\n const normalizedOptions = normalizeOptions(options)\n const prefix = baseUrl || (locale === normalizedOptions.locales?.defaultLocale ? \"\" : locale)\n const segments = [...prefix.split(\"/\"), ...slugs].filter(Boolean)\n return withoutTrailingSlash(`/${segments.join(\"/\")}`)\n}\n\nexport function withLocalePrefix(path: string, locale: Locale, options: PayloadPluginUrlsOptions) {\n const defaultLocale = normalizeOptions(options).locales?.defaultLocale\n if (locale === defaultLocale) {\n return withoutTrailingSlash(path)\n }\n return withoutTrailingSlash(`/${locale}${path}`)\n}\n\nfunction getSlugsForCollection(\n collectionOptions: UrlCollectionOptions | undefined,\n doc: UrlDoc,\n strategy?: UrlPrefixStrategy,\n) {\n if (collectionOptions?.category) {\n return strategy === \"rootPage\"\n ? [doc.slug ?? \"\"]\n : [firstRelatedCategoryPath(doc), doc.slug ?? \"\"]\n }\n\n if (collectionOptions?.breadcrumbs) {\n return [getBreadcrumbsUrl(doc.breadcrumbs) || doc.slug || \"\"]\n }\n\n return [doc.slug ?? \"\"]\n}\n\nfunction firstRelatedCategoryPath(doc: UrlDoc) {\n const categories = doc.categories\n if (!Array.isArray(categories) || categories.length === 0) {\n return \"\"\n }\n\n const categoryItems = categories as unknown[]\n const first = categoryItems[0]\n if (!first || typeof first !== \"object\" || typeof first === \"string\") {\n return \"\"\n }\n\n const categoryDoc = first as UrlDoc\n return (\n getBreadcrumbsUrl(categoryDoc.breadcrumbs) ||\n (categoryDoc.slug ?? \"\").replace(/(^\\/)|(\\/$)/g, \"\")\n )\n}\n","import { getDocumentLink, withLocalePrefix } from \"./link\"\nimport {\n getCollectionOptions,\n getHomepageRootPageField,\n getRootPageFieldOptions,\n normalizeOptions,\n} from \"./options\"\nimport {\n getBreadcrumbsUrl,\n getDocumentId,\n mergeDoc,\n normalizePath,\n withoutPopulatedUrl,\n} from \"./utils\"\n\nimport type {\n Locale,\n PayloadLike,\n PayloadPluginUrlsOptions,\n ResolvePopulatedUrlArgs,\n RootPagesDoc,\n UrlCollectionOptions,\n UrlDoc,\n} from \"./types\"\n\nexport async function resolvePopulatedUrl({\n collection,\n data,\n locale,\n options,\n originalDoc,\n payload,\n rootPages,\n}: ResolvePopulatedUrlArgs): Promise<string | undefined> {\n const normalizedOptions = normalizeOptions(options)\n const collectionOptions = getCollectionOptions(normalizedOptions, collection)\n if (!collectionOptions) {\n return undefined\n }\n\n const doc = mergeDoc(data, originalDoc)\n const homepageField = getHomepageRootPageField(normalizedOptions)\n\n if (collectionOptions.breadcrumbs && !collectionOptions.rootPage) {\n const homepage = await getRootPageDoc({\n field: homepageField,\n locale,\n payload,\n rootPages,\n })\n const homepageId = getDocumentId(homepage)\n\n if (doc.id && homepageId === doc.id) {\n return withLocalePrefix(\"/\", locale, normalizedOptions)\n }\n\n const breadcrumbsPath = normalizePath(getBreadcrumbsUrl(doc.breadcrumbs))\n const homepagePath = normalizePath(getBreadcrumbsUrl(homepage?.breadcrumbs))\n const pagePath =\n homepagePath && breadcrumbsPath.startsWith(`${homepagePath}/`)\n ? normalizePath(breadcrumbsPath.slice(homepagePath.length))\n : breadcrumbsPath\n\n return withLocalePrefix(pagePath || `/${doc.slug ?? \"\"}`, locale, normalizedOptions)\n }\n\n const rootPageUrl: string | undefined = await getRootPageUrl({\n collectionOptions,\n locale,\n options: normalizedOptions,\n payload,\n rootPages,\n })\n\n if (collectionOptions.category) {\n const categories = await resolveCategories({\n categories: doc[collectionOptions.category.field ?? \"categories\"],\n collection: collectionOptions.category.collection,\n locale,\n payload,\n })\n\n return getDocumentLink(\n {\n relationTo: collection,\n value: {\n ...withoutPopulatedUrl(doc),\n [collectionOptions.category.field ?? \"categories\"]: categories,\n categories,\n },\n },\n {\n baseUrl: rootPageUrl,\n locale,\n options: normalizedOptions,\n },\n )\n }\n\n return getDocumentLink(\n {\n relationTo: collection,\n value: withoutPopulatedUrl(doc),\n },\n {\n baseUrl: rootPageUrl,\n locale,\n options: normalizedOptions,\n },\n )\n}\n\nasync function getRootPageUrl({\n collectionOptions,\n locale,\n options,\n payload,\n rootPages,\n}: {\n collectionOptions: UrlCollectionOptions\n locale: Locale\n options: PayloadPluginUrlsOptions\n payload?: PayloadLike\n rootPages: RootPagesDoc\n}): Promise<string | undefined> {\n if (!collectionOptions.rootPage) {\n return undefined\n }\n\n const rootPageField = collectionOptions.rootPage\n const rootPageFieldOptions = getRootPageFieldOptions(options, rootPageField)\n const relationTo = rootPageFieldOptions?.relationTo ?? \"pages\"\n const rootPage = await getRootPageDoc({\n collection: relationTo,\n field: rootPageField,\n locale,\n payload,\n rootPages,\n })\n\n if (!rootPage) {\n return undefined\n }\n\n if (typeof rootPage.populatedUrl === \"string\" && rootPage.populatedUrl) {\n return withLocalePrefixIfNeeded(rootPage.populatedUrl, locale, options)\n }\n\n if (relationTo !== \"pages\") {\n return withLocalePrefixIfNeeded(\n getDocumentLink(\n {\n relationTo,\n value: rootPage,\n },\n {\n locale,\n options,\n },\n ),\n locale,\n options,\n )\n }\n\n return resolvePopulatedUrl({\n collection: relationTo,\n data: {},\n locale,\n options,\n originalDoc: rootPage,\n payload,\n rootPages,\n })\n}\n\nfunction withLocalePrefixIfNeeded(path: string, locale: Locale, options: PayloadPluginUrlsOptions) {\n const normalizedOptions = normalizeOptions(options)\n if (\n locale === normalizedOptions.locales.defaultLocale ||\n path === `/${locale}` ||\n path.startsWith(`/${locale}/`)\n ) {\n return path\n }\n\n return withLocalePrefix(path, locale, normalizedOptions)\n}\n\nasync function getRootPageDoc({\n collection = \"pages\",\n field,\n locale,\n payload,\n rootPages,\n}: {\n collection?: string\n field: string\n locale: Locale\n payload?: PayloadLike\n rootPages: RootPagesDoc\n}) {\n const page = rootPages[field]\n\n if (!page) {\n return undefined\n }\n\n if (typeof page !== \"string\") {\n return page\n }\n\n const found = await payload?.findByID?.({\n collection,\n id: page,\n depth: 0,\n locale,\n select: {\n id: true,\n slug: true,\n populatedUrl: true,\n breadcrumbs: true,\n },\n })\n return found as UrlDoc | undefined\n}\n\nasync function resolveCategories({\n categories,\n collection,\n locale,\n payload,\n}: {\n categories: unknown\n collection: string\n locale: Locale\n payload?: PayloadLike\n}) {\n if (!Array.isArray(categories)) {\n return []\n }\n\n return Promise.all(\n categories.map((category) => {\n if (typeof category !== \"string\") {\n return Promise.resolve(category)\n }\n\n return (\n payload?.findByID?.({\n collection,\n id: category,\n depth: 2,\n locale,\n }) ?? Promise.resolve(category)\n )\n }),\n )\n}\n","import {\n getCollectionEntries,\n getCollectionOptions,\n getCollectionsForCategory,\n getHomepageRootPageField,\n getRootPageFieldNames,\n getRootPageFieldOptions,\n normalizeOptions,\n} from \"./options\"\nimport { resolvePopulatedUrl } from \"./resolver\"\nimport { dedupeSources, getRelationId, getStringValue, isDraftDoc } from \"./utils\"\n\nimport type { NormalizedPayloadPluginUrlsOptions } from \"./options\"\n\nimport type {\n Locale,\n PayloadLike,\n PayloadPluginUrlsOptions,\n RootPagesDoc,\n UrlDoc,\n UrlUpdateSource,\n} from \"./types\"\n\nexport function createUpdateUrlsHandler(options: PayloadPluginUrlsOptions) {\n return async ({\n job,\n req,\n }: {\n job: {\n input?: {\n sources?: UrlUpdateSource[] | null\n }\n }\n req: {\n payload: PayloadLike\n }\n }) => {\n const normalizedOptions = normalizeOptions(options)\n const sources = job.input?.sources ?? []\n\n for (const locale of normalizedOptions.locales?.locales ?? []) {\n const rootPages = await req.payload.findGlobal?.({\n slug: normalizedOptions.rootPages?.slug ?? \"root-pages\",\n depth: 2,\n locale,\n })\n if (!rootPages) {\n continue\n }\n\n for (const source of expandSources(sources, normalizedOptions)) {\n switch (source.type) {\n case \"category\":\n await updateCollectionDocuments({\n collection: source.collection,\n locale,\n options: normalizedOptions,\n payload: req.payload,\n rootPages,\n })\n for (const collection of getCollectionsForCategory(\n normalizedOptions,\n source.collection,\n )) {\n await updateCollectionDocuments({\n collection,\n locale,\n options: normalizedOptions,\n payload: req.payload,\n rootPages,\n })\n }\n break\n case \"collection\":\n await updateCollectionDocuments({\n collection: source.collection,\n locale,\n options: normalizedOptions,\n payload: req.payload,\n rootPages,\n })\n break\n case \"page\": {\n await updateCollectionDocuments({\n collection: source.collection,\n locale,\n options: normalizedOptions,\n payload: req.payload,\n rootPages,\n })\n const pageId = source.id == null ? \"\" : String(source.id)\n if (!pageId) {\n break\n }\n const dependentRoots = rootPageDependentEntryPoints(\n getCollectionsUsingRootPageDoc(pageId, rootPages, normalizedOptions),\n normalizedOptions,\n )\n const visited = new Set<string>()\n for (const collection of dependentRoots) {\n await updateCollectionWithCategoryDependents({\n collection,\n locale,\n options: normalizedOptions,\n payload: req.payload,\n rootPages,\n visited,\n })\n }\n break\n }\n case \"rootPages\":\n break\n }\n }\n }\n }\n}\n\nexport function hasUrlPathChanged(doc: unknown, previousDoc: unknown) {\n const docUrl = getStringValue(doc, \"populatedUrl\")\n const previousUrl = getStringValue(previousDoc, \"populatedUrl\")\n\n if (docUrl && previousUrl) {\n return docUrl !== previousUrl\n }\n\n return getStringValue(doc, \"slug\") !== getStringValue(previousDoc, \"slug\")\n}\n\nexport function getRootPageChangeSources(\n current: RootPagesDoc,\n previous: RootPagesDoc | undefined,\n options: PayloadPluginUrlsOptions,\n): UrlUpdateSource[] {\n const normalizedOptions = normalizeOptions(options)\n const sources: UrlUpdateSource[] = []\n const indexPageField = getHomepageRootPageField(normalizedOptions)\n const indexPageCollection =\n getRootPageFieldOptions(normalizedOptions, indexPageField)?.relationTo ?? \"pages\"\n const currentIndexPageId = getRelationId(current[indexPageField])\n const previousIndexPageId = getRelationId(previous?.[indexPageField])\n\n if (currentIndexPageId !== previousIndexPageId) {\n if (currentIndexPageId) {\n sources.push({ type: \"page\", collection: indexPageCollection, id: currentIndexPageId })\n }\n if (previousIndexPageId) {\n sources.push({ type: \"page\", collection: indexPageCollection, id: previousIndexPageId })\n }\n } else if (\n currentIndexPageId &&\n hasUrlPathChanged(current[indexPageField], previous?.[indexPageField])\n ) {\n sources.push({ type: \"page\", collection: indexPageCollection, id: currentIndexPageId })\n }\n\n for (const [collection, collectionOptions] of getCollectionEntries(normalizedOptions)) {\n if (!collectionOptions.rootPage) {\n continue\n }\n\n const currentRootPageId = getRelationId(current[collectionOptions.rootPage])\n const previousRootPageId = getRelationId(previous?.[collectionOptions.rootPage])\n const relationChanged = currentRootPageId !== previousRootPageId\n const sameRelationPathChanged =\n Boolean(currentRootPageId) &&\n currentRootPageId === previousRootPageId &&\n hasUrlPathChanged(\n current[collectionOptions.rootPage],\n previous?.[collectionOptions.rootPage],\n )\n\n if (relationChanged || sameRelationPathChanged) {\n sources.push({ type: \"collection\", collection })\n }\n }\n\n return dedupeSources(sources)\n}\n\nexport function getRootPageSnapshot(\n rootPages: UrlDoc | undefined,\n options: PayloadPluginUrlsOptions,\n) {\n const snapshot: RootPagesDoc = {}\n\n for (const fieldName of getRootPageFieldNames(options)) {\n snapshot[fieldName] = rootPages?.[fieldName] as RootPagesDoc[string]\n }\n\n return snapshot\n}\n\nfunction expandSources(sources: UrlUpdateSource[], options: PayloadPluginUrlsOptions) {\n return sources.flatMap((source) => {\n if (source.type !== \"rootPages\") {\n return [source]\n }\n\n return getRootPageChangeSources(source.current, source.previous, options)\n })\n}\n\nfunction getCollectionsUsingRootPageDoc(\n rootPageDocId: string,\n rootPages: RootPagesDoc,\n options: NormalizedPayloadPluginUrlsOptions,\n): string[] {\n const collections: string[] = []\n for (const [collection, collectionOptions] of getCollectionEntries(options)) {\n const field = collectionOptions.rootPage\n if (!field) {\n continue\n }\n if (getRelationId(rootPages[field]) === rootPageDocId) {\n collections.push(collection)\n }\n }\n return collections\n}\n\nfunction rootPageDependentEntryPoints(\n collections: string[],\n options: NormalizedPayloadPluginUrlsOptions,\n): string[] {\n const set = new Set(collections)\n return collections.filter((collection) => {\n const parent = getCollectionOptions(options, collection)?.category?.collection\n return !parent || !set.has(parent)\n })\n}\n\nasync function updateCollectionWithCategoryDependents({\n collection,\n locale,\n options,\n payload,\n rootPages,\n visited,\n}: {\n collection: string\n locale: Locale\n options: NormalizedPayloadPluginUrlsOptions\n payload: PayloadLike\n rootPages: RootPagesDoc\n visited: Set<string>\n}): Promise<void> {\n if (visited.has(collection)) {\n return\n }\n visited.add(collection)\n\n await updateCollectionDocuments({\n collection,\n locale,\n options,\n payload,\n rootPages,\n })\n\n for (const dependent of getCollectionsForCategory(options, collection)) {\n await updateCollectionWithCategoryDependents({\n collection: dependent,\n locale,\n options,\n payload,\n rootPages,\n visited,\n })\n }\n}\n\nasync function updateCollectionDocuments({\n collection,\n locale,\n options,\n payload,\n rootPages,\n}: {\n collection: string\n locale: Locale\n options: PayloadPluginUrlsOptions\n payload: PayloadLike\n rootPages: RootPagesDoc\n}) {\n let page = 1\n\n for (;;) {\n const result = await payload.find?.({\n collection,\n depth: 2,\n draft: false,\n limit: 100,\n locale,\n overrideAccess: true,\n page,\n pagination: true,\n })\n\n if (!result) {\n return\n }\n\n for (const doc of result.docs) {\n const urlDoc = doc as UrlDoc\n if (!urlDoc.id || isDraftDoc(urlDoc)) {\n continue\n }\n\n const populatedUrlValue = await resolvePopulatedUrl({\n collection,\n data: {},\n locale,\n options,\n originalDoc: urlDoc,\n payload,\n rootPages,\n })\n\n if (!populatedUrlValue || urlDoc.populatedUrl === populatedUrlValue) {\n continue\n }\n\n await payload.update?.({\n collection,\n id: urlDoc.id,\n locale,\n overrideAccess: true,\n data: {\n [options.field?.name ?? \"populatedUrl\"]: populatedUrlValue,\n },\n context: {\n disablePopulateUrl: true,\n disableUrlUpdates: true,\n disableRevalidate: true,\n },\n })\n }\n\n if (!result.nextPage) {\n return\n }\n\n page = result.nextPage\n }\n}\n","import { getCollectionOptions, getCollectionsForCategory, normalizeOptions } from \"./options\"\nimport { resolvePopulatedUrl } from \"./resolver\"\nimport { getRootPageSnapshot, hasUrlPathChanged } from \"./update-urls\"\nimport { isDraftDoc } from \"./utils\"\n\nimport type { PayloadPluginUrlsOptions, RootPagesDoc, UrlDoc, UrlUpdateSource } from \"./types\"\nimport type {\n CollectionAfterChangeHook,\n CollectionBeforeChangeHook,\n GlobalAfterChangeHook,\n Payload,\n PayloadRequest,\n} from \"payload\"\n\nasync function queueUpdateUrlsWorkflow({\n input,\n payload,\n req,\n runImmediately,\n}: {\n input: { sources: UrlUpdateSource[] }\n payload: Payload\n req: PayloadRequest\n runImmediately: boolean\n}) {\n const jobs = payload.jobs\n if (!jobs?.queue) {\n return\n }\n\n const job = await jobs.queue({\n workflow: \"update-urls\",\n input,\n req,\n })\n\n if (!runImmediately || typeof jobs.runByID !== \"function\") {\n return\n }\n\n const id = job && typeof job === \"object\" && \"id\" in job && job.id != null ? job.id : undefined\n if (id === undefined) {\n return\n }\n\n await jobs.runByID({\n id,\n req,\n })\n}\n\nexport function createPopulateUrlHook(\n options: PayloadPluginUrlsOptions,\n): CollectionBeforeChangeHook {\n return async ({ collection, context, data = {}, originalDoc, req }) => {\n const locale = req.locale\n if (\n !locale ||\n locale === \"all\" ||\n context?.disablePopulateUrl ||\n req.context?.disablePopulateUrl\n ) {\n return data\n }\n\n const rootPages = await req.payload.findGlobal?.({\n slug: normalizeOptions(options).rootPages?.slug ?? \"root-pages\",\n depth: 2,\n locale,\n })\n if (!rootPages) {\n return data\n }\n\n const populatedUrlValue = await resolvePopulatedUrl({\n collection: collection?.slug ?? \"\",\n data: data as UrlDoc,\n locale,\n options,\n originalDoc: originalDoc as UrlDoc | undefined,\n payload: req.payload,\n rootPages: rootPages as RootPagesDoc,\n })\n\n if (populatedUrlValue) {\n data[options.field?.name ?? \"populatedUrl\"] = populatedUrlValue\n }\n\n return data\n }\n}\n\nexport function createCollectionUrlUpdateHook(\n options: PayloadPluginUrlsOptions,\n): CollectionAfterChangeHook {\n return async ({ collection, doc, previousDoc, req }) => {\n const urlDoc = doc as UrlDoc | undefined\n const previousUrlDoc = previousDoc as UrlDoc | undefined\n if (\n req.context?.disableUrlUpdates ||\n !urlDoc ||\n isDraftDoc(urlDoc) ||\n !hasUrlPathChanged(urlDoc, previousUrlDoc)\n ) {\n return urlDoc\n }\n\n const collectionOptions = getCollectionOptions(options, collection?.slug ?? \"\")\n if (!collectionOptions) {\n return urlDoc\n }\n\n const collectionSlug = collection?.slug ?? \"\"\n const isCategoryCollection = getCollectionsForCategory(options, collectionSlug).length > 0\n const docId = urlDoc.id == null ? undefined : String(urlDoc.id)\n const source = isCategoryCollection\n ? {\n type: \"category\" as const,\n collection: collectionSlug,\n id: docId,\n }\n : {\n type:\n collectionOptions.breadcrumbs && !collectionOptions.rootPage\n ? (\"page\" as const)\n : (\"collection\" as const),\n collection: collectionSlug,\n id: docId,\n }\n\n await queueUpdateUrlsWorkflow({\n input: { sources: [source] },\n payload: req.payload,\n req,\n runImmediately: normalizeOptions(options).delayJobsRun !== true,\n })\n\n return urlDoc\n }\n}\n\nexport function createRootPagesUrlUpdateHook(\n options: PayloadPluginUrlsOptions,\n): GlobalAfterChangeHook {\n return async ({ doc, previousDoc, req }) => {\n const rootPagesDoc = doc as RootPagesDoc\n const previousRootPagesDoc = previousDoc as RootPagesDoc | undefined\n if (req.context?.disableUrlUpdates) {\n return rootPagesDoc\n }\n\n await queueUpdateUrlsWorkflow({\n input: {\n sources: [\n {\n type: \"rootPages\",\n current: getRootPageSnapshot(rootPagesDoc, options),\n previous: getRootPageSnapshot(previousRootPagesDoc, options),\n },\n ],\n },\n payload: req.payload,\n req,\n runImmediately: normalizeOptions(options).delayJobsRun !== true,\n })\n\n return rootPagesDoc\n }\n}\n","import { populatedUrlField } from \"./field\"\nimport {\n createCollectionUrlUpdateHook,\n createPopulateUrlHook,\n createRootPagesUrlUpdateHook,\n} from \"./hooks\"\nimport {\n getCollectionOptions,\n getRootPageFieldNames,\n getRootPageFieldOptions,\n normalizeOptions,\n} from \"./options\"\nimport { createUpdateUrlsHandler } from \"./update-urls\"\n\nimport type {\n CollectionConfigLike,\n FieldLike,\n GlobalConfigLike,\n PayloadPlugin,\n PayloadPluginUrlsOptions,\n WorkflowLike,\n} from \"./types\"\nimport type { GlobalConfig } from \"payload\"\n\nexport const payloadPluginUrls = (options?: PayloadPluginUrlsOptions): PayloadPlugin => {\n if (!options) {\n return (config) => config\n }\n\n return (config) => {\n const normalizedOptions = normalizeOptions(options, config)\n const collections = (config.collections ?? []).map((collection) =>\n applyUrlCollectionConfig(collection, normalizedOptions),\n )\n\n return {\n ...config,\n collections,\n globals: [...(config.globals ?? []), createRootPagesGlobal(normalizedOptions)],\n jobs: {\n ...(config.jobs ?? {}),\n workflows: [\n ...(config.jobs?.workflows ?? []),\n {\n slug: \"update-urls\",\n handler: createUpdateUrlsHandler(normalizedOptions),\n } as WorkflowLike,\n ],\n },\n } as ReturnType<PayloadPlugin>\n }\n}\n\nfunction applyUrlCollectionConfig(\n collection: CollectionConfigLike,\n options: PayloadPluginUrlsOptions,\n) {\n const collectionOptions = getCollectionOptions(options, collection.slug)\n if (!collectionOptions) {\n return collection\n }\n\n const fieldName = options.field?.name ?? \"populatedUrl\"\n const fields = collection.fields.some((field) => \"name\" in field && field.name === fieldName)\n ? collection.fields\n : [...collection.fields, populatedUrlField(options)]\n const hooks = collection.hooks ?? {}\n\n return {\n ...collection,\n defaultPopulate: {\n ...(collection.defaultPopulate ?? {}),\n [fieldName]: true,\n },\n fields,\n hooks: {\n ...hooks,\n beforeChange: [...(hooks.beforeChange ?? []), createPopulateUrlHook(options)],\n afterChange: [...(hooks.afterChange ?? []), createCollectionUrlUpdateHook(options)],\n },\n } as CollectionConfigLike\n}\n\nfunction createRootPagesGlobal(options: PayloadPluginUrlsOptions): GlobalConfigLike {\n const rootPagesOptions = normalizeOptions(options).rootPages\n\n const base = {\n slug: rootPagesOptions?.slug ?? \"root-pages\",\n label: rootPagesOptions?.label ?? \"Root pages\",\n fields: getRootPageFieldNames(options).map((fieldName) =>\n createRootPageField(fieldName, options),\n ),\n hooks: {\n afterChange: [createRootPagesUrlUpdateHook(options)],\n },\n } satisfies GlobalConfigLike\n\n const partial = options.overrides\n return partial ? mergeGlobalConfigOverride(base, partial) : base\n}\n\nfunction createRootPageField(fieldName: string, options: PayloadPluginUrlsOptions): FieldLike {\n const fieldOptions = getRootPageFieldOptions(options, fieldName)\n const overrides = (fieldOptions?.overrides ?? {}) as Record<string, unknown>\n const {\n name: _name,\n type: _type,\n hasMany: _hasMany,\n relationTo: _relationTo,\n ...override\n } = overrides\n\n return {\n name: fieldName,\n type: \"relationship\",\n relationTo: fieldOptions?.relationTo ?? \"pages\",\n hasMany: false,\n admin: {\n width: \"50%\",\n },\n ...override,\n } as FieldLike\n}\n\nfunction unknownArrayFrom(value: unknown): unknown[] {\n if (!Array.isArray(value)) {\n return []\n }\n const out: unknown[] = []\n for (const item of value) {\n out.push(item)\n }\n return out\n}\n\nfunction mergeHooks<H extends Record<string, unknown> | undefined>(base: H, extra: H): H {\n if (!extra) {\n return base\n }\n if (!base) {\n return extra\n }\n const a = base\n const b = extra\n const out = { ...a }\n for (const key of Object.keys(b)) {\n const av = a[key]\n const bv = b[key]\n if (Array.isArray(av) || Array.isArray(bv)) {\n out[key] = [...unknownArrayFrom(av), ...unknownArrayFrom(bv)]\n } else if (bv !== undefined) {\n out[key] = bv\n }\n }\n return out as H\n}\n\nfunction mergeRecord(\n base: Record<string, unknown> | undefined,\n extra: Record<string, unknown> | undefined,\n): Record<string, unknown> | undefined {\n if (!extra) {\n return base\n }\n if (!base) {\n return extra\n }\n return { ...base, ...extra }\n}\n\nfunction mergeGlobalConfigOverride(\n global: GlobalConfigLike,\n override: Partial<GlobalConfig>,\n): GlobalConfigLike {\n const { hooks: oHooks, access: oAccess, admin: oAdmin, fields: _fields, ...rest } = override\n\n const merged: GlobalConfigLike = {\n ...global,\n ...rest,\n }\n\n if (oAccess) {\n merged.access = mergeRecord(\n global.access as Record<string, unknown> | undefined,\n oAccess as Record<string, unknown>,\n ) as GlobalConfig[\"access\"]\n }\n\n if (oAdmin) {\n merged.admin = mergeRecord(\n global.admin as Record<string, unknown> | undefined,\n oAdmin as Record<string, unknown>,\n ) as GlobalConfig[\"admin\"]\n }\n\n if (oHooks || global.hooks) {\n merged.hooks = mergeHooks(global.hooks, oHooks)\n }\n\n return merged\n}\n"],"mappings":"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","names":["index_exports","__export","payloadPluginUrls","getBreadcrumbsUrl","getDocumentLink","getDocumentLinkBySlugs","getRootPageChangeSources","hasUrlPathChanged","populatedUrlField","resolvePopulatedUrl","withLocalePrefix","withoutTrailingSlash","__toCommonJS","withoutTrailingSlash","path","getBreadcrumbsUrl","breadcrumbs","mergeDoc","data","originalDoc","withoutUndefinedValues","withoutPopulatedUrl","doc","_populatedUrl","rest","getDocumentId","getRelationId","value","normalizePath","getStringValue","key","record","isDraftDoc","getRecord","dedupeSources","sources","seen","source","sourceKey","entry","populatedUrlField","options","getRecord","normalizeOptions","options","config","locales","getConfigLocales","getCollectionOptions","collection","getCollectionEntries","getCollectionsForCategory","categoryCollection","collectionOptions","getRootPageFieldNames","normalizedOptions","getHomepageRootPageField","fields","field","fieldName","getRootPageFieldOptions","localization","locale","getDocumentLink","reference","baseUrl","locale","options","urlPrefixStrategy","withoutTrailingSlash","normalizedOptions","normalizeOptions","collectionOptions","getCollectionOptions","routeCollection","slugs","getSlugsForCollection","getDocumentLinkBySlugs","segments","withLocalePrefix","path","defaultLocale","doc","strategy","firstRelatedCategoryPath","getBreadcrumbsUrl","categories","first","categoryDoc","resolvePopulatedUrl","collection","data","locale","options","originalDoc","payload","rootPages","normalizedOptions","normalizeOptions","collectionOptions","getCollectionOptions","doc","mergeDoc","homepageField","getHomepageRootPageField","homepage","getRootPageDoc","homepageId","getDocumentId","withLocalePrefix","breadcrumbsPath","normalizePath","getBreadcrumbsUrl","homepagePath","pagePath","rootPageUrl","getRootPageUrl","categories","resolveCategories","getDocumentLink","withoutPopulatedUrl","rootPageField","relationTo","getRootPageFieldOptions","rootPage","withLocalePrefixIfNeeded","path","field","page","category","createUpdateUrlsHandler","options","job","req","normalizedOptions","normalizeOptions","sources","locale","rootPages","source","expandSources","updateCollectionDocuments","collection","getCollectionsForCategory","pageId","dependentRoots","rootPageDependentEntryPoints","getCollectionsUsingRootPageDoc","visited","updateCollectionWithCategoryDependents","hasUrlPathChanged","doc","previousDoc","docUrl","getStringValue","previousUrl","getRootPageChangeSources","current","previous","indexPageField","getHomepageRootPageField","indexPageCollection","getRootPageFieldOptions","currentIndexPageId","getRelationId","previousIndexPageId","collectionOptions","getCollectionEntries","currentRootPageId","previousRootPageId","relationChanged","sameRelationPathChanged","dedupeSources","getRootPageSnapshot","snapshot","fieldName","getRootPageFieldNames","rootPageDocId","collections","field","set","parent","getCollectionOptions","payload","dependent","page","result","urlDoc","isDraftDoc","populatedUrlValue","resolvePopulatedUrl","queueUpdateUrlsWorkflow","input","payload","req","runImmediately","jobs","job","id","createPopulateUrlHook","options","collection","context","data","originalDoc","locale","rootPages","normalizeOptions","populatedUrlValue","resolvePopulatedUrl","createCollectionUrlUpdateHook","doc","previousDoc","urlDoc","previousUrlDoc","isDraftDoc","hasUrlPathChanged","collectionOptions","getCollectionOptions","collectionSlug","isCategoryCollection","getCollectionsForCategory","docId","source","createRootPagesUrlUpdateHook","rootPagesDoc","previousRootPagesDoc","getRootPageSnapshot","payloadPluginUrls","options","config","normalizedOptions","normalizeOptions","collections","collection","applyUrlCollectionConfig","createRootPagesGlobal","createUpdateUrlsHandler","getCollectionOptions","fieldName","fields","field","populatedUrlField","hooks","createPopulateUrlHook","createCollectionUrlUpdateHook","rootPagesOptions","base","getRootPageFieldNames","createRootPageField","createRootPagesUrlUpdateHook","partial","mergeGlobalConfigOverride","fieldOptions","getRootPageFieldOptions","overrides","_name","_type","_hasMany","_relationTo","override","unknownArrayFrom","value","out","item","mergeHooks","extra","a","b","key","av","bv","mergeRecord","global","oHooks","oAccess","oAdmin","_fields","rest","merged"]}
package/dist/index.js CHANGED
@@ -1,2 +1,2 @@
1
- var f=o=>o.replace(/\/$/,"").replace(/^\/?/,"/");function P(o){return(o?.at(-1)?.url??"").replace(/(^\/)|(\/$)/g,"")}function v(o,e){return{...e||{},...oo(o)}}function S(o){let{populatedUrl:e,...t}=o;return t}function z(o){if(!(!o||typeof o!="object"||!("id"in o)))return typeof o.id=="string"?o.id:void 0}function U(o){if(typeof o=="string")return o;if(!(!o||typeof o!="object"||!("id"in o)))return typeof o.id=="string"?o.id:void 0}function h(o){return f(`/${o??""}`.replace(/\/+/g,"/"))}function k(o,e){if(!o||typeof o!="object"||!(e in o))return;let t=o;return typeof t[e]=="string"?t[e]:void 0}function w(o){return o._status==="draft"}function I(o){return o&&typeof o=="object"&&!Array.isArray(o)?o:{}}function $(o){let e=new Set;return o.filter(t=>{let n=q(t);return e.has(n)?!1:(e.add(n),!0)})}function q(o){switch(o.type){case"category":case"collection":case"page":return`${o.type}:${o.collection}:${o.id??""}`;case"rootPages":return`rootPages:${JSON.stringify(o.current)}:${JSON.stringify(o.previous)}`}}function oo(o){return Object.fromEntries(Object.entries(o).filter(([,e])=>e!==void 0))}function A(o={collections:{}}){return{name:o.field?.name??"populatedUrl",type:"text",label:!1,localized:!0,...o.field?.overrides??{},admin:{hidden:!0,...I(o.field?.overrides?.admin)}}}function c(o,e){let r={...eo(e)??{defaultLocale:"en",locales:["en"]},...o.locales};return{...o,field:{name:"populatedUrl",...o.field},locales:{defaultLocale:r.defaultLocale??r.locales[0]??"en",locales:r.locales.length?r.locales:[r.defaultLocale??"en"]},rootPages:{slug:"root-pages",...o.rootPages,fields:o.rootPages?.fields??{indexPage:{isHomepage:!0,relationTo:"pages"}}}}}function d(o,e){return o.collections[e]}function H(o){return Object.entries(o.collections)}function L(o,e){return H(o).filter(([,t])=>t.category?.collection===e).map(([t])=>t)}function R(o){let e=c(o);return Object.keys(e.rootPages.fields)}function D(o){let e=c(o).rootPages.fields;return(Object.entries(e).find(([,n])=>n.isHomepage)??Object.entries(e).find(([n])=>n==="indexPage"))?.[0]??Object.keys(e)[0]??"indexPage"}function y(o,e){return c(o).rootPages.fields[e]}function eo(o){let e=o?.localization||void 0,t=e?.locales?.map(n=>typeof n=="string"?n:n.code).filter(n=>!!n);if(t?.length)return{defaultLocale:e?.defaultLocale??t[0]??"en",locales:t}}function O(o,{baseUrl:e,locale:t,options:n,urlPrefixStrategy:r}){if(typeof o.value=="string")throw new Error("Reference value is a string");if(o.value.populatedUrl)return f(o.value.populatedUrl);let l=c(n),a=d(l,o.relationTo),i=a?.routeCollection??o.relationTo,s=to(a,o.value,r??a?.prefixStrategy);return B(s,{baseUrl:e,collection:i,locale:t,options:l})}function B(o,{baseUrl:e,locale:t,options:n}){let r=c(n),a=[...(e||(t===r.locales?.defaultLocale?"":t)).split("/"),...o].filter(Boolean);return f(`/${a.join("/")}`)}function C(o,e,t){let n=c(t).locales?.defaultLocale;return e===n?f(o):f(`/${e}${o}`)}function to(o,e,t){return o?.category?t==="rootPage"?[e.slug??""]:[no(e),e.slug??""]:o?.breadcrumbs?[P(e.breadcrumbs)||e.slug||""]:[e.slug??""]}function no(o){let e=o.categories;if(!Array.isArray(e)||e.length===0)return"";let n=e[0];if(!n||typeof n!="object"||typeof n=="string")return"";let r=n;return P(r.breadcrumbs)||(r.slug??"").replace(/(^\/)|(\/$)/g,"")}async function m({collection:o,data:e,locale:t,options:n,originalDoc:r,payload:l,rootPages:a}){let i=c(n),s=d(i,o);if(!s)return;let u=v(e,r),g=D(i);if(s.breadcrumbs&&!s.rootPage){let p=await _({field:g,locale:t,payload:l,rootPages:a}),Y=z(p);if(u.id&&Y===u.id)return C("/",t,i);let x=h(P(u.breadcrumbs)),F=h(P(p?.breadcrumbs)),Z=F&&x.startsWith(`${F}/`)?h(x.slice(F.length)):x;return C(Z||`/${u.slug??""}`,t,i)}let b=await ro({collectionOptions:s,locale:t,options:i,payload:l,rootPages:a});if(s.category){let p=await lo({categories:u[s.category.field??"categories"],collection:s.category.collection,locale:t,payload:l});return O({relationTo:o,value:{...S(u),[s.category.field??"categories"]:p,categories:p}},{baseUrl:b,locale:t,options:i})}return O({relationTo:o,value:S(u)},{baseUrl:b,locale:t,options:i})}async function ro({collectionOptions:o,locale:e,options:t,payload:n,rootPages:r}){if(!o.rootPage)return;let l=o.rootPage,i=y(t,l)?.relationTo??"pages",s=await _({collection:i,field:l,locale:e,payload:n,rootPages:r});if(s)return typeof s.populatedUrl=="string"&&s.populatedUrl?N(s.populatedUrl,e,t):i!=="pages"?N(O({relationTo:i,value:s},{locale:e,options:t}),e,t):m({collection:i,data:{},locale:e,options:t,originalDoc:s,payload:n,rootPages:r})}function N(o,e,t){let n=c(t);return e===n.locales.defaultLocale||o===`/${e}`||o.startsWith(`/${e}/`)?o:C(o,e,n)}async function _({collection:o="pages",field:e,locale:t,payload:n,rootPages:r}){let l=r[e];return l?typeof l!="string"?l:await n?.findByID?.({collection:o,id:l,depth:0,locale:t,select:{id:!0,slug:!0,populatedUrl:!0,breadcrumbs:!0}}):void 0}async function lo({categories:o,collection:e,locale:t,payload:n}){return Array.isArray(o)?Promise.all(o.map(r=>typeof r!="string"?Promise.resolve(r):n?.findByID?.({collection:e,id:r,depth:2,locale:t})??Promise.resolve(r))):[]}function E(o){return async({job:e,req:t})=>{let n=c(o),r=e.input?.sources??[];for(let l of n.locales?.locales??[]){let a=await t.payload.findGlobal?.({slug:n.rootPages?.slug??"root-pages",depth:2,locale:l});if(a)for(let i of io(r,n))switch(i.type){case"category":await T({collection:i.collection,locale:l,options:n,payload:t.payload,rootPages:a});for(let s of L(n,i.collection))await T({collection:s,locale:l,options:n,payload:t.payload,rootPages:a});break;case"collection":case"page":await T({collection:i.collection,locale:l,options:n,payload:t.payload,rootPages:a});break;case"rootPages":break}}}}function j(o,e){let t=k(o,"populatedUrl"),n=k(e,"populatedUrl");return t&&n?t!==n:k(o,"slug")!==k(e,"slug")}function V(o,e,t){let n=c(t),r=[],l=D(n),a=y(n,l)?.relationTo??"pages",i=U(o[l]),s=U(e?.[l]);i!==s&&(i&&r.push({type:"page",collection:a,id:i}),s&&r.push({type:"page",collection:a,id:s}));for(let[u,g]of H(n)){if(!g.rootPage)continue;let b=U(o[g.rootPage]),p=U(e?.[g.rootPage]);b!==p&&r.push({type:"collection",collection:u})}return $(r)}function G(o,e){let t={};for(let n of R(e))t[n]=o?.[n];return t}function io(o,e){return o.flatMap(t=>t.type!=="rootPages"?[t]:V(t.current,t.previous,e))}async function T({collection:o,locale:e,options:t,payload:n,rootPages:r}){let l=1;for(;;){let a=await n.find?.({collection:o,depth:2,draft:!1,limit:100,locale:e,overrideAccess:!0,page:l,pagination:!0});if(!a)return;for(let i of a.docs){let s=i;if(!s.id||w(s))continue;let u=await m({collection:o,data:{},locale:e,options:t,originalDoc:s,payload:n,rootPages:r});!u||s.populatedUrl===u||await n.update?.({collection:o,id:s.id,locale:e,overrideAccess:!0,data:{[t.field?.name??"populatedUrl"]:u},context:{disablePopulateUrl:!0,disableUrlUpdates:!0}})}if(!a.nextPage)return;l=a.nextPage}}function W(o){return async({collection:e,context:t,data:n={},originalDoc:r,req:l})=>{let a=l.locale;if(!a||a==="all"||t?.disablePopulateUrl||l.context?.disablePopulateUrl)return n;let i=await l.payload.findGlobal?.({slug:c(o).rootPages?.slug??"root-pages",depth:2,locale:a});if(!i)return n;let s=await m({collection:e?.slug??"",data:n,locale:a,options:o,originalDoc:r,payload:l.payload,rootPages:i});return s&&(n[o.field?.name??"populatedUrl"]=s),n}}function M(o){return async({collection:e,doc:t,previousDoc:n,req:r})=>{let l=t,a=n;if(r.context?.disableUrlUpdates||!l||w(l)||!j(l,a))return l;let i=d(o,e?.slug??"");if(!i)return l;let s=e?.slug??"",g=L(o,s).length>0?{type:"category",collection:s,id:l.id}:{type:i.breadcrumbs&&!i.rootPage?"page":"collection",collection:s,id:l.id};return await r.payload.jobs?.queue?.({workflow:"update-urls",input:{sources:[g]}}),l}}function J(o){return async({doc:e,previousDoc:t,req:n})=>{let r=e,l=t;return n.context?.disableUrlUpdates||await n.payload.jobs?.queue?.({workflow:"update-urls",input:{sources:[{type:"rootPages",current:G(r,o),previous:G(l,o)}]}}),r}}var X=o=>o?e=>{let t=c(o,e),n=(e.collections??[]).map(r=>ao(r,t));return{...e,collections:n,globals:[...e.globals??[],so(t)],jobs:{...e.jobs??{},workflows:[...e.jobs?.workflows??[],{slug:"update-urls",handler:E(t)}]}}}:e=>e;function ao(o,e){if(!d(e,o.slug))return o;let n=e.field?.name??"populatedUrl",r=o.fields.some(a=>"name"in a&&a.name===n)?o.fields:[...o.fields,A(e)],l=o.hooks??{};return{...o,defaultPopulate:{...o.defaultPopulate??{},[n]:!0},fields:r,hooks:{...l,beforeChange:[...l.beforeChange??[],W(e)],afterChange:[...l.afterChange??[],M(e)]}}}function so(o){let e=c(o).rootPages,t={slug:e?.slug??"root-pages",label:e?.label??"Root pages",fields:R(o).map(r=>co(r,o)),hooks:{afterChange:[J(o)]}},n=o.overrides;return n?go(t,n):t}function co(o,e){let t=y(e,o),n=t?.overrides??{},{name:r,type:l,hasMany:a,relationTo:i,...s}=n;return{name:o,type:"relationship",relationTo:t?.relationTo??"pages",hasMany:!1,admin:{width:"50%"},...s}}function K(o){if(!Array.isArray(o))return[];let e=[];for(let t of o)e.push(t);return e}function uo(o,e){if(!e)return o;if(!o)return e;let t=o,n=e,r={...t};for(let l of Object.keys(n)){let a=t[l],i=n[l];Array.isArray(a)||Array.isArray(i)?r[l]=[...K(a),...K(i)]:i!==void 0&&(r[l]=i)}return r}function Q(o,e){return e?o?{...o,...e}:e:o}function go(o,e){let{hooks:t,access:n,admin:r,fields:l,...a}=e,i={...o,...a};return n&&(i.access=Q(o.access,n)),r&&(i.admin=Q(o.admin,r)),(t||o.hooks)&&(i.hooks=uo(o.hooks,t)),i}export{X as default,P as getBreadcrumbsUrl,O as getDocumentLink,B as getDocumentLinkBySlugs,V as getRootPageChangeSources,j as hasUrlPathChanged,X as payloadPluginUrls,A as populatedUrlField,m as resolvePopulatedUrl,C as withLocalePrefix,f as withoutTrailingSlash};
1
+ import{a as q,b as O,c as z,d as S,e as B,f as P,g as D,h as k,i as L,j as T,k as N,l as d,m as f,n as A,o as h,p as x,q as v,r as y,s as C,t as oo,u as R}from"./chunk-OKNQKSNQ.js";function G(o={collections:{}}){return{name:o.field?.name??"populatedUrl",type:"text",label:!1,localized:!0,...o.field?.overrides??{},admin:{hidden:!0,...T(o.field?.overrides?.admin)}}}async function m({collection:o,data:e,locale:t,options:n,originalDoc:a,payload:r,rootPages:l}){let i=d(n),s=f(i,o);if(!s)return;let c=z(e,a),u=v(i);if(s.breadcrumbs&&!s.rootPage){let g=await W({field:u,locale:t,payload:r,rootPages:l}),F=B(g);if(c.id&&F===c.id)return R("/",t,i);let U=D(O(c.breadcrumbs)),H=D(O(g?.breadcrumbs)),Z=H&&U.startsWith(`${H}/`)?D(U.slice(H.length)):U;return R(Z||`/${c.slug??""}`,t,i)}let p=await eo({collectionOptions:s,locale:t,options:i,payload:r,rootPages:l});if(s.category){let g=await to({categories:c[s.category.field??"categories"],collection:s.category.collection,locale:t,payload:r});return C({relationTo:o,value:{...S(c),[s.category.field??"categories"]:g,categories:g}},{baseUrl:p,locale:t,options:i})}return C({relationTo:o,value:S(c)},{baseUrl:p,locale:t,options:i})}async function eo({collectionOptions:o,locale:e,options:t,payload:n,rootPages:a}){if(!o.rootPage)return;let r=o.rootPage,i=y(t,r)?.relationTo??"pages",s=await W({collection:i,field:r,locale:e,payload:n,rootPages:a});if(s)return typeof s.populatedUrl=="string"&&s.populatedUrl?j(s.populatedUrl,e,t):i!=="pages"?j(C({relationTo:i,value:s},{locale:e,options:t}),e,t):m({collection:i,data:{},locale:e,options:t,originalDoc:s,payload:n,rootPages:a})}function j(o,e,t){let n=d(t);return e===n.locales.defaultLocale||o===`/${e}`||o.startsWith(`/${e}/`)?o:R(o,e,n)}async function W({collection:o="pages",field:e,locale:t,payload:n,rootPages:a}){let r=a[e];return r?typeof r!="string"?r:await n?.findByID?.({collection:o,id:r,depth:0,locale:t,select:{id:!0,slug:!0,populatedUrl:!0,breadcrumbs:!0}}):void 0}async function to({categories:o,collection:e,locale:t,payload:n}){return Array.isArray(o)?Promise.all(o.map(a=>typeof a!="string"?Promise.resolve(a):n?.findByID?.({collection:e,id:a,depth:2,locale:t})??Promise.resolve(a))):[]}function _(o){return async({job:e,req:t})=>{let n=d(o),a=e.input?.sources??[];for(let r of n.locales?.locales??[]){let l=await t.payload.findGlobal?.({slug:n.rootPages?.slug??"root-pages",depth:2,locale:r});if(l)for(let i of no(a,n))switch(i.type){case"category":await b({collection:i.collection,locale:r,options:n,payload:t.payload,rootPages:l});for(let s of h(n,i.collection))await b({collection:s,locale:r,options:n,payload:t.payload,rootPages:l});break;case"collection":await b({collection:i.collection,locale:r,options:n,payload:t.payload,rootPages:l});break;case"page":{await b({collection:i.collection,locale:r,options:n,payload:t.payload,rootPages:l});let s=i.id==null?"":String(i.id);if(!s)break;let c=ao(ro(s,l,n),n),u=new Set;for(let p of c)await $({collection:p,locale:r,options:n,payload:t.payload,rootPages:l,visited:u});break}case"rootPages":break}}}}function w(o,e){let t=k(o,"populatedUrl"),n=k(e,"populatedUrl");return t&&n?t!==n:k(o,"slug")!==k(e,"slug")}function M(o,e,t){let n=d(t),a=[],r=v(n),l=y(n,r)?.relationTo??"pages",i=P(o[r]),s=P(e?.[r]);i!==s?(i&&a.push({type:"page",collection:l,id:i}),s&&a.push({type:"page",collection:l,id:s})):i&&w(o[r],e?.[r])&&a.push({type:"page",collection:l,id:i});for(let[c,u]of A(n)){if(!u.rootPage)continue;let p=P(o[u.rootPage]),g=P(e?.[u.rootPage]),F=p!==g,U=!!p&&p===g&&w(o[u.rootPage],e?.[u.rootPage]);(F||U)&&a.push({type:"collection",collection:c})}return N(a)}function I(o,e){let t={};for(let n of x(e))t[n]=o?.[n];return t}function no(o,e){return o.flatMap(t=>t.type!=="rootPages"?[t]:M(t.current,t.previous,e))}function ro(o,e,t){let n=[];for(let[a,r]of A(t)){let l=r.rootPage;l&&P(e[l])===o&&n.push(a)}return n}function ao(o,e){let t=new Set(o);return o.filter(n=>{let a=f(e,n)?.category?.collection;return!a||!t.has(a)})}async function $({collection:o,locale:e,options:t,payload:n,rootPages:a,visited:r}){if(!r.has(o)){r.add(o),await b({collection:o,locale:e,options:t,payload:n,rootPages:a});for(let l of h(t,o))await $({collection:l,locale:e,options:t,payload:n,rootPages:a,visited:r})}}async function b({collection:o,locale:e,options:t,payload:n,rootPages:a}){let r=1;for(;;){let l=await n.find?.({collection:o,depth:2,draft:!1,limit:100,locale:e,overrideAccess:!0,page:r,pagination:!0});if(!l)return;for(let i of l.docs){let s=i;if(!s.id||L(s))continue;let c=await m({collection:o,data:{},locale:e,options:t,originalDoc:s,payload:n,rootPages:a});!c||s.populatedUrl===c||await n.update?.({collection:o,id:s.id,locale:e,overrideAccess:!0,data:{[t.field?.name??"populatedUrl"]:c},context:{disablePopulateUrl:!0,disableUrlUpdates:!0,disableRevalidate:!0}})}if(!l.nextPage)return;r=l.nextPage}}async function V({input:o,payload:e,req:t,runImmediately:n}){let a=e.jobs;if(!a?.queue)return;let r=await a.queue({workflow:"update-urls",input:o,req:t});if(!n||typeof a.runByID!="function")return;let l=r&&typeof r=="object"&&"id"in r&&r.id!=null?r.id:void 0;l!==void 0&&await a.runByID({id:l,req:t})}function E(o){return async({collection:e,context:t,data:n={},originalDoc:a,req:r})=>{let l=r.locale;if(!l||l==="all"||t?.disablePopulateUrl||r.context?.disablePopulateUrl)return n;let i=await r.payload.findGlobal?.({slug:d(o).rootPages?.slug??"root-pages",depth:2,locale:l});if(!i)return n;let s=await m({collection:e?.slug??"",data:n,locale:l,options:o,originalDoc:a,payload:r.payload,rootPages:i});return s&&(n[o.field?.name??"populatedUrl"]=s),n}}function J(o){return async({collection:e,doc:t,previousDoc:n,req:a})=>{let r=t,l=n;if(a.context?.disableUrlUpdates||!r||L(r)||!w(r,l))return r;let i=f(o,e?.slug??"");if(!i)return r;let s=e?.slug??"",c=h(o,s).length>0,u=r.id==null?void 0:String(r.id),p=c?{type:"category",collection:s,id:u}:{type:i.breadcrumbs&&!i.rootPage?"page":"collection",collection:s,id:u};return await V({input:{sources:[p]},payload:a.payload,req:a,runImmediately:d(o).delayJobsRun!==!0}),r}}function K(o){return async({doc:e,previousDoc:t,req:n})=>{let a=e,r=t;return n.context?.disableUrlUpdates||await V({input:{sources:[{type:"rootPages",current:I(a,o),previous:I(r,o)}]},payload:n.payload,req:n,runImmediately:d(o).delayJobsRun!==!0}),a}}var Y=o=>o?e=>{let t=d(o,e),n=(e.collections??[]).map(a=>io(a,t));return{...e,collections:n,globals:[...e.globals??[],lo(t)],jobs:{...e.jobs??{},workflows:[...e.jobs?.workflows??[],{slug:"update-urls",handler:_(t)}]}}}:e=>e;function io(o,e){if(!f(e,o.slug))return o;let n=e.field?.name??"populatedUrl",a=o.fields.some(l=>"name"in l&&l.name===n)?o.fields:[...o.fields,G(e)],r=o.hooks??{};return{...o,defaultPopulate:{...o.defaultPopulate??{},[n]:!0},fields:a,hooks:{...r,beforeChange:[...r.beforeChange??[],E(e)],afterChange:[...r.afterChange??[],J(e)]}}}function lo(o){let e=d(o).rootPages,t={slug:e?.slug??"root-pages",label:e?.label??"Root pages",fields:x(o).map(a=>so(a,o)),hooks:{afterChange:[K(o)]}},n=o.overrides;return n?uo(t,n):t}function so(o,e){let t=y(e,o),n=t?.overrides??{},{name:a,type:r,hasMany:l,relationTo:i,...s}=n;return{name:o,type:"relationship",relationTo:t?.relationTo??"pages",hasMany:!1,admin:{width:"50%"},...s}}function Q(o){if(!Array.isArray(o))return[];let e=[];for(let t of o)e.push(t);return e}function co(o,e){if(!e)return o;if(!o)return e;let t=o,n=e,a={...t};for(let r of Object.keys(n)){let l=t[r],i=n[r];Array.isArray(l)||Array.isArray(i)?a[r]=[...Q(l),...Q(i)]:i!==void 0&&(a[r]=i)}return a}function X(o,e){return e?o?{...o,...e}:e:o}function uo(o,e){let{hooks:t,access:n,admin:a,fields:r,...l}=e,i={...o,...l};return n&&(i.access=X(o.access,n)),a&&(i.admin=X(o.admin,a)),(t||o.hooks)&&(i.hooks=co(o.hooks,t)),i}export{Y as default,O as getBreadcrumbsUrl,C as getDocumentLink,oo as getDocumentLinkBySlugs,M as getRootPageChangeSources,w as hasUrlPathChanged,Y as payloadPluginUrls,G as populatedUrlField,m as resolvePopulatedUrl,R as withLocalePrefix,q as withoutTrailingSlash};
2
2
  //# sourceMappingURL=index.js.map