added /dist

This commit is contained in:
2026-08-03 12:24:28 +02:00
parent dd97bb67fe
commit 05150e7ece
490 changed files with 6667 additions and 0 deletions
+11
View File
@@ -0,0 +1,11 @@
export { Analytics } from '../modules/analytics/client.js';
/**
* Entry point: ipal-kit/client
*
* Client-side ('use client') exports — React hooks, providers, and UI
* components. Kept separate from the main entry so server bundles don't pull in
* client-only code.
*/ export { ConsentProvider, CookieBanner, CookieButton, useConsent, useConsentContext } from '../modules/consent/client.js';
export { Turnstile } from '../modules/turnstile/client.js';
//# sourceMappingURL=client.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["client.d.ts"],"sourcesContent":["export { Analytics } from '../modules/analytics/client.js';\n/**\n * Entry point: ipal-kit/client\n *\n * Client-side ('use client') exports — React hooks, providers, and UI\n * components. Kept separate from the main entry so server bundles don't pull in\n * client-only code.\n */\nexport { ConsentProvider, CookieBanner, CookieButton, useConsent, useConsentContext, } from '../modules/consent/client.js';\nexport type { CookieBannerClassNames } from '../modules/consent/client.js';\nexport { Turnstile } from '../modules/turnstile/client.js';\nexport type { TurnstileProps } from '../modules/turnstile/client.js';\n"],"names":["Analytics","ConsentProvider","CookieBanner","CookieButton","useConsent","useConsentContext","Turnstile"],"mappings":"AAAA,SAASA,SAAS,QAAQ,iCAAiC;AAC3D;;;;;;CAMC,GACD,SAASC,eAAe,EAAEC,YAAY,EAAEC,YAAY,EAAEC,UAAU,EAAEC,iBAAiB,QAAS,+BAA+B;AAE3H,SAASC,SAAS,QAAQ,iCAAiC"}
+12
View File
@@ -0,0 +1,12 @@
export { Analytics } from '../modules/analytics/client.js';
/**
* Entry point: ipal-kit/client
*
* Client-side ('use client') exports — React hooks, providers, and UI
* components. Kept separate from the main entry so server bundles don't pull in
* client-only code.
*/
export { ConsentProvider, CookieBanner, CookieButton, useConsent, useConsentContext, } from '../modules/consent/client.js';
export type { CookieBannerClassNames } from '../modules/consent/client.js';
export { Turnstile } from '../modules/turnstile/client.js';
export type { TurnstileProps } from '../modules/turnstile/client.js';
+12
View File
@@ -0,0 +1,12 @@
'use client';
export { Analytics } from '../modules/analytics/client.js';
/**
* Entry point: ipal-kit/client
*
* Client-side ('use client') exports — React hooks, providers, and UI
* components. Kept separate from the main entry so server bundles don't pull in
* client-only code.
*/ export { ConsentProvider, CookieBanner, CookieButton, useConsent, useConsentContext } from '../modules/consent/client.js';
export { Turnstile } from '../modules/turnstile/client.js';
//# sourceMappingURL=client.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../src/exports/client.ts"],"sourcesContent":["'use client'\nexport { Analytics } from '../modules/analytics/client.js'\n/**\n * Entry point: ipal-kit/client\n *\n * Client-side ('use client') exports — React hooks, providers, and UI\n * components. Kept separate from the main entry so server bundles don't pull in\n * client-only code.\n */\nexport {\n ConsentProvider,\n CookieBanner,\n CookieButton,\n useConsent,\n useConsentContext,\n} from '../modules/consent/client.js'\nexport type { CookieBannerClassNames } from '../modules/consent/client.js'\nexport { Turnstile } from '../modules/turnstile/client.js'\nexport type { TurnstileProps } from '../modules/turnstile/client.js'\n"],"names":["Analytics","ConsentProvider","CookieBanner","CookieButton","useConsent","useConsentContext","Turnstile"],"mappings":"AAAA;AACA,SAASA,SAAS,QAAQ,iCAAgC;AAC1D;;;;;;CAMC,GACD,SACEC,eAAe,EACfC,YAAY,EACZC,YAAY,EACZC,UAAU,EACVC,iBAAiB,QACZ,+BAA8B;AAErC,SAASC,SAAS,QAAQ,iCAAgC"}
+9
View File
@@ -0,0 +1,9 @@
/**
* Entry point: ipal-kit/next/middleware
*
* Re-exports the locale middleware factory and default matcher for use in a
* client project's middleware.ts. Kept as a thin re-export so the Next-facing
* surface is separate from the main package export.
*/ export { createLocaleMiddleware, DEFAULT_MIDDLEWARE_MATCHER } from '../modules/i18n/index.js';
//# sourceMappingURL=next-middleware.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["next-middleware.d.ts"],"sourcesContent":["/**\n * Entry point: ipal-kit/next/middleware\n *\n * Re-exports the locale middleware factory and default matcher for use in a\n * client project's middleware.ts. Kept as a thin re-export so the Next-facing\n * surface is separate from the main package export.\n */\nexport { createLocaleMiddleware, DEFAULT_MIDDLEWARE_MATCHER } from '../modules/i18n/index.js';\nexport type { LocaleMiddlewareResult } from '../modules/i18n/index.js';\n"],"names":["createLocaleMiddleware","DEFAULT_MIDDLEWARE_MATCHER"],"mappings":"AAAA;;;;;;CAMC,GACD,SAASA,sBAAsB,EAAEC,0BAA0B,QAAQ,2BAA2B"}
+9
View File
@@ -0,0 +1,9 @@
/**
* Entry point: ipal-kit/next/middleware
*
* Re-exports the locale middleware factory and default matcher for use in a
* client project's middleware.ts. Kept as a thin re-export so the Next-facing
* surface is separate from the main package export.
*/
export { createLocaleMiddleware, DEFAULT_MIDDLEWARE_MATCHER } from '../modules/i18n/index.js';
export type { LocaleMiddlewareResult } from '../modules/i18n/index.js';
+9
View File
@@ -0,0 +1,9 @@
/**
* Entry point: ipal-kit/next/middleware
*
* Re-exports the locale middleware factory and default matcher for use in a
* client project's middleware.ts. Kept as a thin re-export so the Next-facing
* surface is separate from the main package export.
*/ export { createLocaleMiddleware, DEFAULT_MIDDLEWARE_MATCHER } from '../modules/i18n/index.js';
//# sourceMappingURL=next-middleware.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../src/exports/next-middleware.ts"],"sourcesContent":["/**\n * Entry point: ipal-kit/next/middleware\n *\n * Re-exports the locale middleware factory and default matcher for use in a\n * client project's middleware.ts. Kept as a thin re-export so the Next-facing\n * surface is separate from the main package export.\n */\nexport { createLocaleMiddleware, DEFAULT_MIDDLEWARE_MATCHER } from '../modules/i18n/index.js'\nexport type { LocaleMiddlewareResult } from '../modules/i18n/index.js'\n"],"names":["createLocaleMiddleware","DEFAULT_MIDDLEWARE_MATCHER"],"mappings":"AAAA;;;;;;CAMC,GACD,SAASA,sBAAsB,EAAEC,0BAA0B,QAAQ,2BAA0B"}
+9
View File
@@ -0,0 +1,9 @@
/**
* Entry point: ipal-kit/rsc
*
* Server-component exports. RenderBlocks is a React Server Component, so it
* lives here rather than in the main package entry to keep React out of the
* server-config bundle.
*/ export { RenderBlocks } from '../modules/blocks/index.js';
//# sourceMappingURL=rsc.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["rsc.d.ts"],"sourcesContent":["/**\n * Entry point: ipal-kit/rsc\n *\n * Server-component exports. RenderBlocks is a React Server Component, so it\n * lives here rather than in the main package entry to keep React out of the\n * server-config bundle.\n */\nexport { RenderBlocks } from '../modules/blocks/index.js';\nexport type { BlockComponentMap, BlockData, EnhanceProps, RenderBlocksProps, } from '../modules/blocks/index.js';\n"],"names":["RenderBlocks"],"mappings":"AAAA;;;;;;CAMC,GACD,SAASA,YAAY,QAAQ,6BAA6B"}
+9
View File
@@ -0,0 +1,9 @@
/**
* Entry point: ipal-kit/rsc
*
* Server-component exports. RenderBlocks is a React Server Component, so it
* lives here rather than in the main package entry to keep React out of the
* server-config bundle.
*/
export { RenderBlocks } from '../modules/blocks/index.js';
export type { BlockComponentMap, BlockData, EnhanceProps, RenderBlocksProps, } from '../modules/blocks/index.js';
+9
View File
@@ -0,0 +1,9 @@
/**
* Entry point: ipal-kit/rsc
*
* Server-component exports. RenderBlocks is a React Server Component, so it
* lives here rather than in the main package entry to keep React out of the
* server-config bundle.
*/ export { RenderBlocks } from '../modules/blocks/index.js';
//# sourceMappingURL=rsc.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../src/exports/rsc.ts"],"sourcesContent":["/**\n * Entry point: ipal-kit/rsc\n *\n * Server-component exports. RenderBlocks is a React Server Component, so it\n * lives here rather than in the main package entry to keep React out of the\n * server-config bundle.\n */\nexport { RenderBlocks } from '../modules/blocks/index.js'\nexport type {\n BlockComponentMap,\n BlockData,\n EnhanceProps,\n RenderBlocksProps,\n} from '../modules/blocks/index.js'\n"],"names":["RenderBlocks"],"mappings":"AAAA;;;;;;CAMC,GACD,SAASA,YAAY,QAAQ,6BAA4B"}
+16
View File
@@ -0,0 +1,16 @@
/**
* Entry point: ipal-kit/server
*
* Server-only runtime functions — these import 'server-only' (Turnstile secret,
* SMTP password, nodemailer). Kept OUT of the main entry so that loading the
* Payload config or running `payload generate:importmap` (both Node scripts,
* no bundler) never pulls in 'server-only', which throws outside a bundled
* server context.
*
* Import these only from Server Actions, route handlers, or server components —
* never from the Payload config or client code.
*/ export { verifyTurnstile } from '../modules/turnstile/index.js';
export { sendEmail } from '../modules/email/index.js';
export { submitForm } from '../modules/forms/index.js';
//# sourceMappingURL=server.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["server.d.ts"],"sourcesContent":["/**\n * Entry point: ipal-kit/server\n *\n * Server-only runtime functions — these import 'server-only' (Turnstile secret,\n * SMTP password, nodemailer). Kept OUT of the main entry so that loading the\n * Payload config or running `payload generate:importmap` (both Node scripts,\n * no bundler) never pulls in 'server-only', which throws outside a bundled\n * server context.\n *\n * Import these only from Server Actions, route handlers, or server components —\n * never from the Payload config or client code.\n */\nexport { verifyTurnstile } from '../modules/turnstile/index.js';\nexport { sendEmail } from '../modules/email/index.js';\nexport type { SendEmailArgs, SendEmailResult } from '../modules/email/index.js';\nexport { submitForm } from '../modules/forms/index.js';\nexport type { SubmitFormArgs, SubmitFormResult } from '../modules/forms/index.js';\n"],"names":["verifyTurnstile","sendEmail","submitForm"],"mappings":"AAAA;;;;;;;;;;;CAWC,GACD,SAASA,eAAe,QAAQ,gCAAgC;AAChE,SAASC,SAAS,QAAQ,4BAA4B;AAEtD,SAASC,UAAU,QAAQ,4BAA4B"}
+17
View File
@@ -0,0 +1,17 @@
/**
* Entry point: ipal-kit/server
*
* Server-only runtime functions — these import 'server-only' (Turnstile secret,
* SMTP password, nodemailer). Kept OUT of the main entry so that loading the
* Payload config or running `payload generate:importmap` (both Node scripts,
* no bundler) never pulls in 'server-only', which throws outside a bundled
* server context.
*
* Import these only from Server Actions, route handlers, or server components —
* never from the Payload config or client code.
*/
export { verifyTurnstile } from '../modules/turnstile/index.js';
export { sendEmail } from '../modules/email/index.js';
export type { SendEmailArgs, SendEmailResult } from '../modules/email/index.js';
export { submitForm } from '../modules/forms/index.js';
export type { SubmitFormArgs, SubmitFormResult } from '../modules/forms/index.js';
+16
View File
@@ -0,0 +1,16 @@
/**
* Entry point: ipal-kit/server
*
* Server-only runtime functions — these import 'server-only' (Turnstile secret,
* SMTP password, nodemailer). Kept OUT of the main entry so that loading the
* Payload config or running `payload generate:importmap` (both Node scripts,
* no bundler) never pulls in 'server-only', which throws outside a bundled
* server context.
*
* Import these only from Server Actions, route handlers, or server components —
* never from the Payload config or client code.
*/ export { verifyTurnstile } from '../modules/turnstile/index.js';
export { sendEmail } from '../modules/email/index.js';
export { submitForm } from '../modules/forms/index.js';
//# sourceMappingURL=server.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../src/exports/server.ts"],"sourcesContent":["/**\n * Entry point: ipal-kit/server\n *\n * Server-only runtime functions — these import 'server-only' (Turnstile secret,\n * SMTP password, nodemailer). Kept OUT of the main entry so that loading the\n * Payload config or running `payload generate:importmap` (both Node scripts,\n * no bundler) never pulls in 'server-only', which throws outside a bundled\n * server context.\n *\n * Import these only from Server Actions, route handlers, or server components —\n * never from the Payload config or client code.\n */\nexport { verifyTurnstile } from '../modules/turnstile/index.js'\nexport { sendEmail } from '../modules/email/index.js'\nexport type { SendEmailArgs, SendEmailResult } from '../modules/email/index.js'\nexport { submitForm } from '../modules/forms/index.js'\nexport type { SubmitFormArgs, SubmitFormResult } from '../modules/forms/index.js'\n"],"names":["verifyTurnstile","sendEmail","submitForm"],"mappings":"AAAA;;;;;;;;;;;CAWC,GACD,SAASA,eAAe,QAAQ,gCAA+B;AAC/D,SAASC,SAAS,QAAQ,4BAA2B;AAErD,SAASC,UAAU,QAAQ,4BAA2B"}
+7
View File
@@ -0,0 +1,7 @@
/**
* Fields for the CookieSettings global — GDPR consent banner copy, editable
* per locale. The privacy-policy link is NOT stored here: it comes from the
* pages module (system page role 'privacyPolicy'), keeping one source of truth.
*/ export { };
//# sourceMappingURL=fields.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["fields.d.ts"],"sourcesContent":["import type { Field } from 'payload';\n/**\n * Fields for the CookieSettings global — GDPR consent banner copy, editable\n * per locale. The privacy-policy link is NOT stored here: it comes from the\n * pages module (system page role 'privacyPolicy'), keeping one source of truth.\n */\nexport declare const cookieSettingsFields: Field[];\n"],"names":[],"mappings":"AACA;;;;CAIC,GACD,WAAmD"}
+7
View File
@@ -0,0 +1,7 @@
import type { Field } from 'payload';
/**
* Fields for the CookieSettings global — GDPR consent banner copy, editable
* per locale. The privacy-policy link is NOT stored here: it comes from the
* pages module (system page role 'privacyPolicy'), keeping one source of truth.
*/
export declare const cookieSettingsFields: Field[];
+87
View File
@@ -0,0 +1,87 @@
import { CONSENT_CATEGORIES } from '../../modules/consent/index.js';
/**
* Fields for the CookieSettings global — GDPR consent banner copy, editable
* per locale. The privacy-policy link is NOT stored here: it comes from the
* pages module (system page role 'privacyPolicy'), keeping one source of truth.
*/ export const cookieSettingsFields = [
{
name: 'message',
type: 'textarea',
admin: {
description: 'Main consent message shown in the banner.'
},
localized: true
},
{
name: 'settingsTitle',
type: 'text',
admin: {
description: 'Heading for the detailed settings panel.'
},
localized: true
},
{
name: 'buttons',
type: 'group',
admin: {
description: 'Button labels.'
},
fields: [
{
name: 'acceptAll',
type: 'text',
localized: true
},
{
name: 'reject',
type: 'text',
localized: true
},
{
name: 'settings',
type: 'text',
localized: true
},
{
name: 'save',
type: 'text',
localized: true
},
{
name: 'back',
type: 'text',
localized: true
}
]
},
{
name: 'categories',
type: 'array',
admin: {
description: 'Per-category titles and descriptions.'
},
fields: [
{
name: 'key',
type: 'select',
options: CONSENT_CATEGORIES.map((c)=>({
label: c,
value: c
})),
required: true
},
{
name: 'title',
type: 'text',
localized: true
},
{
name: 'description',
type: 'textarea',
localized: true
}
]
}
];
//# sourceMappingURL=fields.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../src/globals/CookieSettings/fields.ts"],"sourcesContent":["import type { Field } from 'payload'\n\nimport { CONSENT_CATEGORIES } from '../../modules/consent/index.js'\n\n/**\n * Fields for the CookieSettings global — GDPR consent banner copy, editable\n * per locale. The privacy-policy link is NOT stored here: it comes from the\n * pages module (system page role 'privacyPolicy'), keeping one source of truth.\n */\nexport const cookieSettingsFields: Field[] = [\n {\n name: 'message',\n type: 'textarea',\n admin: {\n description: 'Main consent message shown in the banner.',\n },\n localized: true,\n },\n {\n name: 'settingsTitle',\n type: 'text',\n admin: {\n description: 'Heading for the detailed settings panel.',\n },\n localized: true,\n },\n {\n name: 'buttons',\n type: 'group',\n admin: {\n description: 'Button labels.',\n },\n fields: [\n { name: 'acceptAll', type: 'text', localized: true },\n { name: 'reject', type: 'text', localized: true },\n { name: 'settings', type: 'text', localized: true },\n { name: 'save', type: 'text', localized: true },\n { name: 'back', type: 'text', localized: true },\n ],\n },\n {\n name: 'categories',\n type: 'array',\n admin: {\n description: 'Per-category titles and descriptions.',\n },\n fields: [\n {\n name: 'key',\n type: 'select',\n options: CONSENT_CATEGORIES.map((c) => ({ label: c, value: c })),\n required: true,\n },\n { name: 'title', type: 'text', localized: true },\n { name: 'description', type: 'textarea', localized: true },\n ],\n },\n]\n"],"names":["CONSENT_CATEGORIES","cookieSettingsFields","name","type","admin","description","localized","fields","options","map","c","label","value","required"],"mappings":"AAEA,SAASA,kBAAkB,QAAQ,iCAAgC;AAEnE;;;;CAIC,GACD,OAAO,MAAMC,uBAAgC;IAC3C;QACEC,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAC,WAAW;IACb;IACA;QACEJ,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAC,WAAW;IACb;IACA;QACEJ,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAE,QAAQ;YACN;gBAAEL,MAAM;gBAAaC,MAAM;gBAAQG,WAAW;YAAK;YACnD;gBAAEJ,MAAM;gBAAUC,MAAM;gBAAQG,WAAW;YAAK;YAChD;gBAAEJ,MAAM;gBAAYC,MAAM;gBAAQG,WAAW;YAAK;YAClD;gBAAEJ,MAAM;gBAAQC,MAAM;gBAAQG,WAAW;YAAK;YAC9C;gBAAEJ,MAAM;gBAAQC,MAAM;gBAAQG,WAAW;YAAK;SAC/C;IACH;IACA;QACEJ,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAE,QAAQ;YACN;gBACEL,MAAM;gBACNC,MAAM;gBACNK,SAASR,mBAAmBS,GAAG,CAAC,CAACC,IAAO,CAAA;wBAAEC,OAAOD;wBAAGE,OAAOF;oBAAE,CAAA;gBAC7DG,UAAU;YACZ;YACA;gBAAEX,MAAM;gBAASC,MAAM;gBAAQG,WAAW;YAAK;YAC/C;gBAAEJ,MAAM;gBAAeC,MAAM;gBAAYG,WAAW;YAAK;SAC1D;IACH;CACD,CAAA"}
+6
View File
@@ -0,0 +1,6 @@
/**
* Builds the CookieSettings global — consent banner copy managed by editors.
* Public read (the banner needs it on the frontend for anonymous visitors).
*/ export { };
//# sourceMappingURL=index.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["index.d.ts"],"sourcesContent":["import type { GlobalConfig } from 'payload';\n/**\n * Builds the CookieSettings global — consent banner copy managed by editors.\n * Public read (the banner needs it on the frontend for anonymous visitors).\n */\nexport declare function buildCookieSettings(): GlobalConfig;\n"],"names":[],"mappings":"AACA;;;CAGC,GACD,WAA4D"}
+6
View File
@@ -0,0 +1,6 @@
import type { GlobalConfig } from 'payload';
/**
* Builds the CookieSettings global — consent banner copy managed by editors.
* Public read (the banner needs it on the frontend for anonymous visitors).
*/
export declare function buildCookieSettings(): GlobalConfig;
+19
View File
@@ -0,0 +1,19 @@
import { cookieSettingsFields } from './fields.js';
/**
* Builds the CookieSettings global — consent banner copy managed by editors.
* Public read (the banner needs it on the frontend for anonymous visitors).
*/ export function buildCookieSettings() {
return {
slug: 'cookie-settings',
access: {
read: ()=>true
},
admin: {
group: 'Settings'
},
fields: cookieSettingsFields,
label: 'Cookie Settings'
};
}
//# sourceMappingURL=index.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../src/globals/CookieSettings/index.ts"],"sourcesContent":["import type { GlobalConfig } from 'payload'\n\nimport { cookieSettingsFields } from './fields.js'\n\n/**\n * Builds the CookieSettings global — consent banner copy managed by editors.\n * Public read (the banner needs it on the frontend for anonymous visitors).\n */\nexport function buildCookieSettings(): GlobalConfig {\n return {\n slug: 'cookie-settings',\n access: {\n read: () => true,\n },\n admin: {\n group: 'Settings',\n },\n fields: cookieSettingsFields,\n label: 'Cookie Settings',\n }\n}\n"],"names":["cookieSettingsFields","buildCookieSettings","slug","access","read","admin","group","fields","label"],"mappings":"AAEA,SAASA,oBAAoB,QAAQ,cAAa;AAElD;;;CAGC,GACD,OAAO,SAASC;IACd,OAAO;QACLC,MAAM;QACNC,QAAQ;YACNC,MAAM,IAAM;QACd;QACAC,OAAO;YACLC,OAAO;QACT;QACAC,QAAQP;QACRQ,OAAO;IACT;AACF"}
+6
View File
@@ -0,0 +1,6 @@
/**
* Analytics configuration — GA4 measurement ID and GTM container ID.
* IDs are public (exposed client-side), so no read restriction needed.
*/ export { };
//# sourceMappingURL=analytics.d.js.map
@@ -0,0 +1 @@
{"version":3,"sources":["analytics.d.ts"],"sourcesContent":["import type { Field } from 'payload';\n/**\n * Analytics configuration — GA4 measurement ID and GTM container ID.\n * IDs are public (exposed client-side), so no read restriction needed.\n */\nexport declare const analyticsFields: Field[];\n"],"names":[],"mappings":"AACA;;;CAGC,GACD,WAA8C"}
+6
View File
@@ -0,0 +1,6 @@
import type { Field } from 'payload';
/**
* Analytics configuration — GA4 measurement ID and GTM container ID.
* IDs are public (exposed client-side), so no read restriction needed.
*/
export declare const analyticsFields: Field[];
+23
View File
@@ -0,0 +1,23 @@
/**
* Analytics configuration — GA4 measurement ID and GTM container ID.
* IDs are public (exposed client-side), so no read restriction needed.
*/ export const analyticsFields = [
{
name: 'ga4MeasurementId',
type: 'text',
admin: {
description: 'Google Analytics 4 Measurement ID.',
placeholder: 'G-XXXXXXXXXX'
}
},
{
name: 'gtmContainerId',
type: 'text',
admin: {
description: 'Google Tag Manager container ID.',
placeholder: 'GTM-XXXXXXX'
}
}
];
//# sourceMappingURL=analytics.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../../src/globals/SiteIntegrations/fields/analytics.ts"],"sourcesContent":["import type { Field } from 'payload'\n\n/**\n * Analytics configuration — GA4 measurement ID and GTM container ID.\n * IDs are public (exposed client-side), so no read restriction needed.\n */\nexport const analyticsFields: Field[] = [\n {\n name: 'ga4MeasurementId',\n type: 'text',\n admin: {\n description: 'Google Analytics 4 Measurement ID.',\n placeholder: 'G-XXXXXXXXXX',\n },\n },\n {\n name: 'gtmContainerId',\n type: 'text',\n admin: {\n description: 'Google Tag Manager container ID.',\n placeholder: 'GTM-XXXXXXX',\n },\n },\n]\n"],"names":["analyticsFields","name","type","admin","description","placeholder"],"mappings":"AAEA;;;CAGC,GACD,OAAO,MAAMA,kBAA2B;IACtC;QACEC,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;YACbC,aAAa;QACf;IACF;IACA;QACEJ,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;YACbC,aAAa;QACf;IACF;CACD,CAAA"}
+9
View File
@@ -0,0 +1,9 @@
/**
* SMTP transport settings for outbound email.
*
* Protected at the global level (SiteIntegrations requires an authenticated
* user), so all fields — including the password — stay editable in the admin
* panel while remaining inaccessible to anonymous API requests.
*/ export { };
//# sourceMappingURL=smtp.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["smtp.d.ts"],"sourcesContent":["import type { Field } from 'payload';\n/**\n * SMTP transport settings for outbound email.\n *\n * Protected at the global level (SiteIntegrations requires an authenticated\n * user), so all fields — including the password — stay editable in the admin\n * panel while remaining inaccessible to anonymous API requests.\n */\nexport declare const smtpFields: Field[];\n"],"names":[],"mappings":"AACA;;;;;;CAMC,GACD,WAAyC"}
+9
View File
@@ -0,0 +1,9 @@
import type { Field } from 'payload';
/**
* SMTP transport settings for outbound email.
*
* Protected at the global level (SiteIntegrations requires an authenticated
* user), so all fields — including the password — stay editable in the admin
* panel while remaining inaccessible to anonymous API requests.
*/
export declare const smtpFields: Field[];
+59
View File
@@ -0,0 +1,59 @@
/**
* SMTP transport settings for outbound email.
*
* Protected at the global level (SiteIntegrations requires an authenticated
* user), so all fields — including the password — stay editable in the admin
* panel while remaining inaccessible to anonymous API requests.
*/ export const smtpFields = [
{
type: 'row',
fields: [
{
name: 'smtpHost',
type: 'text',
admin: {
placeholder: 'smtp.example.com',
width: '70%'
}
},
{
name: 'smtpPort',
type: 'number',
admin: {
width: '30%'
},
defaultValue: 587
}
]
},
{
name: 'smtpUser',
type: 'text',
admin: {
description: 'SMTP account username.'
}
},
{
name: 'smtpPassword',
type: 'text',
admin: {
description: 'SMTP account password.'
}
},
{
name: 'smtpFromAddress',
type: 'email',
admin: {
description: 'Default "from" address for outgoing mail.'
}
},
{
name: 'smtpFromName',
type: 'text',
admin: {
description: 'Default "from" display name.'
}
}
];
//# sourceMappingURL=smtp.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../../src/globals/SiteIntegrations/fields/smtp.ts"],"sourcesContent":["import type { Field } from 'payload'\n\n/**\n * SMTP transport settings for outbound email.\n *\n * Protected at the global level (SiteIntegrations requires an authenticated\n * user), so all fields — including the password — stay editable in the admin\n * panel while remaining inaccessible to anonymous API requests.\n */\nexport const smtpFields: Field[] = [\n {\n type: 'row',\n fields: [\n {\n name: 'smtpHost',\n type: 'text',\n admin: { placeholder: 'smtp.example.com', width: '70%' },\n },\n {\n name: 'smtpPort',\n type: 'number',\n admin: { width: '30%' },\n defaultValue: 587,\n },\n ],\n },\n {\n name: 'smtpUser',\n type: 'text',\n admin: {\n description: 'SMTP account username.',\n },\n },\n {\n name: 'smtpPassword',\n type: 'text',\n admin: {\n description: 'SMTP account password.',\n },\n },\n {\n name: 'smtpFromAddress',\n type: 'email',\n admin: {\n description: 'Default \"from\" address for outgoing mail.',\n },\n },\n {\n name: 'smtpFromName',\n type: 'text',\n admin: {\n description: 'Default \"from\" display name.',\n },\n },\n]\n"],"names":["smtpFields","type","fields","name","admin","placeholder","width","defaultValue","description"],"mappings":"AAEA;;;;;;CAMC,GACD,OAAO,MAAMA,aAAsB;IACjC;QACEC,MAAM;QACNC,QAAQ;YACN;gBACEC,MAAM;gBACNF,MAAM;gBACNG,OAAO;oBAAEC,aAAa;oBAAoBC,OAAO;gBAAM;YACzD;YACA;gBACEH,MAAM;gBACNF,MAAM;gBACNG,OAAO;oBAAEE,OAAO;gBAAM;gBACtBC,cAAc;YAChB;SACD;IACH;IACA;QACEJ,MAAM;QACNF,MAAM;QACNG,OAAO;YACLI,aAAa;QACf;IACF;IACA;QACEL,MAAM;QACNF,MAAM;QACNG,OAAO;YACLI,aAAa;QACf;IACF;IACA;QACEL,MAAM;QACNF,MAAM;QACNG,OAAO;YACLI,aAAa;QACf;IACF;IACA;QACEL,MAAM;QACNF,MAAM;QACNG,OAAO;YACLI,aAAa;QACf;IACF;CACD,CAAA"}
+10
View File
@@ -0,0 +1,10 @@
/**
* Cloudflare R2 storage credentials.
* Reserved for future use — media offloading to R2.
*
* Protected at the global level (SiteIntegrations requires an authenticated
* user), so the access keys stay editable in the admin panel while remaining
* inaccessible to anonymous API requests.
*/ export { };
//# sourceMappingURL=storage.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["storage.d.ts"],"sourcesContent":["import type { Field } from 'payload';\n/**\n * Cloudflare R2 storage credentials.\n * Reserved for future use — media offloading to R2.\n *\n * Protected at the global level (SiteIntegrations requires an authenticated\n * user), so the access keys stay editable in the admin panel while remaining\n * inaccessible to anonymous API requests.\n */\nexport declare const storageFields: Field[];\n"],"names":[],"mappings":"AACA;;;;;;;CAOC,GACD,WAA4C"}
+10
View File
@@ -0,0 +1,10 @@
import type { Field } from 'payload';
/**
* Cloudflare R2 storage credentials.
* Reserved for future use — media offloading to R2.
*
* Protected at the global level (SiteIntegrations requires an authenticated
* user), so the access keys stay editable in the admin panel while remaining
* inaccessible to anonymous API requests.
*/
export declare const storageFields: Field[];
+39
View File
@@ -0,0 +1,39 @@
/**
* Cloudflare R2 storage credentials.
* Reserved for future use — media offloading to R2.
*
* Protected at the global level (SiteIntegrations requires an authenticated
* user), so the access keys stay editable in the admin panel while remaining
* inaccessible to anonymous API requests.
*/ export const storageFields = [
{
name: 'r2Bucket',
type: 'text',
admin: {
description: 'R2 bucket name.'
}
},
{
name: 'r2Endpoint',
type: 'text',
admin: {
description: 'R2 S3-compatible endpoint URL.'
}
},
{
name: 'r2AccessKeyId',
type: 'text',
admin: {
description: 'R2 access key ID.'
}
},
{
name: 'r2SecretAccessKey',
type: 'text',
admin: {
description: 'R2 secret access key.'
}
}
];
//# sourceMappingURL=storage.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../../src/globals/SiteIntegrations/fields/storage.ts"],"sourcesContent":["import type { Field } from 'payload'\n\n/**\n * Cloudflare R2 storage credentials.\n * Reserved for future use — media offloading to R2.\n *\n * Protected at the global level (SiteIntegrations requires an authenticated\n * user), so the access keys stay editable in the admin panel while remaining\n * inaccessible to anonymous API requests.\n */\nexport const storageFields: Field[] = [\n {\n name: 'r2Bucket',\n type: 'text',\n admin: {\n description: 'R2 bucket name.',\n },\n },\n {\n name: 'r2Endpoint',\n type: 'text',\n admin: {\n description: 'R2 S3-compatible endpoint URL.',\n },\n },\n {\n name: 'r2AccessKeyId',\n type: 'text',\n admin: {\n description: 'R2 access key ID.',\n },\n },\n {\n name: 'r2SecretAccessKey',\n type: 'text',\n admin: {\n description: 'R2 secret access key.',\n },\n },\n]\n"],"names":["storageFields","name","type","admin","description"],"mappings":"AAEA;;;;;;;CAOC,GACD,OAAO,MAAMA,gBAAyB;IACpC;QACEC,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;IACF;IACA;QACEH,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;IACF;IACA;QACEH,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;IACF;IACA;QACEH,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;IACF;CACD,CAAA"}
+10
View File
@@ -0,0 +1,10 @@
/**
* Cloudflare Turnstile credentials.
*
* siteKey is public (rendered in the widget); secretKey is used for
* server-side verification. Both are protected at the global level
* (SiteIntegrations requires an authenticated user) rather than per-field,
* so they remain editable in the admin panel.
*/ export { };
//# sourceMappingURL=turnstile.d.js.map
@@ -0,0 +1 @@
{"version":3,"sources":["turnstile.d.ts"],"sourcesContent":["import type { Field } from 'payload';\n/**\n * Cloudflare Turnstile credentials.\n *\n * siteKey is public (rendered in the widget); secretKey is used for\n * server-side verification. Both are protected at the global level\n * (SiteIntegrations requires an authenticated user) rather than per-field,\n * so they remain editable in the admin panel.\n */\nexport declare const turnstileFields: Field[];\n"],"names":[],"mappings":"AACA;;;;;;;CAOC,GACD,WAA8C"}
+10
View File
@@ -0,0 +1,10 @@
import type { Field } from 'payload';
/**
* Cloudflare Turnstile credentials.
*
* siteKey is public (rendered in the widget); secretKey is used for
* server-side verification. Both are protected at the global level
* (SiteIntegrations requires an authenticated user) rather than per-field,
* so they remain editable in the admin panel.
*/
export declare const turnstileFields: Field[];
+25
View File
@@ -0,0 +1,25 @@
/**
* Cloudflare Turnstile credentials.
*
* siteKey is public (rendered in the widget); secretKey is used for
* server-side verification. Both are protected at the global level
* (SiteIntegrations requires an authenticated user) rather than per-field,
* so they remain editable in the admin panel.
*/ export const turnstileFields = [
{
name: 'turnstileSiteKey',
type: 'text',
admin: {
description: 'Public site key rendered in the Turnstile widget.'
}
},
{
name: 'turnstileSecretKey',
type: 'text',
admin: {
description: 'Secret key used for server-side verification.'
}
}
];
//# sourceMappingURL=turnstile.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../../src/globals/SiteIntegrations/fields/turnstile.ts"],"sourcesContent":["import type { Field } from 'payload'\n\n/**\n * Cloudflare Turnstile credentials.\n *\n * siteKey is public (rendered in the widget); secretKey is used for\n * server-side verification. Both are protected at the global level\n * (SiteIntegrations requires an authenticated user) rather than per-field,\n * so they remain editable in the admin panel.\n */\nexport const turnstileFields: Field[] = [\n {\n name: 'turnstileSiteKey',\n type: 'text',\n admin: {\n description: 'Public site key rendered in the Turnstile widget.',\n },\n },\n {\n name: 'turnstileSecretKey',\n type: 'text',\n admin: {\n description: 'Secret key used for server-side verification.',\n },\n },\n]\n"],"names":["turnstileFields","name","type","admin","description"],"mappings":"AAEA;;;;;;;CAOC,GACD,OAAO,MAAMA,kBAA2B;IACtC;QACEC,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;IACF;IACA;QACEH,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;IACF;CACD,CAAA"}
+3
View File
@@ -0,0 +1,3 @@
export { };
//# sourceMappingURL=index.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["index.d.ts"],"sourcesContent":["import type { Field, GlobalConfig } from 'payload';\ntype BuildSiteIntegrationsArgs = {\n /** Extra fields injected by the client project */\n additionalFields?: Field[];\n};\n/**\n * Builds the SiteIntegrations global.\n *\n * Holds third-party service credentials. Access is enforced at the global\n * level — the whole global requires an authenticated user — so secrets stay\n * out of anonymous API responses while remaining editable in the admin panel\n * and readable via the server-side Local API. (Field-level read:false was\n * avoided because it also hides fields from the admin UI, making them\n * impossible to enter.)\n *\n * Unnamed tabs keep data flat (siteIntegrations.ga4MeasurementId).\n */\nexport declare function buildSiteIntegrations({ additionalFields, }?: BuildSiteIntegrationsArgs): GlobalConfig;\nexport {};\n"],"names":[],"mappings":"AAkBA,WAAU"}
+19
View File
@@ -0,0 +1,19 @@
import type { Field, GlobalConfig } from 'payload';
type BuildSiteIntegrationsArgs = {
/** Extra fields injected by the client project */
additionalFields?: Field[];
};
/**
* Builds the SiteIntegrations global.
*
* Holds third-party service credentials. Access is enforced at the global
* level — the whole global requires an authenticated user — so secrets stay
* out of anonymous API responses while remaining editable in the admin panel
* and readable via the server-side Local API. (Field-level read:false was
* avoided because it also hides fields from the admin UI, making them
* impossible to enter.)
*
* Unnamed tabs keep data flat (siteIntegrations.ga4MeasurementId).
*/
export declare function buildSiteIntegrations({ additionalFields, }?: BuildSiteIntegrationsArgs): GlobalConfig;
export {};
+62
View File
@@ -0,0 +1,62 @@
import { isAdmin } from '../../modules/access/index.js';
import { analyticsFields } from './fields/analytics.js';
import { smtpFields } from './fields/smtp.js';
import { storageFields } from './fields/storage.js';
import { turnstileFields } from './fields/turnstile.js';
/**
* Builds the SiteIntegrations global.
*
* Holds third-party service credentials. Access is enforced at the global
* level — the whole global requires an authenticated user — so secrets stay
* out of anonymous API responses while remaining editable in the admin panel
* and readable via the server-side Local API. (Field-level read:false was
* avoided because it also hides fields from the admin UI, making them
* impossible to enter.)
*
* Unnamed tabs keep data flat (siteIntegrations.ga4MeasurementId).
*/ export function buildSiteIntegrations({ additionalFields } = {}) {
return {
slug: 'site-integrations',
access: {
// Admin-only — secrets live here. Anonymous and non-admin users get
// nothing through the API; admins read/edit in the panel and via Local API.
read: ({ req: { user } })=>isAdmin(user),
update: ({ req: { user } })=>isAdmin(user)
},
admin: {
group: 'Settings'
},
fields: [
{
type: 'tabs',
tabs: [
{
fields: analyticsFields,
label: 'Analytics'
},
{
fields: turnstileFields,
label: 'Turnstile'
},
{
fields: smtpFields,
label: 'SMTP'
},
{
fields: storageFields,
label: 'Storage'
},
...additionalFields?.length ? [
{
fields: additionalFields,
label: 'Custom'
}
] : []
]
}
],
label: 'Site Integrations'
};
}
//# sourceMappingURL=index.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../src/globals/SiteIntegrations/index.ts"],"sourcesContent":["import type { Field, GlobalConfig } from 'payload'\n\nimport { isAdmin } from '../../modules/access/index.js'\nimport { analyticsFields } from './fields/analytics.js'\nimport { smtpFields } from './fields/smtp.js'\nimport { storageFields } from './fields/storage.js'\nimport { turnstileFields } from './fields/turnstile.js'\n\ntype BuildSiteIntegrationsArgs = {\n /** Extra fields injected by the client project */\n additionalFields?: Field[]\n}\n\n/**\n * Builds the SiteIntegrations global.\n *\n * Holds third-party service credentials. Access is enforced at the global\n * level — the whole global requires an authenticated user — so secrets stay\n * out of anonymous API responses while remaining editable in the admin panel\n * and readable via the server-side Local API. (Field-level read:false was\n * avoided because it also hides fields from the admin UI, making them\n * impossible to enter.)\n *\n * Unnamed tabs keep data flat (siteIntegrations.ga4MeasurementId).\n */\nexport function buildSiteIntegrations({\n additionalFields,\n}: BuildSiteIntegrationsArgs = {}): GlobalConfig {\n return {\n slug: 'site-integrations',\n access: {\n // Admin-only — secrets live here. Anonymous and non-admin users get\n // nothing through the API; admins read/edit in the panel and via Local API.\n read: ({ req: { user } }) => isAdmin(user),\n update: ({ req: { user } }) => isAdmin(user),\n },\n admin: {\n group: 'Settings',\n },\n fields: [\n {\n type: 'tabs',\n tabs: [\n { fields: analyticsFields, label: 'Analytics' },\n { fields: turnstileFields, label: 'Turnstile' },\n { fields: smtpFields, label: 'SMTP' },\n { fields: storageFields, label: 'Storage' },\n ...(additionalFields?.length ? [{ fields: additionalFields, label: 'Custom' }] : []),\n ],\n },\n ],\n label: 'Site Integrations',\n }\n}\n"],"names":["isAdmin","analyticsFields","smtpFields","storageFields","turnstileFields","buildSiteIntegrations","additionalFields","slug","access","read","req","user","update","admin","group","fields","type","tabs","label","length"],"mappings":"AAEA,SAASA,OAAO,QAAQ,gCAA+B;AACvD,SAASC,eAAe,QAAQ,wBAAuB;AACvD,SAASC,UAAU,QAAQ,mBAAkB;AAC7C,SAASC,aAAa,QAAQ,sBAAqB;AACnD,SAASC,eAAe,QAAQ,wBAAuB;AAOvD;;;;;;;;;;;CAWC,GACD,OAAO,SAASC,sBAAsB,EACpCC,gBAAgB,EACU,GAAG,CAAC,CAAC;IAC/B,OAAO;QACLC,MAAM;QACNC,QAAQ;YACN,oEAAoE;YACpE,4EAA4E;YAC5EC,MAAM,CAAC,EAAEC,KAAK,EAAEC,IAAI,EAAE,EAAE,GAAKX,QAAQW;YACrCC,QAAQ,CAAC,EAAEF,KAAK,EAAEC,IAAI,EAAE,EAAE,GAAKX,QAAQW;QACzC;QACAE,OAAO;YACLC,OAAO;QACT;QACAC,QAAQ;YACN;gBACEC,MAAM;gBACNC,MAAM;oBACJ;wBAAEF,QAAQd;wBAAiBiB,OAAO;oBAAY;oBAC9C;wBAAEH,QAAQX;wBAAiBc,OAAO;oBAAY;oBAC9C;wBAAEH,QAAQb;wBAAYgB,OAAO;oBAAO;oBACpC;wBAAEH,QAAQZ;wBAAee,OAAO;oBAAU;uBACtCZ,kBAAkBa,SAAS;wBAAC;4BAAEJ,QAAQT;4BAAkBY,OAAO;wBAAS;qBAAE,GAAG,EAAE;iBACpF;YACH;SACD;QACDA,OAAO;IACT;AACF"}
+6
View File
@@ -0,0 +1,6 @@
/**
* General site identity fields.
* Consumed by SEO/OG (siteName, defaultShareImage) and frontend (logo).
*/ export { };
//# sourceMappingURL=general.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["general.d.ts"],"sourcesContent":["import type { Field } from 'payload';\n/**\n * General site identity fields.\n * Consumed by SEO/OG (siteName, defaultShareImage) and frontend (logo).\n */\nexport declare const generalFields: Field[];\n"],"names":[],"mappings":"AACA;;;CAGC,GACD,WAA4C"}
+6
View File
@@ -0,0 +1,6 @@
import type { Field } from 'payload';
/**
* General site identity fields.
* Consumed by SEO/OG (siteName, defaultShareImage) and frontend (logo).
*/
export declare const generalFields: Field[];
+88
View File
@@ -0,0 +1,88 @@
/**
* General site identity fields.
* Consumed by SEO/OG (siteName, defaultShareImage) and frontend (logo).
*/ export const generalFields = [
{
name: 'siteName',
type: 'text',
admin: {
description: 'Used in page titles and Open Graph metadata.'
},
localized: true,
required: true
},
{
name: 'titleOrder',
type: 'select',
admin: {
description: 'Which comes first in browser tabs.'
},
defaultValue: 'page-first',
options: [
{
label: 'Page first — About Us | Acme',
value: 'page-first'
},
{
label: 'Site first — Acme | About Us',
value: 'site-first'
}
]
},
{
name: 'titleSeparator',
type: 'select',
admin: {
description: 'Separates the page title from the site name in browser tabs.'
},
defaultValue: '|',
options: [
{
label: 'Pipe — Page | Site',
value: '|'
},
{
label: 'Dash — Page – Site',
value: '–'
},
{
label: 'Hyphen — Page - Site',
value: '-'
},
{
label: 'Bullet — Page · Site',
value: '·'
},
{
label: 'Slash — Page / Site',
value: '/'
}
]
},
{
name: 'logo',
type: 'upload',
admin: {
description: 'Primary site logo.'
},
relationTo: 'media'
},
{
name: 'defaultShareImage',
type: 'upload',
admin: {
description: 'Fallback Open Graph image when a page has none.'
},
relationTo: 'media'
},
{
name: 'favicon',
type: 'upload',
admin: {
description: 'Square source icon (PNG or SVG) for the browser tab. Rendered by the frontend.'
},
relationTo: 'media'
}
];
//# sourceMappingURL=general.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../../src/globals/SiteSettings/fields/general.ts"],"sourcesContent":["import type { Field } from 'payload'\n\n/**\n * General site identity fields.\n * Consumed by SEO/OG (siteName, defaultShareImage) and frontend (logo).\n */\nexport const generalFields: Field[] = [\n {\n name: 'siteName',\n type: 'text',\n admin: {\n description: 'Used in page titles and Open Graph metadata.',\n },\n localized: true,\n required: true,\n },\n {\n name: 'titleOrder',\n type: 'select',\n admin: {\n description: 'Which comes first in browser tabs.',\n },\n defaultValue: 'page-first',\n options: [\n { label: 'Page first — About Us | Acme', value: 'page-first' },\n { label: 'Site first — Acme | About Us', value: 'site-first' },\n ],\n },\n {\n name: 'titleSeparator',\n type: 'select',\n admin: {\n description: 'Separates the page title from the site name in browser tabs.',\n },\n defaultValue: '|',\n options: [\n { label: 'Pipe — Page | Site', value: '|' },\n { label: 'Dash — Page – Site', value: '–' },\n { label: 'Hyphen — Page - Site', value: '-' },\n { label: 'Bullet — Page · Site', value: '·' },\n { label: 'Slash — Page / Site', value: '/' },\n ],\n },\n {\n name: 'logo',\n type: 'upload',\n admin: {\n description: 'Primary site logo.',\n },\n relationTo: 'media',\n },\n {\n name: 'defaultShareImage',\n type: 'upload',\n admin: {\n description: 'Fallback Open Graph image when a page has none.',\n },\n relationTo: 'media',\n },\n {\n name: 'favicon',\n type: 'upload',\n admin: {\n description: 'Square source icon (PNG or SVG) for the browser tab. Rendered by the frontend.',\n },\n relationTo: 'media',\n },\n]\n"],"names":["generalFields","name","type","admin","description","localized","required","defaultValue","options","label","value","relationTo"],"mappings":"AAEA;;;CAGC,GACD,OAAO,MAAMA,gBAAyB;IACpC;QACEC,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAC,WAAW;QACXC,UAAU;IACZ;IACA;QACEL,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAG,cAAc;QACdC,SAAS;YACP;gBAAEC,OAAO;gBAAkCC,OAAO;YAAa;YAC/D;gBAAED,OAAO;gBAAkCC,OAAO;YAAa;SAChE;IACH;IACA;QACET,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAG,cAAc;QACdC,SAAS;YACP;gBAAEC,OAAO;gBAAwBC,OAAO;YAAI;YAC5C;gBAAED,OAAO;gBAAwBC,OAAO;YAAI;YAC5C;gBAAED,OAAO;gBAA0BC,OAAO;YAAI;YAC9C;gBAAED,OAAO;gBAA0BC,OAAO;YAAI;YAC9C;gBAAED,OAAO;gBAAyBC,OAAO;YAAI;SAC9C;IACH;IACA;QACET,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAO,YAAY;IACd;IACA;QACEV,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAO,YAAY;IACd;IACA;QACEV,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAO,YAAY;IACd;CACD,CAAA"}
+3
View File
@@ -0,0 +1,3 @@
export { };
//# sourceMappingURL=navigation.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["navigation.d.ts"],"sourcesContent":["export {};\n"],"names":[],"mappings":"AAAA,WAAU"}
+1
View File
@@ -0,0 +1 @@
export {};
+2
View File
@@ -0,0 +1,2 @@
//# sourceMappingURL=navigation.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../../src/globals/SiteSettings/fields/navigation.ts"],"names":[],"mappings":""}
+9
View File
@@ -0,0 +1,9 @@
/**
* Theme behavior configuration.
*
* These are decisions, not visuals — the plugin stores them, the client
* template reads them and decides whether to render a toggle and which
* mode to start in. Appearance itself stays in the template.
*/ export { };
//# sourceMappingURL=theme.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["theme.d.ts"],"sourcesContent":["import type { Field } from 'payload';\n/**\n * Theme behavior configuration.\n *\n * These are decisions, not visuals — the plugin stores them, the client\n * template reads them and decides whether to render a toggle and which\n * mode to start in. Appearance itself stays in the template.\n */\nexport declare const themeFields: Field[];\n"],"names":[],"mappings":"AACA;;;;;;CAMC,GACD,WAA0C"}
+9
View File
@@ -0,0 +1,9 @@
import type { Field } from 'payload';
/**
* Theme behavior configuration.
*
* These are decisions, not visuals — the plugin stores them, the client
* template reads them and decides whether to render a toggle and which
* mode to start in. Appearance itself stays in the template.
*/
export declare const themeFields: Field[];
+37
View File
@@ -0,0 +1,37 @@
/**
* Theme behavior configuration.
*
* These are decisions, not visuals — the plugin stores them, the client
* template reads them and decides whether to render a toggle and which
* mode to start in. Appearance itself stays in the template.
*/ export const themeFields = [
{
name: 'defaultTheme',
type: 'select',
admin: {
description: 'Theme applied on a visitor’s first visit.'
},
defaultValue: 'light',
options: [
{
label: 'Light',
value: 'light'
},
{
label: 'Dark',
value: 'dark'
}
],
required: true
},
{
name: 'allowThemeToggle',
type: 'checkbox',
admin: {
description: 'Show a light/dark switch on the site.'
},
defaultValue: true
}
];
//# sourceMappingURL=theme.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../../src/globals/SiteSettings/fields/theme.ts"],"sourcesContent":["import type { Field } from 'payload'\n\n/**\n * Theme behavior configuration.\n *\n * These are decisions, not visuals — the plugin stores them, the client\n * template reads them and decides whether to render a toggle and which\n * mode to start in. Appearance itself stays in the template.\n */\nexport const themeFields: Field[] = [\n {\n name: 'defaultTheme',\n type: 'select',\n admin: {\n description: 'Theme applied on a visitor’s first visit.',\n },\n defaultValue: 'light',\n options: [\n { label: 'Light', value: 'light' },\n { label: 'Dark', value: 'dark' },\n ],\n required: true,\n },\n {\n name: 'allowThemeToggle',\n type: 'checkbox',\n admin: {\n description: 'Show a light/dark switch on the site.',\n },\n defaultValue: true,\n },\n]\n"],"names":["themeFields","name","type","admin","description","defaultValue","options","label","value","required"],"mappings":"AAEA;;;;;;CAMC,GACD,OAAO,MAAMA,cAAuB;IAClC;QACEC,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAC,cAAc;QACdC,SAAS;YACP;gBAAEC,OAAO;gBAASC,OAAO;YAAQ;YACjC;gBAAED,OAAO;gBAAQC,OAAO;YAAO;SAChC;QACDC,UAAU;IACZ;IACA;QACER,MAAM;QACNC,MAAM;QACNC,OAAO;YACLC,aAAa;QACf;QACAC,cAAc;IAChB;CACD,CAAA"}
+3
View File
@@ -0,0 +1,3 @@
export { };
//# sourceMappingURL=index.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["index.d.ts"],"sourcesContent":["import type { Field, GlobalConfig } from 'payload';\ntype BuildSiteSettingsArgs = {\n /** Extra fields injected by the client project */\n additionalFields?: Field[];\n /**\n * Fields for the \"System Pages\" tab — page assignments by role (homepage,\n * privacy policy, collection archives). Assembled by the caller, which is the\n * only place that knows which modules are enabled. The tab is omitted when\n * this is empty.\n */\n systemPageFields?: Field[];\n};\n/**\n * Builds the SiteSettings global.\n *\n * Composes tabs out of field groups; it deliberately doesn't know where those\n * groups come from. Earlier it imported the pages and content modules directly,\n * which meant a global — a presentation-layer concern — had an opinion about\n * blogs. Now the plugin's composition root passes fields in, and adding a new\n * kind of page assignment needs no change here.\n *\n * Uses unnamed tabs — data stays flat (siteSettings.siteName, not\n * siteSettings.general.siteName). Client-provided fields land in their own\n * \"Custom\" tab so core data paths never shift.\n */\nexport declare function buildSiteSettings({ additionalFields, systemPageFields, }?: BuildSiteSettingsArgs): GlobalConfig;\nexport {};\n"],"names":[],"mappings":"AA0BA,WAAU"}
+27
View File
@@ -0,0 +1,27 @@
import type { Field, GlobalConfig } from 'payload';
type BuildSiteSettingsArgs = {
/** Extra fields injected by the client project */
additionalFields?: Field[];
/**
* Fields for the "System Pages" tab — page assignments by role (homepage,
* privacy policy, collection archives). Assembled by the caller, which is the
* only place that knows which modules are enabled. The tab is omitted when
* this is empty.
*/
systemPageFields?: Field[];
};
/**
* Builds the SiteSettings global.
*
* Composes tabs out of field groups; it deliberately doesn't know where those
* groups come from. Earlier it imported the pages and content modules directly,
* which meant a global — a presentation-layer concern — had an opinion about
* blogs. Now the plugin's composition root passes fields in, and adding a new
* kind of page assignment needs no change here.
*
* Uses unnamed tabs — data stays flat (siteSettings.siteName, not
* siteSettings.general.siteName). Client-provided fields land in their own
* "Custom" tab so core data paths never shift.
*/
export declare function buildSiteSettings({ additionalFields, systemPageFields, }?: BuildSiteSettingsArgs): GlobalConfig;
export {};
+55
View File
@@ -0,0 +1,55 @@
import { generalFields } from './fields/general.js';
import { themeFields } from './fields/theme.js';
/**
* Builds the SiteSettings global.
*
* Composes tabs out of field groups; it deliberately doesn't know where those
* groups come from. Earlier it imported the pages and content modules directly,
* which meant a global — a presentation-layer concern — had an opinion about
* blogs. Now the plugin's composition root passes fields in, and adding a new
* kind of page assignment needs no change here.
*
* Uses unnamed tabs — data stays flat (siteSettings.siteName, not
* siteSettings.general.siteName). Client-provided fields land in their own
* "Custom" tab so core data paths never shift.
*/ export function buildSiteSettings({ additionalFields, systemPageFields } = {}) {
return {
slug: 'site-settings',
access: {
read: ()=>true
},
admin: {
group: 'Settings'
},
fields: [
{
type: 'tabs',
tabs: [
{
fields: generalFields,
label: 'General'
},
{
fields: themeFields,
label: 'Theme'
},
...systemPageFields?.length ? [
{
fields: systemPageFields,
label: 'System Pages'
}
] : [],
...additionalFields?.length ? [
{
fields: additionalFields,
label: 'Custom'
}
] : []
]
}
],
label: 'Site Settings'
};
}
//# sourceMappingURL=index.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../src/globals/SiteSettings/index.ts"],"sourcesContent":["import type { Field, GlobalConfig } from 'payload'\n\nimport { generalFields } from './fields/general.js'\nimport { themeFields } from './fields/theme.js'\n\ntype BuildSiteSettingsArgs = {\n /** Extra fields injected by the client project */\n additionalFields?: Field[]\n /**\n * Fields for the \"System Pages\" tab — page assignments by role (homepage,\n * privacy policy, collection archives). Assembled by the caller, which is the\n * only place that knows which modules are enabled. The tab is omitted when\n * this is empty.\n */\n systemPageFields?: Field[]\n}\n\n/**\n * Builds the SiteSettings global.\n *\n * Composes tabs out of field groups; it deliberately doesn't know where those\n * groups come from. Earlier it imported the pages and content modules directly,\n * which meant a global — a presentation-layer concern — had an opinion about\n * blogs. Now the plugin's composition root passes fields in, and adding a new\n * kind of page assignment needs no change here.\n *\n * Uses unnamed tabs — data stays flat (siteSettings.siteName, not\n * siteSettings.general.siteName). Client-provided fields land in their own\n * \"Custom\" tab so core data paths never shift.\n */\nexport function buildSiteSettings({\n additionalFields,\n systemPageFields,\n}: BuildSiteSettingsArgs = {}): GlobalConfig {\n return {\n slug: 'site-settings',\n access: {\n read: () => true,\n },\n admin: {\n group: 'Settings',\n },\n fields: [\n {\n type: 'tabs',\n tabs: [\n {\n fields: generalFields,\n label: 'General',\n },\n {\n fields: themeFields,\n label: 'Theme',\n },\n ...(systemPageFields?.length\n ? [{ fields: systemPageFields, label: 'System Pages' }]\n : []),\n ...(additionalFields?.length ? [{ fields: additionalFields, label: 'Custom' }] : []),\n ],\n },\n ],\n label: 'Site Settings',\n }\n}\n"],"names":["generalFields","themeFields","buildSiteSettings","additionalFields","systemPageFields","slug","access","read","admin","group","fields","type","tabs","label","length"],"mappings":"AAEA,SAASA,aAAa,QAAQ,sBAAqB;AACnD,SAASC,WAAW,QAAQ,oBAAmB;AAc/C;;;;;;;;;;;;CAYC,GACD,OAAO,SAASC,kBAAkB,EAChCC,gBAAgB,EAChBC,gBAAgB,EACM,GAAG,CAAC,CAAC;IAC3B,OAAO;QACLC,MAAM;QACNC,QAAQ;YACNC,MAAM,IAAM;QACd;QACAC,OAAO;YACLC,OAAO;QACT;QACAC,QAAQ;YACN;gBACEC,MAAM;gBACNC,MAAM;oBACJ;wBACEF,QAAQV;wBACRa,OAAO;oBACT;oBACA;wBACEH,QAAQT;wBACRY,OAAO;oBACT;uBACIT,kBAAkBU,SAClB;wBAAC;4BAAEJ,QAAQN;4BAAkBS,OAAO;wBAAe;qBAAE,GACrD,EAAE;uBACFV,kBAAkBW,SAAS;wBAAC;4BAAEJ,QAAQP;4BAAkBU,OAAO;wBAAS;qBAAE,GAAG,EAAE;iBACpF;YACH;SACD;QACDA,OAAO;IACT;AACF"}
+17
View File
@@ -0,0 +1,17 @@
export { adminOnly, adminOnlyField, adminOrEditor, adminOrEditorField, adminOrSelf, authenticated, hasMinimumRole, isAdmin, isEditor, requireRole, requireRoleField, ROLE_HIERARCHY } from './modules/access/index.js';
export { getAnalyticsConfig } from './modules/analytics/index.js';
export { ACCEPT_ALL_CONSENT, CONSENT_CATEGORIES, CONSENT_COOKIE, CONSENT_MAX_AGE, CONSENT_VERSION, DEFAULT_CONSENT, getConsentTexts, parseConsent, REJECT_ALL_CONSENT, serializeConsent, setDefaultConsent, updateConsent } from './modules/consent/index.js';
export { archiveFieldName, buildArchivePath, buildEntryPath, getArchiveEntries, parsePageParam, resolveRoute } from './modules/content/index.js';
export { panelSmtpAdapter } from './modules/email/panelSmtpAdapter.js';
export { buildFormsPlugin } from './modules/forms/formsPluginConfig.js';
export { createContentHelpers } from './modules/frontend/index.js';
export { buildLocalizedPath, getDefaultLocale, getLocaleCodes, getLocaleDefinition, getLocalizedSlugs, isValidLocale, LOCALE_COOKIE_NAME, matchAcceptLanguage, negotiateLocale, switchLocalePath } from './modules/i18n/index.js';
export { createLocaleMiddleware, DEFAULT_MIDDLEWARE_MATCHER } from './modules/i18n/index.js';
export { ALL_SYSTEM_PAGE_ROLES, getSystemPagePath } from './modules/pages/index.js';
export { getGlobal, getSiteIntegrations, getSiteSettings, SITE_INTEGRATIONS_SLUG, SITE_SETTINGS_SLUG } from './modules/payload/index.js';
export { buildHreflangAlternates, buildMetadata, composeTitle } from './modules/seo/index.js';
export { buildAutoFillMetaHook, buildRobots, buildSitemapEntries, createMetadataGenerator, createPageMetadata, injectAutoFillMeta } from './modules/seo/index.js';
export { buildSlugField, toSlug } from './modules/slug/index.js';
export { ipalKit } from './plugin.js';
//# sourceMappingURL=index.d.js.map
+1
View File
File diff suppressed because one or more lines are too long
+29
View File
@@ -0,0 +1,29 @@
export type { AccessOption, Role } from './modules/access/index.js';
export { adminOnly, adminOnlyField, adminOrEditor, adminOrEditorField, adminOrSelf, authenticated, hasMinimumRole, isAdmin, isEditor, requireRole, requireRoleField, ROLE_HIERARCHY, } from './modules/access/index.js';
export type { AnalyticsConfig } from './modules/analytics/index.js';
export { getAnalyticsConfig } from './modules/analytics/index.js';
export { ACCEPT_ALL_CONSENT, CONSENT_CATEGORIES, CONSENT_COOKIE, CONSENT_MAX_AGE, CONSENT_VERSION, DEFAULT_CONSENT, getConsentTexts, parseConsent, REJECT_ALL_CONSENT, serializeConsent, setDefaultConsent, updateConsent, } from './modules/consent/index.js';
export type { ConsentCategory, ConsentState, ConsentTexts } from './modules/consent/index.js';
export type { ContentCollectionOption, ContentOption, ResolvedRoute, } from './modules/content/index.js';
export { archiveFieldName, buildArchivePath, buildEntryPath, getArchiveEntries, parsePageParam, resolveRoute, } from './modules/content/index.js';
export type { ArchiveEntries } from './modules/content/index.js';
export { panelSmtpAdapter } from './modules/email/panelSmtpAdapter.js';
export type { PanelSmtpAdapterArgs } from './modules/email/panelSmtpAdapter.js';
export { buildFormsPlugin } from './modules/forms/formsPluginConfig.js';
export type { FormsCollectionOverrides, FormsFieldsOverride, FormsOption, } from './modules/forms/types.js';
export { createContentHelpers } from './modules/frontend/index.js';
export type { I18nConfig, LocaleDefinition, LocalizedSlugs } from './modules/i18n/index.js';
export { buildLocalizedPath, getDefaultLocale, getLocaleCodes, getLocaleDefinition, getLocalizedSlugs, isValidLocale, LOCALE_COOKIE_NAME, matchAcceptLanguage, negotiateLocale, switchLocalePath, } from './modules/i18n/index.js';
export type { LocaleMiddlewareResult } from './modules/i18n/index.js';
export { createLocaleMiddleware, DEFAULT_MIDDLEWARE_MATCHER } from './modules/i18n/index.js';
export type { PagesOption, SystemPageRole } from './modules/pages/index.js';
export { ALL_SYSTEM_PAGE_ROLES, getSystemPagePath } from './modules/pages/index.js';
export type { GlobalQueryOptions } from './modules/payload/index.js';
export { getGlobal, getSiteIntegrations, getSiteSettings, SITE_INTEGRATIONS_SLUG, SITE_SETTINGS_SLUG, } from './modules/payload/index.js';
export type { PageMetadata, SeoMeta, SeoOption } from './modules/seo/index.js';
export { buildHreflangAlternates, buildMetadata, composeTitle } from './modules/seo/index.js';
export type { AutoFillMapping, RobotsRules, SitemapEntry } from './modules/seo/index.js';
export { buildAutoFillMetaHook, buildRobots, buildSitemapEntries, createMetadataGenerator, createPageMetadata, injectAutoFillMeta, } from './modules/seo/index.js';
export { buildSlugField, toSlug } from './modules/slug/index.js';
export { ipalKit } from './plugin.js';
export type { IpalOptions } from './types.js';
+20
View File
@@ -0,0 +1,20 @@
export { adminOnly, adminOnlyField, adminOrEditor, adminOrEditorField, adminOrSelf, authenticated, hasMinimumRole, isAdmin, isEditor, requireRole, requireRoleField, ROLE_HIERARCHY } from './modules/access/index.js';
export { getAnalyticsConfig } from './modules/analytics/index.js';
export { ACCEPT_ALL_CONSENT, CONSENT_CATEGORIES, CONSENT_COOKIE, CONSENT_MAX_AGE, CONSENT_VERSION, DEFAULT_CONSENT, getConsentTexts, parseConsent, REJECT_ALL_CONSENT, serializeConsent, setDefaultConsent, updateConsent } from './modules/consent/index.js';
export { archiveFieldName, buildArchivePath, buildEntryPath, getArchiveEntries, parsePageParam, resolveRoute } from './modules/content/index.js';
// Imported straight from the file, NOT from ./modules/email/index.js — that
// barrel re-exports sendEmail, which imports 'server-only' and would crash when
// Payload loads the config (or runs generate:importmap) as a plain Node script.
export { panelSmtpAdapter } from './modules/email/panelSmtpAdapter.js';
export { buildFormsPlugin } from './modules/forms/formsPluginConfig.js';
export { createContentHelpers } from './modules/frontend/index.js';
export { buildLocalizedPath, getDefaultLocale, getLocaleCodes, getLocaleDefinition, getLocalizedSlugs, isValidLocale, LOCALE_COOKIE_NAME, matchAcceptLanguage, negotiateLocale, switchLocalePath } from './modules/i18n/index.js';
export { createLocaleMiddleware, DEFAULT_MIDDLEWARE_MATCHER } from './modules/i18n/index.js';
export { ALL_SYSTEM_PAGE_ROLES, getSystemPagePath } from './modules/pages/index.js';
export { getGlobal, getSiteIntegrations, getSiteSettings, SITE_INTEGRATIONS_SLUG, SITE_SETTINGS_SLUG } from './modules/payload/index.js';
export { buildHreflangAlternates, buildMetadata, composeTitle } from './modules/seo/index.js';
export { buildAutoFillMetaHook, buildRobots, buildSitemapEntries, createMetadataGenerator, createPageMetadata, injectAutoFillMeta } from './modules/seo/index.js';
export { buildSlugField, toSlug } from './modules/slug/index.js';
export { ipalKit } from './plugin.js';
//# sourceMappingURL=index.js.map
+1
View File
File diff suppressed because one or more lines are too long
+3
View File
@@ -0,0 +1,3 @@
/** Requires at least the given role, for field-level access. */ export { };
//# sourceMappingURL=access.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["access.d.ts"],"sourcesContent":["import type { Access, FieldAccess } from 'payload';\nimport type { Role } from './types.js';\n/**\n * Collection-level access (returns boolean | Where).\n * Use in collection `access.read/create/update/delete`.\n */\nexport declare const adminOnly: Access;\nexport declare const adminOrEditor: Access;\nexport declare const authenticated: Access;\n/** Requires at least the given role. */\nexport declare const requireRole: (minimum: Role) => Access;\n/** Admins see all; others are constrained to their own document. */\nexport declare const adminOrSelf: Access;\n/**\n * Field-level access (returns boolean only — no Where support).\n * Use in field `access.read/update`.\n */\nexport declare const adminOnlyField: FieldAccess;\nexport declare const adminOrEditorField: FieldAccess;\n/** Requires at least the given role, for field-level access. */\nexport declare const requireRoleField: (minimum: Role) => FieldAccess;\n"],"names":[],"mappings":"AAmBA,8DAA8D,GAC9D,WAAsE"}
+21
View File
@@ -0,0 +1,21 @@
import type { Access, FieldAccess } from 'payload';
import type { Role } from './types.js';
/**
* Collection-level access (returns boolean | Where).
* Use in collection `access.read/create/update/delete`.
*/
export declare const adminOnly: Access;
export declare const adminOrEditor: Access;
export declare const authenticated: Access;
/** Requires at least the given role. */
export declare const requireRole: (minimum: Role) => Access;
/** Admins see all; others are constrained to their own document. */
export declare const adminOrSelf: Access;
/**
* Field-level access (returns boolean only — no Where support).
* Use in field `access.read/update`.
*/
export declare const adminOnlyField: FieldAccess;
export declare const adminOrEditorField: FieldAccess;
/** Requires at least the given role, for field-level access. */
export declare const requireRoleField: (minimum: Role) => FieldAccess;
+29
View File
@@ -0,0 +1,29 @@
import { hasMinimumRole, isAdmin } from './predicates.js';
/**
* Collection-level access (returns boolean | Where).
* Use in collection `access.read/create/update/delete`.
*/ export const adminOnly = ({ req: { user } })=>isAdmin(user);
export const adminOrEditor = ({ req: { user } })=>hasMinimumRole(user, 'editor');
export const authenticated = ({ req: { user } })=>Boolean(user);
/** Requires at least the given role. */ export const requireRole = (minimum)=>({ req: { user } })=>hasMinimumRole(user, minimum);
/** Admins see all; others are constrained to their own document. */ export const adminOrSelf = ({ req: { user } })=>{
if (isAdmin(user)) {
return true;
}
if (!user) {
return false;
}
return {
id: {
equals: user.id
}
};
};
/**
* Field-level access (returns boolean only — no Where support).
* Use in field `access.read/update`.
*/ export const adminOnlyField = ({ req: { user } })=>isAdmin(user);
export const adminOrEditorField = ({ req: { user } })=>hasMinimumRole(user, 'editor');
/** Requires at least the given role, for field-level access. */ export const requireRoleField = (minimum)=>({ req: { user } })=>hasMinimumRole(user, minimum);
//# sourceMappingURL=access.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../src/modules/access/access.ts"],"sourcesContent":["import type { Access, FieldAccess } from 'payload'\n\nimport type { Role } from './types.js'\n\nimport { hasMinimumRole, isAdmin } from './predicates.js'\n\n/**\n * Collection-level access (returns boolean | Where).\n * Use in collection `access.read/create/update/delete`.\n */\nexport const adminOnly: Access = ({ req: { user } }) => isAdmin(user)\n\nexport const adminOrEditor: Access = ({ req: { user } }) => hasMinimumRole(user, 'editor')\n\nexport const authenticated: Access = ({ req: { user } }) => Boolean(user)\n\n/** Requires at least the given role. */\nexport const requireRole =\n (minimum: Role): Access =>\n ({ req: { user } }) =>\n hasMinimumRole(user, minimum)\n\n/** Admins see all; others are constrained to their own document. */\nexport const adminOrSelf: Access = ({ req: { user } }) => {\n if (isAdmin(user)) {return true}\n if (!user) {return false}\n return { id: { equals: user.id } }\n}\n\n/**\n * Field-level access (returns boolean only — no Where support).\n * Use in field `access.read/update`.\n */\nexport const adminOnlyField: FieldAccess = ({ req: { user } }) => isAdmin(user)\n\nexport const adminOrEditorField: FieldAccess = ({ req: { user } }) => hasMinimumRole(user, 'editor')\n\n/** Requires at least the given role, for field-level access. */\nexport const requireRoleField =\n (minimum: Role): FieldAccess =>\n ({ req: { user } }) =>\n hasMinimumRole(user, minimum)\n"],"names":["hasMinimumRole","isAdmin","adminOnly","req","user","adminOrEditor","authenticated","Boolean","requireRole","minimum","adminOrSelf","id","equals","adminOnlyField","adminOrEditorField","requireRoleField"],"mappings":"AAIA,SAASA,cAAc,EAAEC,OAAO,QAAQ,kBAAiB;AAEzD;;;CAGC,GACD,OAAO,MAAMC,YAAoB,CAAC,EAAEC,KAAK,EAAEC,IAAI,EAAE,EAAE,GAAKH,QAAQG,MAAK;AAErE,OAAO,MAAMC,gBAAwB,CAAC,EAAEF,KAAK,EAAEC,IAAI,EAAE,EAAE,GAAKJ,eAAeI,MAAM,UAAS;AAE1F,OAAO,MAAME,gBAAwB,CAAC,EAAEH,KAAK,EAAEC,IAAI,EAAE,EAAE,GAAKG,QAAQH,MAAK;AAEzE,sCAAsC,GACtC,OAAO,MAAMI,cACX,CAACC,UACD,CAAC,EAAEN,KAAK,EAAEC,IAAI,EAAE,EAAE,GAChBJ,eAAeI,MAAMK,SAAQ;AAEjC,kEAAkE,GAClE,OAAO,MAAMC,cAAsB,CAAC,EAAEP,KAAK,EAAEC,IAAI,EAAE,EAAE;IACnD,IAAIH,QAAQG,OAAO;QAAC,OAAO;IAAI;IAC/B,IAAI,CAACA,MAAM;QAAC,OAAO;IAAK;IACxB,OAAO;QAAEO,IAAI;YAAEC,QAAQR,KAAKO,EAAE;QAAC;IAAE;AACnC,EAAC;AAED;;;CAGC,GACD,OAAO,MAAME,iBAA8B,CAAC,EAAEV,KAAK,EAAEC,IAAI,EAAE,EAAE,GAAKH,QAAQG,MAAK;AAE/E,OAAO,MAAMU,qBAAkC,CAAC,EAAEX,KAAK,EAAEC,IAAI,EAAE,EAAE,GAAKJ,eAAeI,MAAM,UAAS;AAEpG,8DAA8D,GAC9D,OAAO,MAAMW,mBACX,CAACN,UACD,CAAC,EAAEN,KAAK,EAAEC,IAAI,EAAE,EAAE,GAChBJ,eAAeI,MAAMK,SAAQ"}
+7
View File
@@ -0,0 +1,7 @@
export { adminOnly, adminOnlyField, adminOrEditor, adminOrEditorField, adminOrSelf, authenticated, requireRole, requireRoleField } from './access.js';
export { injectRoles } from './injectRoles.js';
export { hasMinimumRole, isAdmin, isEditor } from './predicates.js';
export { buildRolesField } from './rolesField.js';
export { ROLE_HIERARCHY } from './types.js';
//# sourceMappingURL=index.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["index.d.ts"],"sourcesContent":["export { adminOnly, adminOnlyField, adminOrEditor, adminOrEditorField, adminOrSelf, authenticated, requireRole, requireRoleField, } from './access.js';\nexport { injectRoles } from './injectRoles.js';\nexport { hasMinimumRole, isAdmin, isEditor } from './predicates.js';\nexport { buildRolesField } from './rolesField.js';\nexport type { AccessOption, Role } from './types.js';\nexport { ROLE_HIERARCHY } from './types.js';\n"],"names":["adminOnly","adminOnlyField","adminOrEditor","adminOrEditorField","adminOrSelf","authenticated","requireRole","requireRoleField","injectRoles","hasMinimumRole","isAdmin","isEditor","buildRolesField","ROLE_HIERARCHY"],"mappings":"AAAA,SAASA,SAAS,EAAEC,cAAc,EAAEC,aAAa,EAAEC,kBAAkB,EAAEC,WAAW,EAAEC,aAAa,EAAEC,WAAW,EAAEC,gBAAgB,QAAS,cAAc;AACvJ,SAASC,WAAW,QAAQ,mBAAmB;AAC/C,SAASC,cAAc,EAAEC,OAAO,EAAEC,QAAQ,QAAQ,kBAAkB;AACpE,SAASC,eAAe,QAAQ,kBAAkB;AAElD,SAASC,cAAc,QAAQ,aAAa"}
+6
View File
@@ -0,0 +1,6 @@
export { adminOnly, adminOnlyField, adminOrEditor, adminOrEditorField, adminOrSelf, authenticated, requireRole, requireRoleField, } from './access.js';
export { injectRoles } from './injectRoles.js';
export { hasMinimumRole, isAdmin, isEditor } from './predicates.js';
export { buildRolesField } from './rolesField.js';
export type { AccessOption, Role } from './types.js';
export { ROLE_HIERARCHY } from './types.js';
+7
View File
@@ -0,0 +1,7 @@
export { adminOnly, adminOnlyField, adminOrEditor, adminOrEditorField, adminOrSelf, authenticated, requireRole, requireRoleField } from './access.js';
export { injectRoles } from './injectRoles.js';
export { hasMinimumRole, isAdmin, isEditor } from './predicates.js';
export { buildRolesField } from './rolesField.js';
export { ROLE_HIERARCHY } from './types.js';
//# sourceMappingURL=index.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../src/modules/access/index.ts"],"sourcesContent":["export {\n adminOnly,\n adminOnlyField,\n adminOrEditor,\n adminOrEditorField,\n adminOrSelf,\n authenticated,\n requireRole,\n requireRoleField,\n} from './access.js'\nexport { injectRoles } from './injectRoles.js'\nexport { hasMinimumRole, isAdmin, isEditor } from './predicates.js'\nexport { buildRolesField } from './rolesField.js'\nexport type { AccessOption, Role } from './types.js'\nexport { ROLE_HIERARCHY } from './types.js'\n"],"names":["adminOnly","adminOnlyField","adminOrEditor","adminOrEditorField","adminOrSelf","authenticated","requireRole","requireRoleField","injectRoles","hasMinimumRole","isAdmin","isEditor","buildRolesField","ROLE_HIERARCHY"],"mappings":"AAAA,SACEA,SAAS,EACTC,cAAc,EACdC,aAAa,EACbC,kBAAkB,EAClBC,WAAW,EACXC,aAAa,EACbC,WAAW,EACXC,gBAAgB,QACX,cAAa;AACpB,SAASC,WAAW,QAAQ,mBAAkB;AAC9C,SAASC,cAAc,EAAEC,OAAO,EAAEC,QAAQ,QAAQ,kBAAiB;AACnE,SAASC,eAAe,QAAQ,kBAAiB;AAEjD,SAASC,cAAc,QAAQ,aAAY"}
+9
View File
@@ -0,0 +1,9 @@
/**
* Injects the fixed `roles` field into the client's auth collection.
*
* The plugin owns the role definition; the client owns the collection. This
* finds the collection by slug and appends the field. We control the whole
* stack, so no conflict handling is needed — the field is simply added.
*/ export { };
//# sourceMappingURL=injectRoles.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["injectRoles.d.ts"],"sourcesContent":["import type { Config } from 'payload';\nimport type { AccessOption } from './types.js';\n/**\n * Injects the fixed `roles` field into the client's auth collection.\n *\n * The plugin owns the role definition; the client owns the collection. This\n * finds the collection by slug and appends the field. We control the whole\n * stack, so no conflict handling is needed — the field is simply added.\n */\nexport declare function injectRoles(config: Config, access: AccessOption): Config;\n"],"names":[],"mappings":"AAEA;;;;;;CAMC,GACD,WAAkF"}
+10
View File
@@ -0,0 +1,10 @@
import type { Config } from 'payload';
import type { AccessOption } from './types.js';
/**
* Injects the fixed `roles` field into the client's auth collection.
*
* The plugin owns the role definition; the client owns the collection. This
* finds the collection by slug and appends the field. We control the whole
* stack, so no conflict handling is needed — the field is simply added.
*/
export declare function injectRoles(config: Config, access: AccessOption): Config;
+27
View File
@@ -0,0 +1,27 @@
import { buildRolesField } from './rolesField.js';
/**
* Injects the fixed `roles` field into the client's auth collection.
*
* The plugin owns the role definition; the client owns the collection. This
* finds the collection by slug and appends the field. We control the whole
* stack, so no conflict handling is needed — the field is simply added.
*/ export function injectRoles(config, access) {
const rolesField = buildRolesField(access.defaultRole);
return {
...config,
collections: (config.collections ?? []).map((collection)=>{
if (collection.slug !== access.authCollection) {
return collection;
}
return {
...collection,
fields: [
...collection.fields,
rolesField
]
};
})
};
}
//# sourceMappingURL=injectRoles.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../src/modules/access/injectRoles.ts"],"sourcesContent":["import type { Config } from 'payload'\n\nimport type { AccessOption } from './types.js'\n\nimport { buildRolesField } from './rolesField.js'\n\n/**\n * Injects the fixed `roles` field into the client's auth collection.\n *\n * The plugin owns the role definition; the client owns the collection. This\n * finds the collection by slug and appends the field. We control the whole\n * stack, so no conflict handling is needed — the field is simply added.\n */\nexport function injectRoles(config: Config, access: AccessOption): Config {\n const rolesField = buildRolesField(access.defaultRole)\n\n return {\n ...config,\n collections: (config.collections ?? []).map((collection) => {\n if (collection.slug !== access.authCollection) {\n return collection\n }\n return {\n ...collection,\n fields: [...collection.fields, rolesField],\n }\n }),\n }\n}\n"],"names":["buildRolesField","injectRoles","config","access","rolesField","defaultRole","collections","map","collection","slug","authCollection","fields"],"mappings":"AAIA,SAASA,eAAe,QAAQ,kBAAiB;AAEjD;;;;;;CAMC,GACD,OAAO,SAASC,YAAYC,MAAc,EAAEC,MAAoB;IAC9D,MAAMC,aAAaJ,gBAAgBG,OAAOE,WAAW;IAErD,OAAO;QACL,GAAGH,MAAM;QACTI,aAAa,AAACJ,CAAAA,OAAOI,WAAW,IAAI,EAAE,AAAD,EAAGC,GAAG,CAAC,CAACC;YAC3C,IAAIA,WAAWC,IAAI,KAAKN,OAAOO,cAAc,EAAE;gBAC7C,OAAOF;YACT;YACA,OAAO;gBACL,GAAGA,UAAU;gBACbG,QAAQ;uBAAIH,WAAWG,MAAM;oBAAEP;iBAAW;YAC5C;QACF;IACF;AACF"}
+3
View File
@@ -0,0 +1,3 @@
export { };
//# sourceMappingURL=predicates.d.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["predicates.d.ts"],"sourcesContent":["import type { Role } from './types.js';\n/**\n * The plugin can't know the client's generated User type, and Payload types\n * `req.user` loosely (UntypedUser | null). Predicates therefore accept an\n * unknown-ish user and read `roles` defensively — no assumptions about shape\n * beyond an optional roles array.\n */\ntype MaybeUser = {\n roles?: null | Role[];\n} | null | Record<string, unknown> | undefined;\n/**\n * True if the user holds at least the given role in the hierarchy.\n * admin satisfies 'editor' and 'user'; editor satisfies 'user'.\n */\nexport declare function hasMinimumRole(user: MaybeUser, minimum: Role): boolean;\n/** True if the user is an admin. */\nexport declare function isAdmin(user: MaybeUser): boolean;\n/** True if the user is an editor or higher (editor, admin). */\nexport declare function isEditor(user: MaybeUser): boolean;\nexport {};\n"],"names":[],"mappings":"AAmBA,WAAU"}
+20
View File
@@ -0,0 +1,20 @@
import type { Role } from './types.js';
/**
* The plugin can't know the client's generated User type, and Payload types
* `req.user` loosely (UntypedUser | null). Predicates therefore accept an
* unknown-ish user and read `roles` defensively — no assumptions about shape
* beyond an optional roles array.
*/
type MaybeUser = {
roles?: null | Role[];
} | null | Record<string, unknown> | undefined;
/**
* True if the user holds at least the given role in the hierarchy.
* admin satisfies 'editor' and 'user'; editor satisfies 'user'.
*/
export declare function hasMinimumRole(user: MaybeUser, minimum: Role): boolean;
/** True if the user is an admin. */
export declare function isAdmin(user: MaybeUser): boolean;
/** True if the user is an editor or higher (editor, admin). */
export declare function isEditor(user: MaybeUser): boolean;
export {};
+32
View File
@@ -0,0 +1,32 @@
import { ROLE_HIERARCHY } from './types.js';
/** Safely extracts the roles array from a loosely-typed user. */ function getRoles(user) {
if (!user || typeof user !== 'object') {
return [];
}
const roles = user.roles;
if (!Array.isArray(roles)) {
return [];
}
return roles.filter((role)=>ROLE_HIERARCHY.includes(role));
}
/** Highest-privilege role index the user holds, or -1 if none. */ function highestRoleIndex(user) {
const roles = getRoles(user);
if (!roles.length) {
return -1;
}
return Math.max(...roles.map((role)=>ROLE_HIERARCHY.indexOf(role)));
}
/**
* True if the user holds at least the given role in the hierarchy.
* admin satisfies 'editor' and 'user'; editor satisfies 'user'.
*/ export function hasMinimumRole(user, minimum) {
return highestRoleIndex(user) >= ROLE_HIERARCHY.indexOf(minimum);
}
/** True if the user is an admin. */ export function isAdmin(user) {
return hasMinimumRole(user, 'admin');
}
/** True if the user is an editor or higher (editor, admin). */ export function isEditor(user) {
return hasMinimumRole(user, 'editor');
}
//# sourceMappingURL=predicates.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"sources":["../../../src/modules/access/predicates.ts"],"sourcesContent":["import type { Role } from './types.js'\n\nimport { ROLE_HIERARCHY } from './types.js'\n\n/**\n * The plugin can't know the client's generated User type, and Payload types\n * `req.user` loosely (UntypedUser | null). Predicates therefore accept an\n * unknown-ish user and read `roles` defensively — no assumptions about shape\n * beyond an optional roles array.\n */\ntype MaybeUser = { roles?: null | Role[] } | null | Record<string, unknown> | undefined\n\n/** Safely extracts the roles array from a loosely-typed user. */\nfunction getRoles(user: MaybeUser): Role[] {\n if (!user || typeof user !== 'object') {return []}\n const roles = (user as { roles?: unknown }).roles\n if (!Array.isArray(roles)) {return []}\n return roles.filter((role): role is Role => ROLE_HIERARCHY.includes(role as Role))\n}\n\n/** Highest-privilege role index the user holds, or -1 if none. */\nfunction highestRoleIndex(user: MaybeUser): number {\n const roles = getRoles(user)\n if (!roles.length) {return -1}\n return Math.max(...roles.map((role) => ROLE_HIERARCHY.indexOf(role)))\n}\n\n/**\n * True if the user holds at least the given role in the hierarchy.\n * admin satisfies 'editor' and 'user'; editor satisfies 'user'.\n */\nexport function hasMinimumRole(user: MaybeUser, minimum: Role): boolean {\n return highestRoleIndex(user) >= ROLE_HIERARCHY.indexOf(minimum)\n}\n\n/** True if the user is an admin. */\nexport function isAdmin(user: MaybeUser): boolean {\n return hasMinimumRole(user, 'admin')\n}\n\n/** True if the user is an editor or higher (editor, admin). */\nexport function isEditor(user: MaybeUser): boolean {\n return hasMinimumRole(user, 'editor')\n}\n"],"names":["ROLE_HIERARCHY","getRoles","user","roles","Array","isArray","filter","role","includes","highestRoleIndex","length","Math","max","map","indexOf","hasMinimumRole","minimum","isAdmin","isEditor"],"mappings":"AAEA,SAASA,cAAc,QAAQ,aAAY;AAU3C,+DAA+D,GAC/D,SAASC,SAASC,IAAe;IAC/B,IAAI,CAACA,QAAQ,OAAOA,SAAS,UAAU;QAAC,OAAO,EAAE;IAAA;IACjD,MAAMC,QAAQ,AAACD,KAA6BC,KAAK;IACjD,IAAI,CAACC,MAAMC,OAAO,CAACF,QAAQ;QAAC,OAAO,EAAE;IAAA;IACrC,OAAOA,MAAMG,MAAM,CAAC,CAACC,OAAuBP,eAAeQ,QAAQ,CAACD;AACtE;AAEA,gEAAgE,GAChE,SAASE,iBAAiBP,IAAe;IACvC,MAAMC,QAAQF,SAASC;IACvB,IAAI,CAACC,MAAMO,MAAM,EAAE;QAAC,OAAO,CAAC;IAAC;IAC7B,OAAOC,KAAKC,GAAG,IAAIT,MAAMU,GAAG,CAAC,CAACN,OAASP,eAAec,OAAO,CAACP;AAChE;AAEA;;;CAGC,GACD,OAAO,SAASQ,eAAeb,IAAe,EAAEc,OAAa;IAC3D,OAAOP,iBAAiBP,SAASF,eAAec,OAAO,CAACE;AAC1D;AAEA,kCAAkC,GAClC,OAAO,SAASC,QAAQf,IAAe;IACrC,OAAOa,eAAeb,MAAM;AAC9B;AAEA,6DAA6D,GAC7D,OAAO,SAASgB,SAAShB,IAAe;IACtC,OAAOa,eAAeb,MAAM;AAC9B"}

Some files were not shown because too many files have changed in this diff Show More