@actuate-media/cms-core 0.38.0 → 0.39.0

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.
Files changed (60) hide show
  1. package/dist/__tests__/api/ai-status.test.d.ts +2 -0
  2. package/dist/__tests__/api/ai-status.test.d.ts.map +1 -0
  3. package/dist/__tests__/api/ai-status.test.js +110 -0
  4. package/dist/__tests__/api/ai-status.test.js.map +1 -0
  5. package/dist/__tests__/api/users-invite.test.d.ts +2 -0
  6. package/dist/__tests__/api/users-invite.test.d.ts.map +1 -0
  7. package/dist/__tests__/api/users-invite.test.js +167 -0
  8. package/dist/__tests__/api/users-invite.test.js.map +1 -0
  9. package/dist/__tests__/auth/invite.test.d.ts +2 -0
  10. package/dist/__tests__/auth/invite.test.d.ts.map +1 -0
  11. package/dist/__tests__/auth/invite.test.js +151 -0
  12. package/dist/__tests__/auth/invite.test.js.map +1 -0
  13. package/dist/__tests__/auth/reset.test.js +52 -1
  14. package/dist/__tests__/auth/reset.test.js.map +1 -1
  15. package/dist/__tests__/email/sender.test.d.ts +2 -0
  16. package/dist/__tests__/email/sender.test.d.ts.map +1 -0
  17. package/dist/__tests__/email/sender.test.js +33 -0
  18. package/dist/__tests__/email/sender.test.js.map +1 -0
  19. package/dist/__tests__/middleware.test.js +30 -0
  20. package/dist/__tests__/middleware.test.js.map +1 -1
  21. package/dist/__tests__/setup/index.test.js +37 -2
  22. package/dist/__tests__/setup/index.test.js.map +1 -1
  23. package/dist/api/handlers.d.ts.map +1 -1
  24. package/dist/api/handlers.js +102 -1
  25. package/dist/api/handlers.js.map +1 -1
  26. package/dist/auth/index.d.ts +2 -0
  27. package/dist/auth/index.d.ts.map +1 -1
  28. package/dist/auth/index.js +1 -0
  29. package/dist/auth/index.js.map +1 -1
  30. package/dist/auth/invite-email.d.ts +12 -0
  31. package/dist/auth/invite-email.d.ts.map +1 -0
  32. package/dist/auth/invite-email.js +57 -0
  33. package/dist/auth/invite-email.js.map +1 -0
  34. package/dist/auth/invite.d.ts +37 -0
  35. package/dist/auth/invite.d.ts.map +1 -0
  36. package/dist/auth/invite.js +104 -0
  37. package/dist/auth/invite.js.map +1 -0
  38. package/dist/auth/reset.d.ts +6 -0
  39. package/dist/auth/reset.d.ts.map +1 -1
  40. package/dist/auth/reset.js +11 -3
  41. package/dist/auth/reset.js.map +1 -1
  42. package/dist/email/sender.d.ts +35 -0
  43. package/dist/email/sender.d.ts.map +1 -0
  44. package/dist/email/sender.js +25 -0
  45. package/dist/email/sender.js.map +1 -0
  46. package/dist/forms/notify.d.ts.map +1 -1
  47. package/dist/forms/notify.js +3 -2
  48. package/dist/forms/notify.js.map +1 -1
  49. package/dist/index.d.ts +1 -0
  50. package/dist/index.d.ts.map +1 -1
  51. package/dist/index.js +2 -0
  52. package/dist/index.js.map +1 -1
  53. package/dist/middleware.d.ts.map +1 -1
  54. package/dist/middleware.js +60 -1
  55. package/dist/middleware.js.map +1 -1
  56. package/dist/setup/index.d.ts +14 -0
  57. package/dist/setup/index.d.ts.map +1 -1
  58. package/dist/setup/index.js +29 -3
  59. package/dist/setup/index.js.map +1 -1
  60. package/package.json +6 -1
@@ -34,8 +34,13 @@ export function createCMSMiddleware(cmsConfig) {
34
34
  return new Response('Forbidden', { status: 403 });
35
35
  }
36
36
  }
