@forumone/throughline 1.0.0-next.0 → 1.0.0-next.2
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/CHANGELOG.md +46 -0
- package/README.md +70 -324
- package/bin/throughline.mjs +6 -0
- package/dist/approvals/tokens.d.ts +2 -2
- package/dist/approvals/tokens.d.ts.map +1 -1
- package/dist/approvals/tokens.js +2 -2
- package/dist/audit/query/options.d.ts +6 -4
- package/dist/audit/query/options.d.ts.map +1 -1
- package/dist/audit/query/options.js.map +1 -1
- package/dist/audit/query/plugin.d.ts.map +1 -1
- package/dist/audit/query/plugin.js +5 -1
- package/dist/audit/query/plugin.js.map +1 -1
- package/dist/audit/query/tools/get-change-history.d.ts +3 -1
- package/dist/audit/query/tools/get-change-history.d.ts.map +1 -1
- package/dist/audit/query/tools/get-change-history.js +2 -2
- package/dist/audit/query/tools/get-change-history.js.map +1 -1
- package/dist/audit/query/tools/get-recent-failures.d.ts +3 -1
- package/dist/audit/query/tools/get-recent-failures.d.ts.map +1 -1
- package/dist/audit/query/tools/get-recent-failures.js +2 -2
- package/dist/audit/query/tools/get-recent-failures.js.map +1 -1
- package/dist/audit/query/tools/query-audit.d.ts +5 -3
- package/dist/audit/query/tools/query-audit.d.ts.map +1 -1
- package/dist/audit/query/tools/query-audit.js +2 -2
- package/dist/audit/query/tools/query-audit.js.map +1 -1
- package/dist/audit/query/tools/what-changed-in-range.d.ts +3 -1
- package/dist/audit/query/tools/what-changed-in-range.d.ts.map +1 -1
- package/dist/audit/query/tools/what-changed-in-range.js +2 -2
- package/dist/audit/query/tools/what-changed-in-range.js.map +1 -1
- package/dist/audit/query/tools/who-changed-what.d.ts +3 -1
- package/dist/audit/query/tools/who-changed-what.d.ts.map +1 -1
- package/dist/audit/query/tools/who-changed-what.js +2 -2
- package/dist/audit/query/tools/who-changed-what.js.map +1 -1
- package/dist/components/manifest-source.d.ts +1 -1
- package/dist/components/manifest-source.d.ts.map +1 -1
- package/dist/components/manifest-source.js +1 -1
- package/dist/components/manifest-source.js.map +1 -1
- package/dist/components/matching/tfidf.d.ts +1 -1
- package/dist/components/matching/tfidf.d.ts.map +1 -1
- package/dist/components/matching/types.d.ts +1 -1
- package/dist/components/matching/types.d.ts.map +1 -1
- package/dist/components/options.d.ts +1 -1
- package/dist/components/options.d.ts.map +1 -1
- package/dist/components/validation/composition.d.ts +1 -1
- package/dist/components/validation/composition.d.ts.map +1 -1
- package/dist/email/client.d.ts.map +1 -1
- package/dist/email/client.js +3 -2
- package/dist/email/client.js.map +1 -1
- package/dist/email/functions/_shared.d.ts +6 -0
- package/dist/email/functions/_shared.d.ts.map +1 -1
- package/dist/email/functions/_shared.js +9 -0
- package/dist/email/functions/_shared.js.map +1 -1
- package/dist/email/functions/notify-approval-decision.d.ts.map +1 -1
- package/dist/email/functions/notify-approval-decision.js +2 -1
- package/dist/email/functions/notify-approval-decision.js.map +1 -1
- package/dist/email/functions/notify-approval-expired.d.ts.map +1 -1
- package/dist/email/functions/notify-approval-expired.js +2 -1
- package/dist/email/functions/notify-approval-expired.js.map +1 -1
- package/dist/email/functions/notify-approval-request.d.ts.map +1 -1
- package/dist/email/functions/notify-approval-request.js +2 -1
- package/dist/email/functions/notify-approval-request.js.map +1 -1
- package/dist/email/index.d.ts +1 -1
- package/dist/email/index.d.ts.map +1 -1
- package/dist/email/index.js +1 -1
- package/dist/email/index.js.map +1 -1
- package/dist/email/options.js +1 -1
- package/dist/email/options.js.map +1 -1
- package/dist/env/index.d.ts +0 -1
- package/dist/env/index.d.ts.map +1 -1
- package/dist/env/index.js +0 -1
- package/dist/env/index.js.map +1 -1
- package/dist/index.d.ts +3 -10
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +5 -11
- package/dist/index.js.map +1 -1
- package/dist/integrations/index.d.ts +1 -1
- package/dist/integrations/index.d.ts.map +1 -1
- package/dist/integrations/index.js +1 -1
- package/dist/integrations/index.js.map +1 -1
- package/dist/integrations/integrations/webhook/config-fields.d.ts.map +1 -1
- package/dist/integrations/integrations/webhook/config-fields.js +3 -0
- package/dist/integrations/integrations/webhook/config-fields.js.map +1 -1
- package/dist/integrations/integrations/webhook/functions.d.ts.map +1 -1
- package/dist/integrations/integrations/webhook/functions.js +0 -1
- package/dist/integrations/integrations/webhook/functions.js.map +1 -1
- package/dist/integrations/integrations/webhook/index.d.ts.map +1 -1
- package/dist/integrations/integrations/webhook/index.js +0 -1
- package/dist/integrations/integrations/webhook/index.js.map +1 -1
- package/dist/integrations/jobs/healthcheck.js +1 -1
- package/dist/integrations/jobs/healthcheck.js.map +1 -1
- package/dist/integrations/plugin.js +1 -1
- package/dist/integrations/plugin.js.map +1 -1
- package/dist/integrations/registry.d.ts +1 -1
- package/dist/integrations/registry.js +1 -1
- package/dist/integrations/types.d.ts +11 -9
- package/dist/integrations/types.d.ts.map +1 -1
- package/dist/jobs/failure-handler.d.ts.map +1 -1
- package/dist/jobs/failure-handler.js +5 -2
- package/dist/jobs/failure-handler.js.map +1 -1
- package/dist/jobs/workflow-types.d.ts +5 -1
- package/dist/jobs/workflow-types.d.ts.map +1 -1
- package/dist/mcp/audit-server.js +1 -1
- package/dist/mcp/audit-server.js.map +1 -1
- package/dist/mcp/meta.d.ts +8 -8
- package/dist/migrate/cli.d.ts +9 -0
- package/dist/migrate/cli.d.ts.map +1 -0
- package/dist/migrate/cli.js +105 -0
- package/dist/migrate/cli.js.map +1 -0
- package/dist/migrate/exports.json +601 -0
- package/dist/migrate/rewrite.d.ts +28 -0
- package/dist/migrate/rewrite.d.ts.map +1 -0
- package/dist/migrate/rewrite.js +188 -0
- package/dist/migrate/rewrite.js.map +1 -0
- package/dist/observability/collection.d.ts +3 -0
- package/dist/observability/collection.d.ts.map +1 -1
- package/dist/observability/collection.js +2 -0
- package/dist/observability/collection.js.map +1 -1
- package/dist/publishing/hooks/block-status-writes.d.ts +32 -0
- package/dist/publishing/hooks/block-status-writes.d.ts.map +1 -1
- package/dist/publishing/hooks/block-status-writes.js +52 -9
- package/dist/publishing/hooks/block-status-writes.js.map +1 -1
- package/dist/publishing/index.d.ts +6 -0
- package/dist/publishing/index.d.ts.map +1 -1
- package/dist/publishing/index.js +6 -0
- package/dist/publishing/index.js.map +1 -1
- package/dist/publishing/pipeline/steps/accessibility.d.ts +4 -3
- package/dist/publishing/pipeline/steps/accessibility.d.ts.map +1 -1
- package/dist/publishing/pipeline/steps/accessibility.js +10 -4
- package/dist/publishing/pipeline/steps/accessibility.js.map +1 -1
- package/dist/publishing/pipeline/steps/approval.js +1 -1
- package/dist/publishing/pipeline/steps/approval.js.map +1 -1
- package/dist/throughline.d.ts +123 -0
- package/dist/throughline.d.ts.map +1 -0
- package/dist/throughline.js +190 -0
- package/dist/throughline.js.map +1 -0
- package/dist/utils/optionalPeer.d.ts +12 -0
- package/dist/utils/optionalPeer.d.ts.map +1 -0
- package/dist/utils/optionalPeer.js +28 -0
- package/dist/utils/optionalPeer.js.map +1 -0
- package/package.json +33 -17
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
import type { CollectionSlug, Plugin } from 'payload';
|
|
2
|
+
import type { ApprovalsPluginOptions } from './approvals/options.js';
|
|
3
|
+
import { type AuditPluginOptions } from './audit/plugin.js';
|
|
4
|
+
import type { AuditQueryPluginOptions } from './audit/query/options.js';
|
|
5
|
+
import type { ComponentsPluginOptions } from './components/options.js';
|
|
6
|
+
import { type EditorialPluginOptions } from './editorial/plugin.js';
|
|
7
|
+
import type { WorkOptions } from './editorial/work/work.js';
|
|
8
|
+
import type { EmailPluginOptions } from './email/options.js';
|
|
9
|
+
import type { IntegrationsPluginOptions } from './integrations/options.js';
|
|
10
|
+
import type { Job, JobsAdapter } from './jobs/types.js';
|
|
11
|
+
import type { AuditEventEchoOptions, ExecuteScheduledPublishesOptions, ExpireStaleApprovalsOptions, HealthcheckOptions, PublishAtScheduledTimeOptions, RevalidateOnPublishOptions, ScheduledPublishRequest, ScheduledPublishResult } from './jobs/workflow-types.js';
|
|
12
|
+
import type { PayloadMcpTool } from './mcp/payload-mcp.js';
|
|
13
|
+
import { type JobFailuresPluginOptions } from './observability/plugin.js';
|
|
14
|
+
import type { PluginAdminOptions } from './plugin-contract/admin.js';
|
|
15
|
+
import type { Logger } from './plugin-contract/index.js';
|
|
16
|
+
import type { McpToolContext } from './plugin-contract/mcp.js';
|
|
17
|
+
import type { PublishableCollection, PublishingPluginOptions } from './publishing/options.js';
|
|
18
|
+
import { type ReferencesPluginOptions } from './references/plugin.js';
|
|
19
|
+
/** The scheduled-publish callback the scheduling jobs call for each due document. */
|
|
20
|
+
type ScheduledPublish = (request: ScheduledPublishRequest, context: Parameters<PublishAtScheduledTimeOptions['publish']>[1]) => Promise<ScheduledPublishResult>;
|
|
21
|
+
/** What only `throughline()` supplies, so a site does not pass it. */
|
|
22
|
+
type Supplied = 'enabled' | 'mcpTools' | 'inngest' | 'emit' | 'logger';
|
|
23
|
+
export interface ThroughlineOptions {
|
|
24
|
+
/**
|
|
25
|
+
* The jobs adapter: `inngestJobs(inngest)` or `payloadJobs()`. Every plugin
|
|
26
|
+
* that announces events sends them through it. On Payload Jobs the suite's
|
|
27
|
+
* jobs are registered with it too; on Inngest the site serves `suite.jobs`
|
|
28
|
+
* from its own endpoint.
|
|
29
|
+
*/
|
|
30
|
+
jobs: JobsAdapter;
|
|
31
|
+
/**
|
|
32
|
+
* The content collections the suite governs: what publishing gates, what
|
|
33
|
+
* "Your work" lists, and what the scheduling jobs publish.
|
|
34
|
+
*/
|
|
35
|
+
collections: readonly CollectionSlug[];
|
|
36
|
+
/** The sidebar group for every collection the suite adds, unless a plugin's own `admin` says otherwise. */
|
|
37
|
+
admin?: PluginAdminOptions;
|
|
38
|
+
/** For every plugin's diagnostics. */
|
|
39
|
+
logger?: Logger;
|
|
40
|
+
/** The audit log. Always on: every other plugin needs it. */
|
|
41
|
+
audit?: Omit<AuditPluginOptions, Supplied>;
|
|
42
|
+
/** Where a job that ran out of retries is recorded. Always on. */
|
|
43
|
+
jobFailures?: Omit<JobFailuresPluginOptions, Supplied>;
|
|
44
|
+
/** `check_slug`. Always on. */
|
|
45
|
+
fields?: {
|
|
46
|
+
canUse?: (ctx: McpToolContext) => boolean;
|
|
47
|
+
};
|
|
48
|
+
/** On when present: the design system's components over MCP. */
|
|
49
|
+
components?: Omit<ComponentsPluginOptions, Supplied>;
|
|
50
|
+
/** On when present: the publish pipeline, revalidation and scheduled publishing. */
|
|
51
|
+
publishing?: ThroughlinePublishingOptions;
|
|
52
|
+
/** On when present: approval requests, their links and their expiry. */
|
|
53
|
+
approvals?: Omit<ApprovalsPluginOptions, Supplied> & {
|
|
54
|
+
/** The expiry job's own options. */
|
|
55
|
+
expiry?: Omit<ExpireStaleApprovalsOptions, 'payload' | 'collectionSlug'>;
|
|
56
|
+
};
|
|
57
|
+
/** On when present: the audit log's MCP query tools. */
|
|
58
|
+
auditQuery?: Omit<AuditQueryPluginOptions, Supplied | 'collectionSlug'>;
|
|
59
|
+
/**
|
|
60
|
+
* On when present: approval notifications. `buildActionUrl` defaults to a
|
|
61
|
+
* link signed with approvals' secret, against approvals' public URL.
|
|
62
|
+
*/
|
|
63
|
+
email?: Omit<EmailPluginOptions, Supplied | 'approvalsCollectionSlug' | 'onTerminalFailure' | 'buildActionUrl'> & Partial<Pick<EmailPluginOptions, 'buildActionUrl'>>;
|
|
64
|
+
/** On when present: third-party integrations. Each must define `createJobs`. */
|
|
65
|
+
integrations?: Omit<IntegrationsPluginOptions, Supplied | 'onTerminalFailure'>;
|
|
66
|
+
/** On when present: what refers to a document, and the delete guards. */
|
|
67
|
+
references?: Omit<ReferencesPluginOptions, Supplied>;
|
|
68
|
+
/** On when present: content health, the calendar, "Your work" and the palette. */
|
|
69
|
+
editorial?: Omit<EditorialPluginOptions, Supplied | 'work'> & {
|
|
70
|
+
work?: Omit<WorkOptions, 'collections'> & {
|
|
71
|
+
dashboard?: boolean;
|
|
72
|
+
};
|
|
73
|
+
};
|
|
74
|
+
/** On when present: the healthcheck job. */
|
|
75
|
+
healthcheck?: Omit<HealthcheckOptions, 'payload'>;
|
|
76
|
+
/** Extra handlers for the audit echo job, which runs whenever approvals or email are on. */
|
|
77
|
+
auditEcho?: Omit<AuditEventEchoOptions, 'onTerminalFailure'>;
|
|
78
|
+
}
|
|
79
|
+
export interface ThroughlinePublishingOptions extends Omit<PublishingPluginOptions, Supplied | 'collections'> {
|
|
80
|
+
/** The group publishing's required-field step reads `title` and `description` from. Default `seo`. */
|
|
81
|
+
seoField?: string;
|
|
82
|
+
/** Per-collection settings beyond `seoField`, by slug. */
|
|
83
|
+
collectionOptions?: Partial<Record<string, Omit<PublishableCollection, 'slug'>>>;
|
|
84
|
+
/**
|
|
85
|
+
* Where each collection's documents are served, for revalidation. Without
|
|
86
|
+
* it there is no revalidation job: a collection with no builder would have
|
|
87
|
+
* its tags dropped and no path revalidated.
|
|
88
|
+
*/
|
|
89
|
+
urls?: RevalidateOnPublishOptions['urlBuilders'];
|
|
90
|
+
/** The revalidation job's other options. */
|
|
91
|
+
revalidation?: Omit<RevalidateOnPublishOptions, 'payload' | 'urlBuilders'>;
|
|
92
|
+
scheduling?: {
|
|
93
|
+
/** Default: through the publishing service, as `scheduled-publish`. */
|
|
94
|
+
publish?: ScheduledPublish;
|
|
95
|
+
/** The on-time job's own options. */
|
|
96
|
+
onTime?: Omit<PublishAtScheduledTimeOptions, 'payload' | 'collections' | 'publish'>;
|
|
97
|
+
/** The daily backstop for a schedule whose wake-up never arrived, or `false` for none. */
|
|
98
|
+
backstop?: false | Omit<ExecuteScheduledPublishesOptions, 'payload' | 'collections' | 'publish'>;
|
|
99
|
+
};
|
|
100
|
+
}
|
|
101
|
+
export interface ThroughlineSuite {
|
|
102
|
+
/** Every enabled Throughline plugin, in order. Add it before `mcpPlugin`. */
|
|
103
|
+
plugin: Plugin;
|
|
104
|
+
/** For `mcpPlugin({ mcp: { tools: suite.mcpTools } })`. Filled as the plugins load. */
|
|
105
|
+
mcpTools: PayloadMcpTool[];
|
|
106
|
+
/** Every job the options call for. On Inngest, serve them: `inngestJobs(inngest, …).functions(suite.jobs)`. */
|
|
107
|
+
jobs: Job[];
|
|
108
|
+
}
|
|
109
|
+
/**
|
|
110
|
+
* Publishes a due document through the pipeline, as the clock rather than a
|
|
111
|
+
* person, so a scheduled publish passes the same composition, accessibility
|
|
112
|
+
* and approval gates an interactive one does.
|
|
113
|
+
*/
|
|
114
|
+
export declare const publishScheduledThroughPipeline: ScheduledPublish;
|
|
115
|
+
export declare function throughline(options: ThroughlineOptions): ThroughlineSuite;
|
|
116
|
+
/**
|
|
117
|
+
* An approval link signed with approvals' secret, against approvals' public
|
|
118
|
+
* URL: what every site wrote by hand. Each is read when a link is built, so an
|
|
119
|
+
* environment variable set after the config loads still counts.
|
|
120
|
+
*/
|
|
121
|
+
export declare function signedActionUrl(approvals: Pick<ApprovalsPluginOptions, 'tokenSecret' | 'publicUrl'>): EmailPluginOptions['buildActionUrl'];
|
|
122
|
+
export {};
|
|
123
|
+
//# sourceMappingURL=throughline.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"throughline.d.ts","sourceRoot":"","sources":["../src/throughline.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,190 @@
|
|
|
1
|
+
import { approvalsPlugin } from './approvals/plugin.js';
|
|
2
|
+
import { expireStaleApprovalsJob } from './approvals/jobs/expire-stale-approvals.js';
|
|
3
|
+
import { DEFAULT_APPROVALS_SLUG } from './approvals/collection.js';
|
|
4
|
+
import { buildActionUrl, generateActionToken } from './approvals/tokens.js';
|
|
5
|
+
import { auditEventEchoJob } from './audit/jobs/audit-event-echo.js';
|
|
6
|
+
import { auditPlugin } from './audit/plugin.js';
|
|
7
|
+
import { DEFAULT_AUDIT_SLUG } from './audit/collection.js';
|
|
8
|
+
import { auditQueryPlugin } from './audit/query/plugin.js';
|
|
9
|
+
import { componentsPlugin } from './components/plugin.js';
|
|
10
|
+
import { editorialPlugin } from './editorial/plugin.js';
|
|
11
|
+
import { emailJobs, emailPlugin } from './email/plugin.js';
|
|
12
|
+
import { fieldsPlugin } from './fields/checkSlug.js';
|
|
13
|
+
import { healthcheckJob } from './integrations/jobs/healthcheck.js';
|
|
14
|
+
import { integrationsJobs, integrationsPlugin } from './integrations/plugin.js';
|
|
15
|
+
import { eventSenderFor } from './jobs/sender.js';
|
|
16
|
+
import { createHealthcheckFailureHandler } from './jobs/failure-handler.js';
|
|
17
|
+
import { createMcpToolCollector } from './mcp/collector.js';
|
|
18
|
+
import { jobFailuresPlugin } from './observability/plugin.js';
|
|
19
|
+
import { publishingPlugin } from './publishing/plugin.js';
|
|
20
|
+
import { executeScheduledPublishesJob } from './publishing/jobs/execute-scheduled-publishes.js';
|
|
21
|
+
import { publishAtScheduledTimeJob } from './publishing/jobs/publish-at-scheduled-time.js';
|
|
22
|
+
import { revalidateOnPublishJob } from './publishing/jobs/revalidate-on-publish.js';
|
|
23
|
+
import { getPublishingService } from './publishing/service.js';
|
|
24
|
+
import { referencesPlugin } from './references/plugin.js';
|
|
25
|
+
/**
|
|
26
|
+
* Publishes a due document through the pipeline, as the clock rather than a
|
|
27
|
+
* person, so a scheduled publish passes the same composition, accessibility
|
|
28
|
+
* and approval gates an interactive one does.
|
|
29
|
+
*/
|
|
30
|
+
export const publishScheduledThroughPipeline = async ({ collection, id, reasoning }, { payload }) => {
|
|
31
|
+
const outcome = await getPublishingService(payload).publish({
|
|
32
|
+
collection,
|
|
33
|
+
id,
|
|
34
|
+
actor: { apiKeyName: 'scheduled-publish', channel: 'mcp' },
|
|
35
|
+
meta: { reasoning },
|
|
36
|
+
});
|
|
37
|
+
return { published: outcome.published, reason: outcome.reason };
|
|
38
|
+
};
|
|
39
|
+
export function throughline(options) {
|
|
40
|
+
const mcpTools = createMcpToolCollector();
|
|
41
|
+
// Plugins that announce events take an Inngest-shaped sender; this one sends
|
|
42
|
+
// through the adapter, whichever runner it is.
|
|
43
|
+
const inngest = eventSenderFor(options.jobs);
|
|
44
|
+
const logger = options.logger ? { logger: options.logger } : {};
|
|
45
|
+
/** A plugin's own sidebar group, or the suite's. */
|
|
46
|
+
const adminFor = (own) => {
|
|
47
|
+
const group = own?.admin ?? options.admin;
|
|
48
|
+
return group ? { admin: group } : {};
|
|
49
|
+
};
|
|
50
|
+
const auditSlug = options.audit?.slug ?? DEFAULT_AUDIT_SLUG;
|
|
51
|
+
const approvalsSlug = options.approvals?.collectionSlug ?? DEFAULT_APPROVALS_SLUG;
|
|
52
|
+
const collections = options.collections;
|
|
53
|
+
for (const integration of options.integrations?.integrations ?? []) {
|
|
54
|
+
if (!integration.createJobs) {
|
|
55
|
+
throw new Error(`throughline(): integration "${integration.id}" defines no createJobs. ` +
|
|
56
|
+
'throughline() runs integrations through the jobs adapter, so give it a createJobs; ' +
|
|
57
|
+
'a 0.x createFunctions can be derived from it, as the webhook integration does.');
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
if (options.email && !options.email.buildActionUrl && !options.approvals) {
|
|
61
|
+
throw new Error('throughline(): email has no buildActionUrl, and approvals is off, so there is no secret to sign its links with. ' +
|
|
62
|
+
'Turn approvals on or pass email.buildActionUrl.');
|
|
63
|
+
}
|
|
64
|
+
const plugins = [
|
|
65
|
+
auditPlugin({ ...options.audit, ...logger, ...adminFor(options.audit), inngest }),
|
|
66
|
+
jobFailuresPlugin({ ...options.jobFailures, ...logger, ...adminFor(options.jobFailures), mcpTools }),
|
|
67
|
+
];
|
|
68
|
+
if (options.components) {
|
|
69
|
+
plugins.push(componentsPlugin({ ...options.components, ...logger, mcpTools }));
|
|
70
|
+
}
|
|
71
|
+
if (options.publishing) {
|
|
72
|
+
const { seoField, collectionOptions, urls: _urls, revalidation: _r, scheduling: _s, ...rest } = options.publishing;
|
|
73
|
+
plugins.push(publishingPlugin({
|
|
74
|
+
...rest,
|
|
75
|
+
...logger,
|
|
76
|
+
collections: collections.map((slug) => ({
|
|
77
|
+
slug,
|
|
78
|
+
...(seoField ? { seoField } : {}),
|
|
79
|
+
...collectionOptions?.[slug],
|
|
80
|
+
})),
|
|
81
|
+
inngest,
|
|
82
|
+
mcpTools,
|
|
83
|
+
}));
|
|
84
|
+
}
|
|
85
|
+
if (options.approvals) {
|
|
86
|
+
const { expiry: _expiry, ...rest } = options.approvals;
|
|
87
|
+
plugins.push(approvalsPlugin({
|
|
88
|
+
...rest,
|
|
89
|
+
...logger,
|
|
90
|
+
...adminFor(options.approvals),
|
|
91
|
+
collectionSlug: approvalsSlug,
|
|
92
|
+
inngest,
|
|
93
|
+
mcpTools,
|
|
94
|
+
}));
|
|
95
|
+
}
|
|
96
|
+
if (options.auditQuery) {
|
|
97
|
+
plugins.push(auditQueryPlugin({ ...options.auditQuery, ...logger, collectionSlug: auditSlug, mcpTools }));
|
|
98
|
+
}
|
|
99
|
+
const emailOptions = options.email && {
|
|
100
|
+
...options.email,
|
|
101
|
+
...logger,
|
|
102
|
+
approvalsCollectionSlug: approvalsSlug,
|
|
103
|
+
buildActionUrl: options.email.buildActionUrl ?? signedActionUrl(options.approvals ?? {}),
|
|
104
|
+
};
|
|
105
|
+
if (emailOptions)
|
|
106
|
+
plugins.push(emailPlugin(emailOptions));
|
|
107
|
+
if (options.integrations) {
|
|
108
|
+
plugins.push(integrationsPlugin({
|
|
109
|
+
...options.integrations,
|
|
110
|
+
...logger,
|
|
111
|
+
...adminFor(options.integrations),
|
|
112
|
+
emit: (event) => options.jobs.emit(event),
|
|
113
|
+
mcpTools,
|
|
114
|
+
}));
|
|
115
|
+
}
|
|
116
|
+
if (options.references) {
|
|
117
|
+
plugins.push(referencesPlugin({ ...options.references, mcpTools }));
|
|
118
|
+
}
|
|
119
|
+
plugins.push(fieldsPlugin({ ...options.fields, mcpTools }));
|
|
120
|
+
if (options.editorial) {
|
|
121
|
+
const { work, ...rest } = options.editorial;
|
|
122
|
+
plugins.push(editorialPlugin({ ...rest, work: { ...work, collections }, mcpTools }));
|
|
123
|
+
}
|
|
124
|
+
const jobs = suiteJobs(options, { approvalsSlug, emailOptions });
|
|
125
|
+
if (isPayloadJobs(options.jobs))
|
|
126
|
+
plugins.push(options.jobs.plugin(jobs));
|
|
127
|
+
const plugin = async (config) => {
|
|
128
|
+
let next = config;
|
|
129
|
+
for (const each of plugins)
|
|
130
|
+
next = await each(next);
|
|
131
|
+
return next;
|
|
132
|
+
};
|
|
133
|
+
return { plugin, mcpTools: mcpTools.tools, jobs };
|
|
134
|
+
}
|
|
135
|
+
function suiteJobs(options, shared) {
|
|
136
|
+
const jobs = [];
|
|
137
|
+
const scheduled = options.collections.map((slug) => ({ slug }));
|
|
138
|
+
if (options.publishing) {
|
|
139
|
+
const { urls, revalidation, scheduling } = options.publishing;
|
|
140
|
+
if (urls)
|
|
141
|
+
jobs.push(revalidateOnPublishJob({ ...revalidation, urlBuilders: urls }));
|
|
142
|
+
const publish = scheduling?.publish ?? publishScheduledThroughPipeline;
|
|
143
|
+
jobs.push(publishAtScheduledTimeJob({ ...scheduling?.onTime, collections: scheduled, publish }));
|
|
144
|
+
if (scheduling?.backstop !== false) {
|
|
145
|
+
jobs.push(executeScheduledPublishesJob({ ...scheduling?.backstop, collections: scheduled, publish }));
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
if (options.approvals) {
|
|
149
|
+
jobs.push(expireStaleApprovalsJob({
|
|
150
|
+
...options.approvals.expiry,
|
|
151
|
+
collectionSlug: shared.approvalsSlug,
|
|
152
|
+
}));
|
|
153
|
+
}
|
|
154
|
+
if (options.approvals || options.email || options.auditEcho) {
|
|
155
|
+
jobs.push(auditEventEchoJob({ ...options.auditEcho }));
|
|
156
|
+
}
|
|
157
|
+
if (options.healthcheck) {
|
|
158
|
+
jobs.push(healthcheckJob({
|
|
159
|
+
onFailure: createHealthcheckFailureHandler(),
|
|
160
|
+
...options.healthcheck,
|
|
161
|
+
}));
|
|
162
|
+
}
|
|
163
|
+
if (shared.emailOptions)
|
|
164
|
+
jobs.push(...emailJobs(shared.emailOptions));
|
|
165
|
+
if (options.integrations) {
|
|
166
|
+
jobs.push(...integrationsJobs({ integrations: options.integrations.integrations ?? [] }));
|
|
167
|
+
}
|
|
168
|
+
return jobs;
|
|
169
|
+
}
|
|
170
|
+
/**
|
|
171
|
+
* An approval link signed with approvals' secret, against approvals' public
|
|
172
|
+
* URL: what every site wrote by hand. Each is read when a link is built, so an
|
|
173
|
+
* environment variable set after the config loads still counts.
|
|
174
|
+
*/
|
|
175
|
+
export function signedActionUrl(approvals) {
|
|
176
|
+
return async ({ approvalId, action, approverId }) => {
|
|
177
|
+
const secret = approvals.tokenSecret ?? process.env['APPROVAL_TOKEN_SECRET'];
|
|
178
|
+
if (!secret)
|
|
179
|
+
throw new Error('Signing an approval link needs APPROVAL_TOKEN_SECRET, or approvals.tokenSecret.');
|
|
180
|
+
const base = approvals.publicUrl ?? process.env['NEXT_PUBLIC_SERVER_URL'];
|
|
181
|
+
if (!base)
|
|
182
|
+
throw new Error('Building an approval link needs NEXT_PUBLIC_SERVER_URL, or approvals.publicUrl.');
|
|
183
|
+
const token = await generateActionToken({ approvalId, action, approverId, issuedAt: Date.now() }, secret);
|
|
184
|
+
return buildActionUrl(base, token);
|
|
185
|
+
};
|
|
186
|
+
}
|
|
187
|
+
function isPayloadJobs(adapter) {
|
|
188
|
+
return adapter.runner === 'payload';
|
|
189
|
+
}
|
|
190
|
+
//# sourceMappingURL=throughline.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"throughline.js","sourceRoot":"","sources":["../src/throughline.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Loads an optional peer dependency, and turns "Cannot find module" into an
|
|
3
|
+
* error that says which feature needs it and how to install it.
|
|
4
|
+
*
|
|
5
|
+
* `resend`, React Email and `inngest` are optional peers of
|
|
6
|
+
* `@forumone/throughline`: a site that sends no email, or runs on Payload Jobs,
|
|
7
|
+
* never installs them. Each is imported where it is used, when it is used, so
|
|
8
|
+
* the first a site hears of a missing one is the moment that feature runs —
|
|
9
|
+
* and this is what it hears.
|
|
10
|
+
*/
|
|
11
|
+
export declare function loadOptionalPeer<T>(name: string, feature: string, load: () => Promise<T>): Promise<T>;
|
|
12
|
+
//# sourceMappingURL=optionalPeer.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"optionalPeer.d.ts","sourceRoot":"","sources":["../../src/utils/optionalPeer.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AACH,wBAAsB,gBAAgB,CAAC,CAAC,EACtC,IAAI,EAAE,MAAM,EACZ,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GACrB,OAAO,CAAC,CAAC,CAAC,CAYZ"}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Loads an optional peer dependency, and turns "Cannot find module" into an
|
|
3
|
+
* error that says which feature needs it and how to install it.
|
|
4
|
+
*
|
|
5
|
+
* `resend`, React Email and `inngest` are optional peers of
|
|
6
|
+
* `@forumone/throughline`: a site that sends no email, or runs on Payload Jobs,
|
|
7
|
+
* never installs them. Each is imported where it is used, when it is used, so
|
|
8
|
+
* the first a site hears of a missing one is the moment that feature runs —
|
|
9
|
+
* and this is what it hears.
|
|
10
|
+
*/
|
|
11
|
+
export async function loadOptionalPeer(name, feature, load) {
|
|
12
|
+
try {
|
|
13
|
+
return await load();
|
|
14
|
+
}
|
|
15
|
+
catch (error) {
|
|
16
|
+
if (isMissingModule(error, name)) {
|
|
17
|
+
throw new Error(`${feature} needs \`${name}\`, an optional peer of @forumone/throughline. Install it: pnpm add ${name}`, { cause: error });
|
|
18
|
+
}
|
|
19
|
+
throw error;
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
function isMissingModule(error, name) {
|
|
23
|
+
if (!(error instanceof Error))
|
|
24
|
+
return false;
|
|
25
|
+
const code = error.code;
|
|
26
|
+
return ((code === 'ERR_MODULE_NOT_FOUND' || code === 'MODULE_NOT_FOUND') && error.message.includes(name));
|
|
27
|
+
}
|
|
28
|
+
//# sourceMappingURL=optionalPeer.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"optionalPeer.js","sourceRoot":"","sources":["../../src/utils/optionalPeer.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AACH,MAAM,CAAC,KAAK,UAAU,gBAAgB,CACpC,IAAY,EACZ,OAAe,EACf,IAAsB;IAEtB,IAAI,CAAC;QACH,OAAO,MAAM,IAAI,EAAE,CAAA;IACrB,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,IAAI,eAAe,CAAC,KAAK,EAAE,IAAI,CAAC,EAAE,CAAC;YACjC,MAAM,IAAI,KAAK,CACb,GAAG,OAAO,YAAY,IAAI,uEAAuE,IAAI,EAAE,EACvG,EAAE,KAAK,EAAE,KAAK,EAAE,CACjB,CAAA;QACH,CAAC;QACD,MAAM,KAAK,CAAA;IACb,CAAC;AACH,CAAC;AAED,SAAS,eAAe,CAAC,KAAc,EAAE,IAAY;IACnD,IAAI,CAAC,CAAC,KAAK,YAAY,KAAK,CAAC;QAAE,OAAO,KAAK,CAAA;IAC3C,MAAM,IAAI,GAAI,KAA4B,CAAC,IAAI,CAAA;IAC/C,OAAO,CACL,CAAC,IAAI,KAAK,sBAAsB,IAAI,IAAI,KAAK,kBAAkB,CAAC,IAAI,KAAK,CAAC,OAAO,CAAC,QAAQ,CAAC,IAAI,CAAC,CACjG,CAAA;AACH,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@forumone/throughline",
|
|
3
|
-
"version": "1.0.0-next.
|
|
3
|
+
"version": "1.0.0-next.2",
|
|
4
4
|
"description": "Throughline: an editorial platform for Payload CMS. Publishing, approvals, audit, integrations, email and jobs, with every feature reachable over MCP.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
7
7
|
"types": "./dist/index.d.ts",
|
|
8
8
|
"bin": {
|
|
9
|
+
"throughline": "./bin/throughline.mjs",
|
|
9
10
|
"throughline-payload": "./bin/throughline-payload.mjs"
|
|
10
11
|
},
|
|
11
12
|
"exports": {
|
|
@@ -110,52 +111,66 @@
|
|
|
110
111
|
"access": "public"
|
|
111
112
|
},
|
|
112
113
|
"peerDependencies": {
|
|
113
|
-
"
|
|
114
|
-
"
|
|
115
|
-
"vitest": "^3.0.0 || ^4.0.0",
|
|
116
|
-
"react": "^18.0.0 || ^19.0.0",
|
|
114
|
+
"@payloadcms/next": "^3.0.0",
|
|
115
|
+
"@payloadcms/plugin-cloud-storage": "^3.0.0",
|
|
117
116
|
"@payloadcms/ui": "^3.0.0",
|
|
117
|
+
"@react-email/components": "^0.5.4",
|
|
118
|
+
"@react-email/render": "^1.3.2",
|
|
118
119
|
"@vercel/blob": "^2.0.0",
|
|
119
|
-
"
|
|
120
|
+
"inngest": "^4.0.0",
|
|
120
121
|
"next": "^15.0.0 || ^16.0.0",
|
|
121
|
-
"
|
|
122
|
+
"payload": "^3.89.0",
|
|
123
|
+
"react": "^18.0.0 || ^19.0.0",
|
|
124
|
+
"resend": "^6.1.4",
|
|
125
|
+
"vitest": "^3.0.0 || ^4.0.0"
|
|
122
126
|
},
|
|
123
127
|
"peerDependenciesMeta": {
|
|
124
|
-
"
|
|
128
|
+
"@payloadcms/next": {
|
|
125
129
|
"optional": true
|
|
126
130
|
},
|
|
127
|
-
"
|
|
131
|
+
"@payloadcms/plugin-cloud-storage": {
|
|
128
132
|
"optional": true
|
|
129
133
|
},
|
|
130
134
|
"@payloadcms/ui": {
|
|
131
135
|
"optional": true
|
|
132
136
|
},
|
|
137
|
+
"@react-email/components": {
|
|
138
|
+
"optional": true
|
|
139
|
+
},
|
|
140
|
+
"@react-email/render": {
|
|
141
|
+
"optional": true
|
|
142
|
+
},
|
|
133
143
|
"@vercel/blob": {
|
|
134
144
|
"optional": true
|
|
135
145
|
},
|
|
136
|
-
"
|
|
146
|
+
"inngest": {
|
|
137
147
|
"optional": true
|
|
138
148
|
},
|
|
139
149
|
"next": {
|
|
140
150
|
"optional": true
|
|
141
151
|
},
|
|
142
|
-
"
|
|
152
|
+
"react": {
|
|
153
|
+
"optional": true
|
|
154
|
+
},
|
|
155
|
+
"resend": {
|
|
156
|
+
"optional": true
|
|
157
|
+
},
|
|
158
|
+
"vitest": {
|
|
143
159
|
"optional": true
|
|
144
160
|
}
|
|
145
161
|
},
|
|
146
162
|
"dependencies": {
|
|
147
|
-
"@react-email/components": "^0.5.4",
|
|
148
|
-
"@react-email/render": "^1.3.2",
|
|
149
|
-
"resend": "^6.1.4",
|
|
150
163
|
"zod": "^3.23.0",
|
|
151
164
|
"zod-to-json-schema": "^3.25.2",
|
|
152
|
-
"@forumone/throughline-design-
|
|
165
|
+
"@forumone/throughline-design-system": "1.0.0-next.2"
|
|
153
166
|
},
|
|
154
167
|
"devDependencies": {
|
|
155
168
|
"@payloadcms/db-sqlite": "^3.83.0",
|
|
156
169
|
"@payloadcms/next": "^3.83.0",
|
|
157
170
|
"@payloadcms/plugin-cloud-storage": "^3.83.0",
|
|
158
171
|
"@payloadcms/ui": "^3.83.0",
|
|
172
|
+
"@react-email/components": "^0.5.4",
|
|
173
|
+
"@react-email/render": "^1.3.2",
|
|
159
174
|
"@types/node": "^24.13.2",
|
|
160
175
|
"@types/react": "^19.2.0",
|
|
161
176
|
"@types/react-dom": "^19.2.0",
|
|
@@ -166,11 +181,12 @@
|
|
|
166
181
|
"payload": "^3.83.0",
|
|
167
182
|
"react": "^19.2.0",
|
|
168
183
|
"react-dom": "^19.2.0",
|
|
184
|
+
"resend": "^6.1.4",
|
|
169
185
|
"typescript": "^5.6.0",
|
|
170
186
|
"vitest": "^4.1.10",
|
|
171
|
-
"@forumone/throughline-
|
|
187
|
+
"@forumone/throughline-reference-ds": "0.3.8-next.1",
|
|
172
188
|
"@forumone/throughline-tsconfig": "0.0.0",
|
|
173
|
-
"@forumone/throughline-
|
|
189
|
+
"@forumone/throughline-eslint-config": "0.0.0"
|
|
174
190
|
},
|
|
175
191
|
"scripts": {
|
|
176
192
|
"build": "tsc -b",
|