37
+ // CMS_SECRET is mandatory: it signs session JWTs, so the admin (including
38
+ // the setup wizard, which auto-logs-in the new admin) cannot function
39
+ // without it. Rather than a bare 500, return an actionable page that tells
40
+ // the operator exactly what to set. The setup *API* route is already
41
+ // bypassed above, so this only guards the admin UI.
37
42
  if (isAdminRoute && !secret) {
38
- return new Response('Server misconfiguration: CMS_SECRET is not set', { status: 500 });
43
+ return configMissingResponse();
39
44
  }
40
45
  // Session verification for admin routes (not API routes — those handle their own auth)
41
46
  if (isAdminRoute && secret) {
@@ -60,6 +65,60 @@ export function createCMSMiddleware(cmsConfig) {
60
65
  return null;
61
66
  };
62
67
  }
68
+ /**
69
+ * Actionable error page shown when the admin UI is requested but `CMS_SECRET`
70
+ * is not configured. Self-contained HTML (no external assets, no theme access)
71
+ * because it renders before the admin shell can load. Deliberately leaks no
72
+ * secret values — only the variable name and remediation steps.
73
+ */
74
+ function configMissingResponse() {
75
+ const html = `<!doctype html>
76
+ <html lang="en">
77
+ <head>
78
+ <meta charset="utf-8" />
79
+ <meta name="viewport" content="width=device-width, initial-scale=1" />
80
+ <title>Actuate CMS — Configuration required</title>
81
+ <style>
82
+ :root { color-scheme: light dark; }
83
+ body { margin: 0; min-height: 100vh; display: grid; place-items: center;
84
+ font-family: system-ui, -apple-system, Segoe UI, Roboto, sans-serif;
85
+ background: #0b0d12; color: #e6e8eb; line-height: 1.5; padding: 24px; }
86
+ .card { max-width: 560px; width: 100%; background: #151922; border: 1px solid #262c38;
87
+ border-radius: 12px; padding: 28px 32px; }
88
+ h1 { font-size: 1.25rem; margin: 0 0 8px; font-weight: 500; }
89
+ p { margin: 0 0 12px; color: #aab2bd; }
90
+ code { background: #0b0d12; border: 1px solid #262c38; border-radius: 6px;
91
+ padding: 2px 6px; font-size: 0.9em; }
92
+ pre { background: #0b0d12; border: 1px solid #262c38; border-radius: 8px;
93
+ padding: 12px 14px; overflow-x: auto; font-size: 0.85rem; color: #e6e8eb; }
94
+ ol { margin: 0 0 4px; padding-left: 20px; color: #aab2bd; }
95
+ li { margin-bottom: 6px; }
96
+ </style>
97
+ </head>
98
+ <body>
99
+ <main class="card">
100
+ <h1>Actuate CMS isn't configured yet</h1>
101
+ <p>The <code>CMS_SECRET</code> environment variable is missing or empty. It's
102
+ required to sign admin sessions, so the admin panel can't start without it.</p>
103
+ <ol>
104
+ <li>Generate a secret (at least 32 characters):
105
+ <pre>node -e "console.log(require('crypto').randomBytes(32).toString('hex'))"</pre>
106
+ </li>
107
+ <li>Set <code>CMS_SECRET</code> to that value in your environment (or your
108
+ host's environment variables), then restart / redeploy.</li>
109
+ </ol>
110
+ <p>This page is only visible to operators — visitors never see it.</p>
111
+ </main>
112
+ </body>
113
+ </html>`;
114
+ return new Response(html, {
115
+ status: 503,
116
+ headers: {
117
+ 'Content-Type': 'text/html; charset=utf-8',
118
+ 'Cache-Control': 'no-store',
119
+ },
120
+ });
121
+ }
63
122
  /**
64
123
  * Match a pathname against a route prefix on a path-segment boundary, so the
65
124
  * admin guard for `/admin` does not also capture sibling public routes like
@@ -1 +1 @@
1
- {"version":3,"file":"middleware.js","sourceRoot":"","sources":["../src/middleware.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAA;AACjD,OAAO,EAAE,WAAW,EAAE,MAAM,4BAA4B,CAAA;AACxD,OAAO,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,yBAAyB,CAAA;AAYnE,MAAM,UAAU,mBAAmB,CAAC,SAAkC;IACpE,MAAM,SAAS,GAAG,SAAS,CAAC,KAAK,EAAE,IAAI,IAAI,QAAQ,CAAA;IACnD,MAAM,WAAW,GAAG,SAAS,CAAC,KAAK,EAAE,WAAW,CAAA;IAChD,MAAM,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC,UAAU,IAAI,EAAE,CAAA;IAE3C,OAAO,KAAK,UAAU,aAAa,CAAC,OAAgB;QAClD,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,CAAA;QAEhC,MAAM,YAAY,GAAG,iBAAiB,CAAC,GAAG,CAAC,QAAQ,EAAE,SAAS,CAAC,CAAA;QAC/D,MAAM,aAAa,GAAG,iBAAiB,CAAC,GAAG,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAA;QAEjE,IAAI,CAAC,YAAY,IAAI,CAAC,aAAa,EAAE,CAAC;YACpC,OAAO,IAAI,CAAA;QACb,CAAC;QAED,0EAA0E;QAC1E,uEAAuE;QACvE,wEAAwE;QACxE,iCAAiC;QACjC,MAAM,YAAY,GAChB,GAAG,CAAC,QAAQ,KAAK,GAAG,SAAS,QAAQ;YACrC,GAAG,CAAC,QAAQ,CAAC,UAAU,CAAC,GAAG,SAAS,SAAS,CAAC;YAC9C,GAAG,CAAC,QAAQ,CAAC,UAAU,CAAC,gBAAgB,CAAC,CAAA;QAC3C,IAAI,YAAY,EAAE,CAAC;YACjB,OAAO,IAAI,CAAA;QACb,CAAC;QAED,uEAAuE;QACvE,yEAAyE;QACzE,iEAAiE;QACjE,4CAA4C;QAC5C,IAAI,WAAW,IAAI,WAAW,CAAC,MAAM,GAAG,CAAC,IAAI,CAAC,YAAY,IAAI,aAAa,CAAC,EAAE,CAAC;YAC7E,MAAM,QAAQ,GAAG,WAAW,CAAC,OAAO,CAAC,CAAA;YACrC,kEAAkE;YAClE,mCAAmC;YACnC,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC,IAAI,CAAC,WAAW,CAAC,QAAQ,EAAE,WAAW,CAAC,EAAE,CAAC;gBACnE,OAAO,IAAI,QAAQ,CAAC,WAAW,EAAE,EAAE,MAAM,EAAE,GAAG,EAAE,CAAC,CAAA;YACnD,CAAC;QACH,CAAC;QAED,IAAI,YAAY,IAAI,CAAC,MAAM,EAAE,CAAC;YAC5B,OAAO,IAAI,QAAQ,CAAC,gDAAgD,EAAE,EAAE,MAAM,EAAE,GAAG,EAAE,CAAC,CAAA;QACxF,CAAC;QAED,uFAAuF;QACvF,IAAI,YAAY,IAAI,MAAM,EAAE,CAAC;YAC3B,MAAM,MAAM,GAAG,WAAW,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,IAAI,EAAE,CAAC,CAAA;YAC/D,MAAM,KAAK,GAAG,MAAM,CAAC,iBAAiB,CAAC,CAAA;YAEvC,IAAI,CAAC,KAAK,EAAE,CAAC;gBACX,OAAO,IAAI,CAAA;YACb,CAAC;YAED,IAAI,CAAC;gBACH,MAAM,aAAa,CAAC,KAAK,EAAE,EAAE,MAAM,EAAE,CAAC,CAAA;YACxC,CAAC;YAAC,MAAM,CAAC;gBACP,OAAO,IAAI,QAAQ,CAAC,IAAI,EAAE;oBACxB,MAAM,EAAE,GAAG;oBACX,OAAO,EAAE;wBACP,QAAQ,EAAE,SAAS;wBACnB,YAAY,EAAE,+CAA+C;qBAC9D;iBACF,CAAC,CAAA;YACJ,CAAC;QACH,CAAC;QAED,OAAO,IAAI,CAAA;IACb,CAAC,CAAA;AACH,CAAC;AAED;;;;;GAKG;AACH,SAAS,iBAAiB,CAAC,QAAgB,EAAE,MAAc;IACzD,MAAM,UAAU,GAAG,MAAM,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,MAAM,CAAA;IACtE,OAAO,QAAQ,KAAK,UAAU,IAAI,QAAQ,CAAC,UAAU,CAAC,GAAG,UAAU,GAAG,CAAC,CAAA;AACzE,CAAC;AAED,SAAS,WAAW,CAAC,YAAoB;IACvC,MAAM,OAAO,GAA2B,EAAE,CAAA;IAC1C,KAAK,MAAM,IAAI,IAAI,YAAY,CAAC,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC;QAC3C,MAAM,CAAC,GAAG,EAAE,GAAG,IAAI,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAA;QACtC,IAAI,GAAG,EAAE,CAAC;YACR,OAAO,CAAC,GAAG,CAAC,IAAI,EAAE,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,CAAA;QAC7C,CAAC;IACH,CAAC;IACD,OAAO,OAAO,CAAA;AAChB,CAAC"}
1
+ {"version":3,"file":"middleware.js","sourceRoot":"","sources":["../src/middleware.ts"],"names":[],"mappings":"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"}
@@ -8,6 +8,12 @@
8
8
  export interface SetupStatus {
9
9
  setupRequired: boolean;
10
10
  userCount: number;
11
+ /**
12
+ * True when the database is reachable but the Actuate CMS tables don't exist
13
+ * yet (migrations have not been applied). Distinct from `setupRequired`: the
14
+ * fix is `prisma migrate deploy`, not the setup wizard.
15
+ */
16
+ migrationsRequired?: boolean;
11
17
  }
12
18
  export interface CreateAdminInput {
13
19
  email: string;
@@ -30,6 +36,14 @@ export interface SetupResult {
30
36
  * see the real cause (e.g. `ECONNREFUSED`, Prisma `P1001`).
31
37
  */
32
38
  export declare function isDatabaseUnavailableError(err: unknown): boolean;
39
+ /**
40
+ * Detect errors that mean the database is reachable but the Actuate CMS tables
41
+ * have not been created yet (migrations not applied). This is a distinct,
42
+ * recoverable state from "empty database" — surfacing it lets the UI tell the
43
+ * operator to run migrations instead of dropping them on the login screen or a
44
+ * wizard that will fail on the first write.
45
+ */
46
+ export declare function isSchemaMissingError(err: unknown): boolean;
33
47
  /**
34
48
  * Check if the CMS needs first-run setup (no admin users exist).
35
49
  * Uses a count query to avoid loading the full user model.
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/setup/index.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAIH,MAAM,WAAW,WAAW;IAC1B,aAAa,EAAE,OAAO,CAAA;IACtB,SAAS,EAAE,MAAM,CAAA;CAClB;AAED,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,MAAM,CAAA;IACb,QAAQ,EAAE,MAAM,CAAA;IAChB,IAAI,EAAE,MAAM,CAAA;CACb;AAED,MAAM,WAAW,WAAW;IAC1B,OAAO,EAAE,OAAO,CAAA;IAChB,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,MAAM,CAAC,EAAE,MAAM,CAAA;CAChB;AAED;;;;;;;;;GASG;AACH,wBAAgB,0BAA0B,CAAC,GAAG,EAAE,OAAO,GAAG,OAAO,CA4BhE;AAED;;;;;;;GAOG;AACH,wBAAsB,kBAAkB,CAAC,EAAE,EAAE,GAAG,GAAG,OAAO,CAAC,WAAW,CAAC,CAQtE;AAED;;;GAGG;AACH,wBAAsB,kBAAkB,CAAC,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,gBAAgB,GAAG,OAAO,CAAC,WAAW,CAAC,CAuC/F;AAED;;;;GAIG;AACH,wBAAsB,aAAa,CAAC,EAAE,EAAE,GAAG,GAAG,OAAO,CAAC,WAAW,GAAG,IAAI,CAAC,CAgBxE"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/setup/index.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAIH,MAAM,WAAW,WAAW;IAC1B,aAAa,EAAE,OAAO,CAAA;IACtB,SAAS,EAAE,MAAM,CAAA;IACjB;;;;OAIG;IACH,kBAAkB,CAAC,EAAE,OAAO,CAAA;CAC7B;AAED,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,MAAM,CAAA;IACb,QAAQ,EAAE,MAAM,CAAA;IAChB,IAAI,EAAE,MAAM,CAAA;CACb;AAED,MAAM,WAAW,WAAW;IAC1B,OAAO,EAAE,OAAO,CAAA;IAChB,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,MAAM,CAAC,EAAE,MAAM,CAAA;CAChB;AAED;;;;;;;;;GASG;AACH,wBAAgB,0BAA0B,CAAC,GAAG,EAAE,OAAO,GAAG,OAAO,CA4BhE;AAED;;;;;;GAMG;AACH,wBAAgB,oBAAoB,CAAC,GAAG,EAAE,OAAO,GAAG,OAAO,CAa1D;AAED;;;;;;;GAOG;AACH,wBAAsB,kBAAkB,CAAC,EAAE,EAAE,GAAG,GAAG,OAAO,CAAC,WAAW,CAAC,CAYtE;AAED;;;GAGG;AACH,wBAAsB,kBAAkB,CAAC,EAAE,EAAE,GAAG,EAAE,KAAK,EAAE,gBAAgB,GAAG,OAAO,CAAC,WAAW,CAAC,CAwC/F;AAED;;;;GAIG;AACH,wBAAsB,aAAa,CAAC,EAAE,EAAE,GAAG,GAAG,OAAO,CAAC,WAAW,GAAG,IAAI,CAAC,CAgBxE"}
@@ -46,6 +46,27 @@ export function isDatabaseUnavailableError(err) {
46
46
  }
47
47
  return false;
48
48
  }
49
+ /**
50
+ * Detect errors that mean the database is reachable but the Actuate CMS tables
51
+ * have not been created yet (migrations not applied). This is a distinct,
52
+ * recoverable state from "empty database" — surfacing it lets the UI tell the
53
+ * operator to run migrations instead of dropping them on the login screen or a
54
+ * wizard that will fail on the first write.
55
+ */
56
+ export function isSchemaMissingError(err) {
57
+ if (!err || typeof err !== 'object')
58
+ return false;
59
+ const code = err.code;
60
+ // Prisma P2021: table does not exist. P2022: column does not exist.
61
+ if (code === 'P2021' || code === 'P2022')
62
+ return true;
63
+ const message = err.message;
64
+ if (typeof message === 'string') {
65
+ return (message.includes('does not exist in the current database') ||
66
+ /relation "[^"]+" does not exist/i.test(message));
67
+ }
68
+ return false;
69
+ }
49
70
  /**
50
71
  * Check if the CMS needs first-run setup (no admin users exist).
51
72
  * Uses a count query to avoid loading the full user model.
@@ -62,6 +83,10 @@ export async function checkSetupRequired(db) {
62
83
  catch (err) {
63
84
  if (isDatabaseUnavailableError(err))
64
85
  throw err;
86
+ // Reachable DB but no tables yet → operator must run migrations.
87
+ if (isSchemaMissingError(err)) {
88
+ return { setupRequired: false, userCount: 0, migrationsRequired: true };
89
+ }
65
90
  return { setupRequired: true, userCount: 0 };
66
91
  }
67
92
  }
@@ -98,9 +123,10 @@ export async function createInitialAdmin(db, input) {
98
123
  return { success: true, userId: user.id };
99
124
  }
100
125
  catch (err) {
101
- // A DB outage is an infrastructure failure, not a bad request —
102
- // rethrow so the caller can return a 5xx instead of a confusing 400.
103
- if (isDatabaseUnavailableError(err))
126
+ // A DB outage or an unmigrated schema is an infrastructure failure, not a
127
+ // bad request — rethrow so the caller can return a 5xx with an actionable
128
+ // message instead of a confusing 400.
129
+ if (isDatabaseUnavailableError(err) || isSchemaMissingError(err))
104
130
  throw err;
105
131
  const message = err instanceof Error ? err.message : 'Setup failed';
106
132
  return { success: false, error: message };
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/setup/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/setup/index.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@actuate-media/cms-core",
3
- "version": "0.38.0",
3
+ "version": "0.39.0",
4
4
  "repository": {
5
5
  "type": "git",
6
6
  "url": "https://github.com/actuate-media/actuatecms.git",
@@ -64,6 +64,11 @@
64
64
  "import": "./dist/security/center/index.js",
65
65
  "default": "./dist/security/center/index.js"
66
66
  },
67
+ "./email-sender": {
68
+ "types": "./dist/email/sender.d.ts",
69
+ "import": "./dist/email/sender.js",
70
+ "default": "./dist/email/sender.js"
71
+ },
67
72
  "./page-builder": {
68
73
  "types": "./dist/page-builder/index.d.ts",
69
74
  "import": "./dist/page-builder/index.js",