@forge-cms/runtime 0.5.0 → 0.7.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 (71) hide show
  1. package/dist/auth-handlers.d.ts +43 -1
  2. package/dist/auth-handlers.d.ts.map +1 -1
  3. package/dist/auth-handlers.js +64 -18
  4. package/dist/auth-handlers.js.map +1 -1
  5. package/dist/auth-managed.d.ts +19 -0
  6. package/dist/auth-managed.d.ts.map +1 -0
  7. package/dist/auth-managed.js +24 -0
  8. package/dist/auth-managed.js.map +1 -0
  9. package/dist/body.d.ts +28 -0
  10. package/dist/body.d.ts.map +1 -0
  11. package/dist/body.js +81 -0
  12. package/dist/body.js.map +1 -0
  13. package/dist/concurrency.d.ts +8 -0
  14. package/dist/concurrency.d.ts.map +1 -0
  15. package/dist/concurrency.js +15 -0
  16. package/dist/concurrency.js.map +1 -0
  17. package/dist/context.d.ts +5 -0
  18. package/dist/context.d.ts.map +1 -1
  19. package/dist/errors.d.ts +46 -1
  20. package/dist/errors.d.ts.map +1 -1
  21. package/dist/errors.js +61 -0
  22. package/dist/errors.js.map +1 -1
  23. package/dist/files.d.ts +15 -1
  24. package/dist/files.d.ts.map +1 -1
  25. package/dist/files.js +55 -14
  26. package/dist/files.js.map +1 -1
  27. package/dist/globals.d.ts +21 -3
  28. package/dist/globals.d.ts.map +1 -1
  29. package/dist/globals.js +216 -28
  30. package/dist/globals.js.map +1 -1
  31. package/dist/handlers.d.ts +3 -2
  32. package/dist/handlers.d.ts.map +1 -1
  33. package/dist/handlers.js +51 -49
  34. package/dist/handlers.js.map +1 -1
  35. package/dist/index.d.ts +5 -2
  36. package/dist/index.d.ts.map +1 -1
  37. package/dist/index.js +6 -1
  38. package/dist/index.js.map +1 -1
  39. package/dist/localization.d.ts +17 -0
  40. package/dist/localization.d.ts.map +1 -1
  41. package/dist/localization.js +56 -0
  42. package/dist/localization.js.map +1 -1
  43. package/dist/operations.d.ts +51 -12
  44. package/dist/operations.d.ts.map +1 -1
  45. package/dist/operations.js +728 -125
  46. package/dist/operations.js.map +1 -1
  47. package/dist/relation-integrity.d.ts +31 -13
  48. package/dist/relation-integrity.d.ts.map +1 -1
  49. package/dist/relation-integrity.js +62 -6
  50. package/dist/relation-integrity.js.map +1 -1
  51. package/dist/relation-lifecycle.d.ts +95 -0
  52. package/dist/relation-lifecycle.d.ts.map +1 -0
  53. package/dist/relation-lifecycle.js +424 -0
  54. package/dist/relation-lifecycle.js.map +1 -0
  55. package/dist/runtime.d.ts +21 -0
  56. package/dist/runtime.d.ts.map +1 -1
  57. package/dist/runtime.js +112 -20
  58. package/dist/runtime.js.map +1 -1
  59. package/dist/storage-intents.d.ts +96 -0
  60. package/dist/storage-intents.d.ts.map +1 -0
  61. package/dist/storage-intents.js +217 -0
  62. package/dist/storage-intents.js.map +1 -0
  63. package/dist/system-fields.d.ts +27 -0
  64. package/dist/system-fields.d.ts.map +1 -0
  65. package/dist/system-fields.js +74 -0
  66. package/dist/system-fields.js.map +1 -0
  67. package/dist/versions.d.ts +73 -1
  68. package/dist/versions.d.ts.map +1 -1
  69. package/dist/versions.js +204 -17
  70. package/dist/versions.js.map +1 -1
  71. package/package.json +9 -7
@@ -8,12 +8,50 @@ import type { AnyForgeCmsRuntime } from './runtime.js';
8
8
  * instead of re-implementing (and risking drifting from) this switch.
9
9
  */
10
10
  export declare function authFailureResponse(reason: AuthFailureReason): Response;
11
+ /** One login or signup attempt, as handed to the host's {@link AuthAttemptThrottle} (spec 069). */
12
+ export interface AuthAttempt {
13
+ action: 'login' | 'signup';
14
+ /**
15
+ * The submitted email, trimmed and lower-cased — the same canonical form the users adapter looks up.
16
+ * It is what was *submitted*: it says nothing about whether such an account exists.
17
+ */
18
+ identifier: string;
19
+ /** The original request, for host policy (a client address, a tenant header, …). Its body is consumed. */
20
+ request: Request;
21
+ }
22
+ export type AuthAttemptDecision = {
23
+ allowed: true;
24
+ } | {
25
+ allowed: false;
26
+ /** Seconds until a retry may succeed. Emitted as `Retry-After` when a finite number > 0. */
27
+ retryAfterSeconds?: number;
28
+ };
29
+ /**
30
+ * A host-provided limiter for login/signup (spec 069). Forge calls it exactly once per well-formed
31
+ * attempt — after the bounded body is parsed and before any credential lookup or password hashing —
32
+ * with the same arguments whether or not the account exists. Forge keeps no counters: the host decides
33
+ * the key(s) (identifier, client, tenant, a combination) and where the state lives (a Cloudflare Rate
34
+ * Limiting binding, a proxy, an external service). A rejection is `429 RATE_LIMITED`; a throw or any
35
+ * result other than `{ allowed: true | false }` fails closed as `500`.
36
+ */
37
+ export type AuthAttemptThrottle = (attempt: AuthAttempt) => AuthAttemptDecision | Promise<AuthAttemptDecision>;
11
38
  export interface AuthHandlerOptions<TEnv = unknown> {
12
39
  runtime: AnyForgeCmsRuntime<TEnv>;
13
40
  /** Omit the cookie's `Secure` attribute — only for local `http://` development. Defaults to `true`. */
14
41
  cookie?: {
15
42
  secure?: boolean;
16
43
  };
44
+ /**
45
+ * Login/signup only: the host's attempt limiter. Omitted, nothing is throttled (unchanged behaviour).
46
+ * Ignored by `handleLogout`/`handleMe`.
47
+ */
48
+ throttle?: AuthAttemptThrottle;
49
+ /**
50
+ * Login/signup only: the largest accepted JSON body, in bytes. Defaults to
51
+ * `DEFAULT_AUTH_MAX_BODY_BYTES` (8 KiB); raise it only with `passwordPolicy.maxLength`. An integer
52
+ * from 1 to 1 MiB; anything else makes the handler throw (a configuration error, not a response).
53
+ */
54
+ maxBodyBytes?: number;
17
55
  }
18
56
  export interface SignupHandlerOptions<TEnv = unknown> extends AuthHandlerOptions<TEnv> {
19
57
  /** Public signup is opt-in — no implicit default-on. */
@@ -23,13 +61,17 @@ export interface SignupHandlerOptions<TEnv = unknown> extends AuthHandlerOptions
23
61
  * `POST` `{ email, password }` → `{ data: { user, token } }` (unchanged shape — Bearer-compatible)
24
62
  * plus a `Set-Cookie` that starts a browser session. `404` if the configured `AuthAdapter` doesn't
25
63
  * implement `login`.
64
+ *
65
+ * Order (spec 069): bounded body (`413`/`400`) → `options.throttle` (`429`) → `auth.login` → response.
26
66
  */
27
67
  export declare function handleLogin<TEnv = unknown>(context: ApiContext<TEnv>, options: AuthHandlerOptions<TEnv>): Promise<Response>;
28
68
  /**
29
69
  * `POST` `{ email, password, name? }` → `{ data: { user, token } }` + `Set-Cookie`. Any other body
30
70
  * field (e.g. a `role`) is never read — role escalation through this endpoint is structurally
31
71
  * impossible, not merely hidden. `404` when `options.enabled` is `false` or the adapter doesn't
32
- * implement `signup`.
72
+ * implement `signup` — decided before the body is read or the throttle is called.
73
+ *
74
+ * Order (spec 069): bounded body (`413`/`400`) → `options.throttle` (`429`) → `auth.signup` → response.
33
75
  */
34
76
  export declare function handleSignup<TEnv = unknown>(context: ApiContext<TEnv>, options: SignupHandlerOptions<TEnv>): Promise<Response>;
35
77
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"auth-handlers.d.ts","sourceRoot":"","sources":["../src/auth-handlers.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAEjD,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AAEzD,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,cAAc,CAAC;AAwBvD;;;;;GAKG;AACH,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,iBAAiB,GAAG,QAAQ,CAWvE;AAUD,MAAM,WAAW,kBAAkB,CAAC,IAAI,GAAG,OAAO;IAChD,OAAO,EAAE,kBAAkB,CAAC,IAAI,CAAC,CAAC;IAClC,uGAAuG;IACvG,MAAM,CAAC,EAAE;QAAE,MAAM,CAAC,EAAE,OAAO,CAAA;KAAE,CAAC;CAC/B;AAED,MAAM,WAAW,oBAAoB,CAAC,IAAI,GAAG,OAAO,CAAE,SAAQ,kBAAkB,CAAC,IAAI,CAAC;IACpF,wDAAwD;IACxD,OAAO,EAAE,OAAO,CAAC;CAClB;AAED;;;;GAIG;AACH,wBAAsB,WAAW,CAAC,IAAI,GAAG,OAAO,EAC9C,OAAO,EAAE,UAAU,CAAC,IAAI,CAAC,EACzB,OAAO,EAAE,kBAAkB,CAAC,IAAI,CAAC,GAChC,OAAO,CAAC,QAAQ,CAAC,CA0BnB;AAED;;;;;GAKG;AACH,wBAAsB,YAAY,CAAC,IAAI,GAAG,OAAO,EAC/C,OAAO,EAAE,UAAU,CAAC,IAAI,CAAC,EACzB,OAAO,EAAE,oBAAoB,CAAC,IAAI,CAAC,GAClC,OAAO,CAAC,QAAQ,CAAC,CAmCnB;AAED;;;;GAIG;AACH,wBAAsB,YAAY,CAAC,IAAI,GAAG,OAAO,EAC/C,OAAO,EAAE,UAAU,CAAC,IAAI,CAAC,EACzB,OAAO,EAAE,kBAAkB,CAAC,IAAI,CAAC,GAChC,OAAO,CAAC,QAAQ,CAAC,CAanB;AAED,8EAA8E;AAC9E,wBAAsB,QAAQ,CAAC,IAAI,GAAG,OAAO,EAC3C,OAAO,EAAE,UAAU,CAAC,IAAI,CAAC,EACzB,OAAO,EAAE,kBAAkB,CAAC,IAAI,CAAC,GAChC,OAAO,CAAC,QAAQ,CAAC,CAUnB"}
1
+ {"version":3,"file":"auth-handlers.d.ts","sourceRoot":"","sources":["../src/auth-handlers.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAEjD,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AAEzD,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,cAAc,CAAC;AAuCvD;;;;;GAKG;AACH,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,iBAAiB,GAAG,QAAQ,CAavE;AAED,mGAAmG;AACnG,MAAM,WAAW,WAAW;IAC1B,MAAM,EAAE,OAAO,GAAG,QAAQ,CAAC;IAC3B;;;OAGG;IACH,UAAU,EAAE,MAAM,CAAC;IACnB,0GAA0G;IAC1G,OAAO,EAAE,OAAO,CAAC;CAClB;AAED,MAAM,MAAM,mBAAmB,GAC3B;IAAE,OAAO,EAAE,IAAI,CAAA;CAAE,GACjB;IACE,OAAO,EAAE,KAAK,CAAC;IACf,4FAA4F;IAC5F,iBAAiB,CAAC,EAAE,MAAM,CAAC;CAC5B,CAAC;AAEN;;;;;;;GAOG;AACH,MAAM,MAAM,mBAAmB,GAAG,CAChC,OAAO,EAAE,WAAW,KACjB,mBAAmB,GAAG,OAAO,CAAC,mBAAmB,CAAC,CAAC;AAExD,MAAM,WAAW,kBAAkB,CAAC,IAAI,GAAG,OAAO;IAChD,OAAO,EAAE,kBAAkB,CAAC,IAAI,CAAC,CAAC;IAClC,uGAAuG;IACvG,MAAM,CAAC,EAAE;QAAE,MAAM,CAAC,EAAE,OAAO,CAAA;KAAE,CAAC;IAC9B;;;OAGG;IACH,QAAQ,CAAC,EAAE,mBAAmB,CAAC;IAC/B;;;;OAIG;IACH,YAAY,CAAC,EAAE,MAAM,CAAC;CACvB;AA4BD,MAAM,WAAW,oBAAoB,CAAC,IAAI,GAAG,OAAO,CAAE,SAAQ,kBAAkB,CAAC,IAAI,CAAC;IACpF,wDAAwD;IACxD,OAAO,EAAE,OAAO,CAAC;CAClB;AAED;;;;;;GAMG;AACH,wBAAsB,WAAW,CAAC,IAAI,GAAG,OAAO,EAC9C,OAAO,EAAE,UAAU,CAAC,IAAI,CAAC,EACzB,OAAO,EAAE,kBAAkB,CAAC,IAAI,CAAC,GAChC,OAAO,CAAC,QAAQ,CAAC,CAiCnB;AAED;;;;;;;GAOG;AACH,wBAAsB,YAAY,CAAC,IAAI,GAAG,OAAO,EAC/C,OAAO,EAAE,UAAU,CAAC,IAAI,CAAC,EACzB,OAAO,EAAE,oBAAoB,CAAC,IAAI,CAAC,GAClC,OAAO,CAAC,QAAQ,CAAC,CA0CnB;AAED;;;;GAIG;AACH,wBAAsB,YAAY,CAAC,IAAI,GAAG,OAAO,EAC/C,OAAO,EAAE,UAAU,CAAC,IAAI,CAAC,EACzB,OAAO,EAAE,kBAAkB,CAAC,IAAI,CAAC,GAChC,OAAO,CAAC,QAAQ,CAAC,CAanB;AAED,8EAA8E;AAC9E,wBAAsB,QAAQ,CAAC,IAAI,GAAG,OAAO,EAC3C,OAAO,EAAE,UAAU,CAAC,IAAI,CAAC,EACzB,OAAO,EAAE,kBAAkB,CAAC,IAAI,CAAC,GAChC,OAAO,CAAC,QAAQ,CAAC,CAUnB"}
@@ -1,7 +1,8 @@
1
1
  import { getLogger } from '@forge-cms/core';
2
2
  import { ForgeAuthError, buildLogoutCookie, buildSessionCookie } from '@forge-cms/auth';
3
3
  import { assertCsrfSafe } from './csrf.js';
4
- import { InvalidInputError, isForgeError, toApiErrorBody } from './errors.js';
4
+ import { readBoundedJsonObject, resolveMaxBodyBytes } from './body.js';
5
+ import { RateLimitedError, isForgeError, toApiErrorBody } from './errors.js';
5
6
  function jsonResponse(data, status = 200) {
6
7
  return new Response(JSON.stringify(data), {
7
8
  status,
@@ -11,12 +12,24 @@ function jsonResponse(data, status = 200) {
11
12
  function errorResponse(code, message, status) {
12
13
  return jsonResponse({ error: { code, message } }, status);
13
14
  }
14
- function toErrorResponse(err) {
15
+ /**
16
+ * Expected failures (typed `ForgeError`s: bad JSON, 413, 429, CSRF, …) are responses, never log lines.
17
+ * An unexpected one is logged as metadata only — the operation and the error's class name — because an
18
+ * adapter's, driver's or host throttle's error message can quote whatever it was handed: a password,
19
+ * a token, a cookie, the request body (spec 069).
20
+ */
21
+ function toErrorResponse(err, operation) {
15
22
  if (isForgeError(err)) {
16
- const body = toApiErrorBody(err);
17
- return jsonResponse(body, err.status);
23
+ const response = jsonResponse(toApiErrorBody(err), err.status);
24
+ if (err instanceof RateLimitedError && err.retryAfterSeconds !== undefined) {
25
+ response.headers.set('retry-after', String(err.retryAfterSeconds));
26
+ }
27
+ return response;
18
28
  }
19
- getLogger().error('Unexpected error in auth handler', err);
29
+ getLogger().error('Unexpected error in auth handler', {
30
+ operation,
31
+ error: err instanceof Error ? err.name : typeof err
32
+ });
20
33
  return errorResponse('INTERNAL_ERROR', 'An unexpected error occurred', 500);
21
34
  }
22
35
  /**
@@ -35,33 +48,57 @@ export function authFailureResponse(reason) {
35
48
  return errorResponse('INVALID_INPUT', 'Password does not meet requirements', 400);
36
49
  case 'email-in-use':
37
50
  return errorResponse('UNIQUE_CONSTRAINT', 'Email is already in use', 409);
51
+ case 'invalid-name':
52
+ return errorResponse('INVALID_INPUT', 'Invalid name', 400);
38
53
  }
39
54
  }
40
- async function readJsonBody(request) {
41
- try {
42
- return (await request.json());
43
- }
44
- catch {
45
- throw new InvalidInputError('Invalid JSON body');
55
+ /** `Retry-After` must be a positive whole number of seconds; clamp absurd values to one day. */
56
+ const MAX_RETRY_AFTER_SECONDS = 24 * 60 * 60;
57
+ async function enforceThrottle(throttle, attempt) {
58
+ if (!throttle)
59
+ return;
60
+ const decision = (await throttle(attempt));
61
+ if (decision?.allowed === true)
62
+ return;
63
+ if (decision?.allowed !== false) {
64
+ throw new Error('The auth throttle returned neither { allowed: true } nor { allowed: false }');
46
65
  }
66
+ const retry = 'retryAfterSeconds' in decision ? decision.retryAfterSeconds : undefined;
67
+ const retryAfter = typeof retry === 'number' && Number.isFinite(retry) && retry > 0
68
+ ? Math.min(Math.ceil(retry), MAX_RETRY_AFTER_SECONDS)
69
+ : undefined;
70
+ throw new RateLimitedError(retryAfter);
71
+ }
72
+ /** The canonical identifier handed to the throttle — the users adapter's own email normalisation. */
73
+ function canonicalIdentifier(email) {
74
+ return email.trim().toLowerCase();
47
75
  }
48
76
  /**
49
77
  * `POST` `{ email, password }` → `{ data: { user, token } }` (unchanged shape — Bearer-compatible)
50
78
  * plus a `Set-Cookie` that starts a browser session. `404` if the configured `AuthAdapter` doesn't
51
79
  * implement `login`.
80
+ *
81
+ * Order (spec 069): bounded body (`413`/`400`) → `options.throttle` (`429`) → `auth.login` → response.
52
82
  */
53
83
  export async function handleLogin(context, options) {
54
84
  const auth = options.runtime.adapters.auth;
55
85
  if (!auth.login) {
56
86
  return errorResponse('NOT_FOUND', 'Login is not supported by the configured auth adapter', 404);
57
87
  }
88
+ // A bad `maxBodyBytes` is a host configuration error: thrown as is, never mapped to a response.
89
+ const maxBytes = resolveMaxBodyBytes(options.maxBodyBytes);
58
90
  try {
59
- const body = await readJsonBody(context.request);
91
+ const body = await readBoundedJsonObject(context.request, { maxBytes });
60
92
  const email = typeof body['email'] === 'string' ? body['email'] : undefined;
61
93
  const password = typeof body['password'] === 'string' ? body['password'] : undefined;
62
94
  if (!email || !password) {
63
95
  return errorResponse('INVALID_INPUT', 'Missing email or password', 400);
64
96
  }
97
+ await enforceThrottle(options.throttle, {
98
+ action: 'login',
99
+ identifier: canonicalIdentifier(email),
100
+ request: context.request
101
+ });
65
102
  const result = await auth.login(email, password);
66
103
  if (!result.ok)
67
104
  return authFailureResponse(result.reason);
@@ -70,14 +107,16 @@ export async function handleLogin(context, options) {
70
107
  return response;
71
108
  }
72
109
  catch (err) {
73
- return toErrorResponse(err);
110
+ return toErrorResponse(err, 'login');
74
111
  }
75
112
  }
76
113
  /**
77
114
  * `POST` `{ email, password, name? }` → `{ data: { user, token } }` + `Set-Cookie`. Any other body
78
115
  * field (e.g. a `role`) is never read — role escalation through this endpoint is structurally
79
116
  * impossible, not merely hidden. `404` when `options.enabled` is `false` or the adapter doesn't
80
- * implement `signup`.
117
+ * implement `signup` — decided before the body is read or the throttle is called.
118
+ *
119
+ * Order (spec 069): bounded body (`413`/`400`) → `options.throttle` (`429`) → `auth.signup` → response.
81
120
  */
82
121
  export async function handleSignup(context, options) {
83
122
  if (!options.enabled) {
@@ -87,14 +126,21 @@ export async function handleSignup(context, options) {
87
126
  if (!auth.signup) {
88
127
  return errorResponse('NOT_FOUND', 'Signup is not supported by the configured auth adapter', 404);
89
128
  }
129
+ // A bad `maxBodyBytes` is a host configuration error: thrown as is, never mapped to a response.
130
+ const maxBytes = resolveMaxBodyBytes(options.maxBodyBytes);
90
131
  try {
91
- const body = await readJsonBody(context.request);
132
+ const body = await readBoundedJsonObject(context.request, { maxBytes });
92
133
  const email = typeof body['email'] === 'string' ? body['email'] : undefined;
93
134
  const password = typeof body['password'] === 'string' ? body['password'] : undefined;
94
135
  const name = typeof body['name'] === 'string' ? body['name'] : undefined;
95
136
  if (!email || !password) {
96
137
  return errorResponse('INVALID_INPUT', 'Missing email or password', 400);
97
138
  }
139
+ await enforceThrottle(options.throttle, {
140
+ action: 'signup',
141
+ identifier: canonicalIdentifier(email),
142
+ request: context.request
143
+ });
98
144
  const result = await auth.signup({ email, password, ...(name !== undefined && { name }) });
99
145
  if (!result.ok)
100
146
  return authFailureResponse(result.reason);
@@ -103,7 +149,7 @@ export async function handleSignup(context, options) {
103
149
  return response;
104
150
  }
105
151
  catch (err) {
106
- return toErrorResponse(err);
152
+ return toErrorResponse(err, 'signup');
107
153
  }
108
154
  }
109
155
  /**
@@ -116,7 +162,7 @@ export async function handleLogout(context, options) {
116
162
  assertCsrfSafe(context.request);
117
163
  }
118
164
  catch (err) {
119
- return toErrorResponse(err);
165
+ return toErrorResponse(err, 'logout');
120
166
  }
121
167
  const response = new Response(null, { status: 204 });
122
168
  response.headers.append('set-cookie', buildLogoutCookie({ secure: options.cookie?.secure ?? true }));
@@ -132,7 +178,7 @@ export async function handleMe(context, options) {
132
178
  if (err instanceof ForgeAuthError) {
133
179
  return errorResponse('UNAUTHORIZED', 'Unauthorized', 401);
134
180
  }
135
- return toErrorResponse(err);
181
+ return toErrorResponse(err, 'me');
136
182
  }
137
183
  }
138
184
  //# sourceMappingURL=auth-handlers.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"auth-handlers.js","sourceRoot":"","sources":["../src/auth-handlers.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,SAAS,EAAE,MAAM,iBAAiB,CAAC;AAE5C,OAAO,EAAE,cAAc,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AAExF,OAAO,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAC3C,OAAO,EAAE,iBAAiB,EAAE,YAAY,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAE9E,SAAS,YAAY,CAAC,IAAa,EAAE,MAAM,GAAG,GAAG;IAC/C,OAAO,IAAI,QAAQ,CAAC,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,EAAE;QACxC,MAAM;QACN,OAAO,EAAE,EAAE,cAAc,EAAE,kBAAkB,EAAE;KAChD,CAAC,CAAC;AACL,CAAC;AAED,SAAS,aAAa,CAAC,IAAY,EAAE,OAAe,EAAE,MAAc;IAClE,OAAO,YAAY,CAAC,EAAE,KAAK,EAAE,EAAE,IAAI,EAAE,OAAO,EAAE,EAAE,EAAE,MAAM,CAAC,CAAC;AAC5D,CAAC;AAED,SAAS,eAAe,CAAC,GAAY;IACnC,IAAI,YAAY,CAAC,GAAG,CAAC,EAAE,CAAC;QACtB,MAAM,IAAI,GAAG,cAAc,CAAC,GAAG,CAAC,CAAC;QACjC,OAAO,YAAY,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,CAAC;IACxC,CAAC;IACD,SAAS,EAAE,CAAC,KAAK,CAAC,kCAAkC,EAAE,GAAG,CAAC,CAAC;IAC3D,OAAO,aAAa,CAAC,gBAAgB,EAAE,8BAA8B,EAAE,GAAG,CAAC,CAAC;AAC9E,CAAC;AAED;;;;;GAKG;AACH,MAAM,UAAU,mBAAmB,CAAC,MAAyB;IAC3D,QAAQ,MAAM,EAAE,CAAC;QACf,KAAK,qBAAqB;YACxB,OAAO,aAAa,CAAC,cAAc,EAAE,2BAA2B,EAAE,GAAG,CAAC,CAAC;QACzE,KAAK,eAAe;YAClB,OAAO,aAAa,CAAC,eAAe,EAAE,uBAAuB,EAAE,GAAG,CAAC,CAAC;QACtE,KAAK,eAAe;YAClB,OAAO,aAAa,CAAC,eAAe,EAAE,qCAAqC,EAAE,GAAG,CAAC,CAAC;QACpF,KAAK,cAAc;YACjB,OAAO,aAAa,CAAC,mBAAmB,EAAE,yBAAyB,EAAE,GAAG,CAAC,CAAC;IAC9E,CAAC;AACH,CAAC;AAED,KAAK,UAAU,YAAY,CAAC,OAAgB;IAC1C,IAAI,CAAC;QACH,OAAO,CAAC,MAAM,OAAO,CAAC,IAAI,EAAE,CAA4B,CAAC;IAC3D,CAAC;IAAC,MAAM,CAAC;QACP,MAAM,IAAI,iBAAiB,CAAC,mBAAmB,CAAC,CAAC;IACnD,CAAC;AACH,CAAC;AAaD;;;;GAIG;AACH,MAAM,CAAC,KAAK,UAAU,WAAW,CAC/B,OAAyB,EACzB,OAAiC;IAEjC,MAAM,IAAI,GAAG,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,IAAI,CAAC;IAC3C,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE,CAAC;QAChB,OAAO,aAAa,CAAC,WAAW,EAAE,uDAAuD,EAAE,GAAG,CAAC,CAAC;IAClG,CAAC;IAED,IAAI,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,YAAY,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;QACjD,MAAM,KAAK,GAAG,OAAO,IAAI,CAAC,OAAO,CAAC,KAAK,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QAC5E,MAAM,QAAQ,GAAG,OAAO,IAAI,CAAC,UAAU,CAAC,KAAK,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QACrF,IAAI,CAAC,KAAK,IAAI,CAAC,QAAQ,EAAE,CAAC;YACxB,OAAO,aAAa,CAAC,eAAe,EAAE,2BAA2B,EAAE,GAAG,CAAC,CAAC;QAC1E,CAAC;QAED,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,KAAK,CAAC,KAAK,EAAE,QAAQ,CAAC,CAAC;QACjD,IAAI,CAAC,MAAM,CAAC,EAAE;YAAE,OAAO,mBAAmB,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;QAE1D,MAAM,QAAQ,GAAG,YAAY,CAAC,EAAE,IAAI,EAAE,EAAE,IAAI,EAAE,MAAM,CAAC,IAAI,EAAE,KAAK,EAAE,MAAM,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC;QACpF,QAAQ,CAAC,OAAO,CAAC,MAAM,CACrB,YAAY,EACZ,kBAAkB,CAAC,MAAM,CAAC,KAAK,EAAE,EAAE,MAAM,EAAE,OAAO,CAAC,MAAM,EAAE,MAAM,IAAI,IAAI,EAAE,CAAC,CAC7E,CAAC;QACF,OAAO,QAAQ,CAAC;IAClB,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,eAAe,CAAC,GAAG,CAAC,CAAC;IAC9B,CAAC;AACH,CAAC;AAED;;;;;GAKG;AACH,MAAM,CAAC,KAAK,UAAU,YAAY,CAChC,OAAyB,EACzB,OAAmC;IAEnC,IAAI,CAAC,OAAO,CAAC,OAAO,EAAE,CAAC;QACrB,OAAO,aAAa,CAAC,WAAW,EAAE,oBAAoB,EAAE,GAAG,CAAC,CAAC;IAC/D,CAAC;IAED,MAAM,IAAI,GAAG,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,IAAI,CAAC;IAC3C,IAAI,CAAC,IAAI,CAAC,MAAM,EAAE,CAAC;QACjB,OAAO,aAAa,CAClB,WAAW,EACX,wDAAwD,EACxD,GAAG,CACJ,CAAC;IACJ,CAAC;IAED,IAAI,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,YAAY,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;QACjD,MAAM,KAAK,GAAG,OAAO,IAAI,CAAC,OAAO,CAAC,KAAK,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QAC5E,MAAM,QAAQ,GAAG,OAAO,IAAI,CAAC,UAAU,CAAC,KAAK,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QACrF,MAAM,IAAI,GAAG,OAAO,IAAI,CAAC,MAAM,CAAC,KAAK,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QACzE,IAAI,CAAC,KAAK,IAAI,CAAC,QAAQ,EAAE,CAAC;YACxB,OAAO,aAAa,CAAC,eAAe,EAAE,2BAA2B,EAAE,GAAG,CAAC,CAAC;QAC1E,CAAC;QAED,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,MAAM,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,GAAG,CAAC,IAAI,KAAK,SAAS,IAAI,EAAE,IAAI,EAAE,CAAC,EAAE,CAAC,CAAC;QAC3F,IAAI,CAAC,MAAM,CAAC,EAAE;YAAE,OAAO,mBAAmB,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;QAE1D,MAAM,QAAQ,GAAG,YAAY,CAAC,EAAE,IAAI,EAAE,EAAE,IAAI,EAAE,MAAM,CAAC,IAAI,EAAE,KAAK,EAAE,MAAM,CAAC,KAAK,EAAE,EAAE,EAAE,GAAG,CAAC,CAAC;QACzF,QAAQ,CAAC,OAAO,CAAC,MAAM,CACrB,YAAY,EACZ,kBAAkB,CAAC,MAAM,CAAC,KAAK,EAAE,EAAE,MAAM,EAAE,OAAO,CAAC,MAAM,EAAE,MAAM,IAAI,IAAI,EAAE,CAAC,CAC7E,CAAC;QACF,OAAO,QAAQ,CAAC;IAClB,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,eAAe,CAAC,GAAG,CAAC,CAAC;IAC9B,CAAC;AACH,CAAC;AAED;;;;GAIG;AACH,MAAM,CAAC,KAAK,UAAU,YAAY,CAChC,OAAyB,EACzB,OAAiC;IAEjC,IAAI,CAAC;QACH,cAAc,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;IAClC,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,eAAe,CAAC,GAAG,CAAC,CAAC;IAC9B,CAAC;IAED,MAAM,QAAQ,GAAG,IAAI,QAAQ,CAAC,IAAI,EAAE,EAAE,MAAM,EAAE,GAAG,EAAE,CAAC,CAAC;IACrD,QAAQ,CAAC,OAAO,CAAC,MAAM,CACrB,YAAY,EACZ,iBAAiB,CAAC,EAAE,MAAM,EAAE,OAAO,CAAC,MAAM,EAAE,MAAM,IAAI,IAAI,EAAE,CAAC,CAC9D,CAAC;IACF,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED,8EAA8E;AAC9E,MAAM,CAAC,KAAK,UAAU,QAAQ,CAC5B,OAAyB,EACzB,OAAiC;IAEjC,IAAI,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,IAAI,CAAC,WAAW,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;QAC9E,OAAO,YAAY,CAAC,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC,CAAC;IACtC,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,IAAI,GAAG,YAAY,cAAc,EAAE,CAAC;YAClC,OAAO,aAAa,CAAC,cAAc,EAAE,cAAc,EAAE,GAAG,CAAC,CAAC;QAC5D,CAAC;QACD,OAAO,eAAe,CAAC,GAAG,CAAC,CAAC;IAC9B,CAAC;AACH,CAAC"}
1
+ {"version":3,"file":"auth-handlers.js","sourceRoot":"","sources":["../src/auth-handlers.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,19 @@
1
+ import type { OperationContext } from './context.js';
2
+ /**
3
+ * Is `slug` a collection whose lifecycle the configured `AuthAdapter` owns (spec 061)? Asked of the
4
+ * adapter through its optional `managesCollection` — the runtime never inspects a concrete adapter or a
5
+ * slug convention, so an adapter that omits the method (or a composite of such adapters) restricts
6
+ * nothing.
7
+ */
8
+ export declare function isAuthManagedCollection(ctx: OperationContext, slug: string): boolean;
9
+ /**
10
+ * The generic-mutation boundary. Called first thing by `create`/`update`/`deleteDocumentInternal`/
11
+ * `restoreVersion` — before hooks, access checks and any read or write — so the answer is the same for
12
+ * every caller (`overrideAccess: true` bypasses *authorization*, never the auth subsystem's
13
+ * data-integrity invariants) and for a document that does not exist, and a refusal has no side effects.
14
+ * The message deliberately does not distinguish create/update/delete — the boundary is the same for all
15
+ * three, and the caller's fix (use the auth adapter's own operations) does not depend on which one this
16
+ * was.
17
+ */
18
+ export declare function assertNotAuthManaged(ctx: OperationContext, slug: string): void;
19
+ //# sourceMappingURL=auth-managed.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth-managed.d.ts","sourceRoot":"","sources":["../src/auth-managed.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,cAAc,CAAC;AAGrD;;;;;GAKG;AACH,wBAAgB,uBAAuB,CAAC,GAAG,EAAE,gBAAgB,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAEpF;AAED;;;;;;;;GAQG;AACH,wBAAgB,oBAAoB,CAAC,GAAG,EAAE,gBAAgB,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI,CAE9E"}
@@ -0,0 +1,24 @@
1
+ import { AuthManagedCollectionError } from './errors.js';
2
+ /**
3
+ * Is `slug` a collection whose lifecycle the configured `AuthAdapter` owns (spec 061)? Asked of the
4
+ * adapter through its optional `managesCollection` — the runtime never inspects a concrete adapter or a
5
+ * slug convention, so an adapter that omits the method (or a composite of such adapters) restricts
6
+ * nothing.
7
+ */
8
+ export function isAuthManagedCollection(ctx, slug) {
9
+ return ctx.adapters.auth.managesCollection?.(slug) === true;
10
+ }
11
+ /**
12
+ * The generic-mutation boundary. Called first thing by `create`/`update`/`deleteDocumentInternal`/
13
+ * `restoreVersion` — before hooks, access checks and any read or write — so the answer is the same for
14
+ * every caller (`overrideAccess: true` bypasses *authorization*, never the auth subsystem's
15
+ * data-integrity invariants) and for a document that does not exist, and a refusal has no side effects.
16
+ * The message deliberately does not distinguish create/update/delete — the boundary is the same for all
17
+ * three, and the caller's fix (use the auth adapter's own operations) does not depend on which one this
18
+ * was.
19
+ */
20
+ export function assertNotAuthManaged(ctx, slug) {
21
+ if (isAuthManagedCollection(ctx, slug))
22
+ throw new AuthManagedCollectionError(slug);
23
+ }
24
+ //# sourceMappingURL=auth-managed.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth-managed.js","sourceRoot":"","sources":["../src/auth-managed.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,0BAA0B,EAAE,MAAM,aAAa,CAAC;AAEzD;;;;;GAKG;AACH,MAAM,UAAU,uBAAuB,CAAC,GAAqB,EAAE,IAAY;IACzE,OAAO,GAAG,CAAC,QAAQ,CAAC,IAAI,CAAC,iBAAiB,EAAE,CAAC,IAAI,CAAC,KAAK,IAAI,CAAC;AAC9D,CAAC;AAED;;;;;;;;GAQG;AACH,MAAM,UAAU,oBAAoB,CAAC,GAAqB,EAAE,IAAY;IACtE,IAAI,uBAAuB,CAAC,GAAG,EAAE,IAAI,CAAC;QAAE,MAAM,IAAI,0BAA0B,CAAC,IAAI,CAAC,CAAC;AACrF,CAAC"}
package/dist/body.d.ts ADDED
@@ -0,0 +1,28 @@
1
+ /**
2
+ * Default bound for an auth JSON body (spec 069): `{ email, password, name }` at their own bounds —
3
+ * a 1024-character password (≤ 3 KB of UTF-8), a 254-character email and a 256-character name — plus
4
+ * keys and whitespace, with room to spare. A request needs a fraction of it.
5
+ */
6
+ export declare const DEFAULT_AUTH_MAX_BODY_BYTES: number;
7
+ export interface ReadBoundedJsonOptions {
8
+ /** Defaults to {@link DEFAULT_AUTH_MAX_BODY_BYTES}. An integer between 1 and 1 MiB. */
9
+ maxBytes?: number;
10
+ }
11
+ /**
12
+ * Validates a configured bound. Called by the auth handlers before their error mapping, so a bad value
13
+ * is a thrown configuration error with its message intact, not a redacted `500` on every request.
14
+ */
15
+ export declare function resolveMaxBodyBytes(maxBytes: number | undefined): number;
16
+ /**
17
+ * Reads a JSON-object request body without ever holding more than `maxBytes` of it (spec 069).
18
+ *
19
+ * 1. A valid `Content-Length` over the bound is refused before any read.
20
+ * 2. The stream is read chunk by chunk and cancelled as soon as the running total passes the bound — a
21
+ * missing or lying `Content-Length` cannot get past it.
22
+ * 3. The bytes must be valid UTF-8 and parse as JSON, and the value must be a plain object.
23
+ *
24
+ * Throws `PayloadTooLargeError` (`413`) or `InvalidInputError` (`400`); neither message contains any of
25
+ * the body. Web Streams only — runs unchanged on Workers, Node, Deno and Bun.
26
+ */
27
+ export declare function readBoundedJsonObject(request: Request, options?: ReadBoundedJsonOptions): Promise<Record<string, unknown>>;
28
+ //# sourceMappingURL=body.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"body.d.ts","sourceRoot":"","sources":["../src/body.ts"],"names":[],"mappings":"AAEA;;;;GAIG;AACH,eAAO,MAAM,2BAA2B,QAAW,CAAC;AAKpD,MAAM,WAAW,sBAAsB;IACrC,uFAAuF;IACvF,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED;;;GAGG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,SAAS,GAAG,MAAM,CAQxE;AAQD;;;;;;;;;;GAUG;AACH,wBAAsB,qBAAqB,CACzC,OAAO,EAAE,OAAO,EAChB,OAAO,GAAE,sBAA2B,GACnC,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CA2ClC"}
package/dist/body.js ADDED
@@ -0,0 +1,81 @@
1
+ import { InvalidInputError, PayloadTooLargeError } from './errors.js';
2
+ /**
3
+ * Default bound for an auth JSON body (spec 069): `{ email, password, name }` at their own bounds —
4
+ * a 1024-character password (≤ 3 KB of UTF-8), a 254-character email and a 256-character name — plus
5
+ * keys and whitespace, with room to spare. A request needs a fraction of it.
6
+ */
7
+ export const DEFAULT_AUTH_MAX_BODY_BYTES = 8 * 1024;
8
+ /** No configuration may raise a bounded body above this. */
9
+ const MAX_BODY_BYTES_CEILING = 1024 * 1024;
10
+ /**
11
+ * Validates a configured bound. Called by the auth handlers before their error mapping, so a bad value
12
+ * is a thrown configuration error with its message intact, not a redacted `500` on every request.
13
+ */
14
+ export function resolveMaxBodyBytes(maxBytes) {
15
+ const value = maxBytes ?? DEFAULT_AUTH_MAX_BODY_BYTES;
16
+ if (!Number.isInteger(value) || value < 1 || value > MAX_BODY_BYTES_CEILING) {
17
+ throw new Error(`maxBodyBytes must be an integer between 1 and ${MAX_BODY_BYTES_CEILING}; got ${String(value)}.`);
18
+ }
19
+ return value;
20
+ }
21
+ function cancelQuietly(body) {
22
+ if (!body)
23
+ return;
24
+ // Best effort: stop the upstream sender. A body that is already locked or closed has nothing to cancel.
25
+ body.cancel().catch(() => undefined);
26
+ }
27
+ /**
28
+ * Reads a JSON-object request body without ever holding more than `maxBytes` of it (spec 069).
29
+ *
30
+ * 1. A valid `Content-Length` over the bound is refused before any read.
31
+ * 2. The stream is read chunk by chunk and cancelled as soon as the running total passes the bound — a
32
+ * missing or lying `Content-Length` cannot get past it.
33
+ * 3. The bytes must be valid UTF-8 and parse as JSON, and the value must be a plain object.
34
+ *
35
+ * Throws `PayloadTooLargeError` (`413`) or `InvalidInputError` (`400`); neither message contains any of
36
+ * the body. Web Streams only — runs unchanged on Workers, Node, Deno and Bun.
37
+ */
38
+ export async function readBoundedJsonObject(request, options = {}) {
39
+ const maxBytes = resolveMaxBodyBytes(options.maxBytes);
40
+ const declared = request.headers.get('content-length');
41
+ if (declared !== null && /^\d+$/.test(declared.trim()) && Number(declared) > maxBytes) {
42
+ cancelQuietly(request.body);
43
+ throw new PayloadTooLargeError();
44
+ }
45
+ if (request.bodyUsed)
46
+ throw new InvalidInputError('Request body was already read');
47
+ const chunks = [];
48
+ let total = 0;
49
+ if (request.body) {
50
+ const reader = request.body.getReader();
51
+ for (;;) {
52
+ const { done, value } = await reader.read();
53
+ if (done)
54
+ break;
55
+ total += value.byteLength;
56
+ if (total > maxBytes) {
57
+ await reader.cancel().catch(() => undefined);
58
+ throw new PayloadTooLargeError();
59
+ }
60
+ chunks.push(value);
61
+ }
62
+ }
63
+ const bytes = new Uint8Array(total);
64
+ let offset = 0;
65
+ for (const chunk of chunks) {
66
+ bytes.set(chunk, offset);
67
+ offset += chunk.byteLength;
68
+ }
69
+ let parsed;
70
+ try {
71
+ parsed = JSON.parse(new TextDecoder('utf-8', { fatal: true }).decode(bytes));
72
+ }
73
+ catch {
74
+ throw new InvalidInputError('Invalid JSON body');
75
+ }
76
+ if (typeof parsed !== 'object' || parsed === null || Array.isArray(parsed)) {
77
+ throw new InvalidInputError('JSON body must be an object');
78
+ }
79
+ return parsed;
80
+ }
81
+ //# sourceMappingURL=body.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"body.js","sourceRoot":"","sources":["../src/body.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,8 @@
1
+ /**
2
+ * A compare-and-set on `updated_at` is only as fine as the millisecond the adapters stamp. Before a CAS
3
+ * write, wait until the clock has passed the stamp that was read, so this write's own stamp is strictly
4
+ * later: a concurrent CAS writer that read the same row then cannot match it (spec 066 review). Bounded:
5
+ * at most a few milliseconds. Clock skew *between* processes is outside what this can see.
6
+ */
7
+ export declare function afterStamp(stamp: unknown): Promise<void>;
8
+ //# sourceMappingURL=concurrency.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"concurrency.d.ts","sourceRoot":"","sources":["../src/concurrency.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,wBAAsB,UAAU,CAAC,KAAK,EAAE,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAM9D"}
@@ -0,0 +1,15 @@
1
+ /**
2
+ * A compare-and-set on `updated_at` is only as fine as the millisecond the adapters stamp. Before a CAS
3
+ * write, wait until the clock has passed the stamp that was read, so this write's own stamp is strictly
4
+ * later: a concurrent CAS writer that read the same row then cannot match it (spec 066 review). Bounded:
5
+ * at most a few milliseconds. Clock skew *between* processes is outside what this can see.
6
+ */
7
+ export async function afterStamp(stamp) {
8
+ const seen = typeof stamp === 'string' ? Date.parse(stamp) : NaN;
9
+ if (Number.isNaN(seen))
10
+ return;
11
+ for (let i = 0; i < 20 && Date.now() <= seen; i++) {
12
+ await new Promise((resolve) => setTimeout(resolve, 1));
13
+ }
14
+ }
15
+ //# sourceMappingURL=concurrency.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"concurrency.js","sourceRoot":"","sources":["../src/concurrency.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,MAAM,CAAC,KAAK,UAAU,UAAU,CAAC,KAAc;IAC7C,MAAM,IAAI,GAAG,OAAO,KAAK,KAAK,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC;IACjE,IAAI,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC;QAAE,OAAO;IAC/B,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,EAAE,IAAI,IAAI,CAAC,GAAG,EAAE,IAAI,IAAI,EAAE,CAAC,EAAE,EAAE,CAAC;QAClD,MAAM,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,CAAC;IACzD,CAAC;AACH,CAAC"}
package/dist/context.d.ts CHANGED
@@ -12,5 +12,10 @@ export interface OperationContext {
12
12
  getCollection(slug: string): CollectionDefinition | undefined;
13
13
  getGlobal(slug: string): GlobalDefinition | undefined;
14
14
  getCollections(): readonly CollectionDefinition[];
15
+ /**
16
+ * Every registered global. Optional so a structural implementation written before spec 064 still
17
+ * type-checks; without it, relation integrity cannot see references held by globals.
18
+ */
19
+ getGlobals?(): readonly GlobalDefinition[];
15
20
  }
16
21
  //# sourceMappingURL=context.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AAC9E,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAE9C;;;;;;GAMG;AACH,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,QAAQ,EAAE,UAAU,CAAC;IAC9B,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,oBAAoB,GAAG,SAAS,CAAC;IAC9D,SAAS,CAAC,IAAI,EAAE,MAAM,GAAG,gBAAgB,GAAG,SAAS,CAAC;IACtD,cAAc,IAAI,SAAS,oBAAoB,EAAE,CAAC;CACnD"}
1
+ {"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AAC9E,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAE9C;;;;;;GAMG;AACH,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,QAAQ,EAAE,UAAU,CAAC;IAC9B,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,oBAAoB,GAAG,SAAS,CAAC;IAC9D,SAAS,CAAC,IAAI,EAAE,MAAM,GAAG,gBAAgB,GAAG,SAAS,CAAC;IACtD,cAAc,IAAI,SAAS,oBAAoB,EAAE,CAAC;IAClD;;;OAGG;IACH,UAAU,CAAC,IAAI,SAAS,gBAAgB,EAAE,CAAC;CAC5C"}
package/dist/errors.d.ts CHANGED
@@ -1,5 +1,5 @@
1
1
  import type { ValidationError } from '@forge-cms/core';
2
- export type ForgeErrorCode = 'NOT_FOUND' | 'INVALID_INPUT' | 'VALIDATION_ERROR' | 'UNAUTHORIZED' | 'FORBIDDEN' | 'UNKNOWN_FIELD' | 'INVALID_QUERY' | 'UNIQUE_CONSTRAINT' | 'INTERNAL_ERROR';
2
+ export type ForgeErrorCode = 'NOT_FOUND' | 'INVALID_INPUT' | 'VALIDATION_ERROR' | 'UNAUTHORIZED' | 'FORBIDDEN' | 'UNKNOWN_FIELD' | 'INVALID_QUERY' | 'UNIQUE_CONSTRAINT' | 'AUTH_MANAGED_COLLECTION' | 'CONCURRENT_MODIFICATION' | 'PAYLOAD_TOO_LARGE' | 'RATE_LIMITED' | 'INTERNAL_ERROR';
3
3
  export declare class ForgeError extends Error {
4
4
  readonly status: number;
5
5
  readonly code: ForgeErrorCode;
@@ -47,6 +47,51 @@ export declare class UniqueConstraintError extends ForgeError {
47
47
  readonly fields: string[];
48
48
  constructor(collection: string, fields: string[]);
49
49
  }
50
+ /**
51
+ * A generic `create`/`update`/`delete` targeted a collection whose lifecycle the configured
52
+ * `AuthAdapter` owns (`AuthAdapter.managesCollection`, spec 061). Those mutations would bypass the
53
+ * adapter's invariants — first-admin provisioning, last-admin protection, password hashing, email
54
+ * normalisation, session versioning — so they are refused for every caller, trusted (`overrideAccess:
55
+ * true`) or not. Deliberately says nothing about which adapter or how; the way out is the auth
56
+ * adapter's own user-management operations.
57
+ */
58
+ export declare class AuthManagedCollectionError extends ForgeError {
59
+ readonly collection: string;
60
+ constructor(collection: string);
61
+ }
62
+ /**
63
+ * A versioned document mutation lost a race (spec 062): another write committed a new version of the
64
+ * same document after this one read it, so this one's document write and snapshot were rolled back
65
+ * together — nothing was written. Forge never retries it automatically (`before*` hooks may already
66
+ * have run); re-read the document and submit again. Deliberately names the public collection slug,
67
+ * never the internal `_versions_*` table whose unique index detected the conflict.
68
+ *
69
+ * Spec 064 reuses it for relation lifecycle conflicts — a referenced document deleted while a write was
70
+ * in progress, or a relation delete whose graph changed before it committed — with a `message` saying
71
+ * so. The meaning is the same: another request changed what this one depended on; nothing was written.
72
+ */
73
+ export declare class ConcurrentModificationError extends ForgeError {
74
+ readonly collection: string;
75
+ readonly id: string;
76
+ constructor(collection: string, id: string, message?: string);
77
+ }
78
+ /**
79
+ * A request body over a Forge-owned size bound (spec 069; today: the auth JSON bodies read by
80
+ * `readBoundedJsonObject`). Says nothing about the body's contents.
81
+ */
82
+ export declare class PayloadTooLargeError extends ForgeError {
83
+ constructor(message?: string);
84
+ }
85
+ /**
86
+ * The host's auth throttle refused a login/signup attempt (spec 069). The message is fixed and generic:
87
+ * it never says whether the account exists, which limit fired or how many attempts remain.
88
+ * `retryAfterSeconds` is already validated (a positive integer) when present; the auth handlers emit it
89
+ * as `Retry-After`.
90
+ */
91
+ export declare class RateLimitedError extends ForgeError {
92
+ readonly retryAfterSeconds?: number;
93
+ constructor(retryAfterSeconds?: number);
94
+ }
50
95
  export declare function isForgeError(err: unknown): err is ForgeError;
51
96
  export interface ForgeApiErrorBody {
52
97
  error: {
@@ -1 +1 @@
1
- {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,iBAAiB,CAAC;AAEvD,MAAM,MAAM,cAAc,GACtB,WAAW,GACX,eAAe,GACf,kBAAkB,GAClB,cAAc,GACd,WAAW,GACX,eAAe,GACf,eAAe,GACf,mBAAmB,GACnB,gBAAgB,CAAC;AAErB,qBAAa,UAAW,SAAQ,KAAK;IACnC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,IAAI,EAAE,cAAc,CAAC;gBAElB,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,cAAc;CAMlE;AAED,qBAAa,aAAc,SAAQ,UAAU;gBAC/B,OAAO,EAAE,MAAM;CAG5B;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,EAAE,MAAM;CAG5B;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,EAAE,MAAM;CAG5B;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,EAAE,MAAM;CAG5B;AAED,qBAAa,qBAAsB,SAAQ,UAAU;IACnD,QAAQ,CAAC,OAAO,EAAE,eAAe,EAAE,CAAC;gBAExB,OAAO,EAAE,eAAe,EAAE;CAIvC;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,SAAiB;CAGrC;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,SAAc;CAGlC;AAED;;;;;GAKG;AACH,qBAAa,SAAU,SAAQ,UAAU;gBAC3B,OAAO,SAAgC;CAGpD;AAED;;;;;GAKG;AACH,qBAAa,qBAAsB,SAAQ,UAAU;IACnD,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC;gBAEd,UAAU,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE;CAWjD;AAED,wBAAgB,YAAY,CAAC,GAAG,EAAE,OAAO,GAAG,GAAG,IAAI,UAAU,CAE5D;AAED,MAAM,WAAW,iBAAiB;IAChC,KAAK,EAAE;QACL,IAAI,EAAE,cAAc,CAAC;QACrB,OAAO,EAAE,MAAM,CAAC;QAChB,OAAO,CAAC,EAAE,OAAO,CAAC;KACnB,CAAC;CACH;AAED,wBAAgB,cAAc,CAAC,GAAG,EAAE,UAAU,GAAG,iBAAiB,CAyBjE"}
1
+ {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,iBAAiB,CAAC;AAEvD,MAAM,MAAM,cAAc,GACtB,WAAW,GACX,eAAe,GACf,kBAAkB,GAClB,cAAc,GACd,WAAW,GACX,eAAe,GACf,eAAe,GACf,mBAAmB,GACnB,yBAAyB,GACzB,yBAAyB,GACzB,mBAAmB,GACnB,cAAc,GACd,gBAAgB,CAAC;AAErB,qBAAa,UAAW,SAAQ,KAAK;IACnC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,IAAI,EAAE,cAAc,CAAC;gBAElB,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,cAAc;CAMlE;AAED,qBAAa,aAAc,SAAQ,UAAU;gBAC/B,OAAO,EAAE,MAAM;CAG5B;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,EAAE,MAAM;CAG5B;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,EAAE,MAAM;CAG5B;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,EAAE,MAAM;CAG5B;AAED,qBAAa,qBAAsB,SAAQ,UAAU;IACnD,QAAQ,CAAC,OAAO,EAAE,eAAe,EAAE,CAAC;gBAExB,OAAO,EAAE,eAAe,EAAE;CAIvC;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,SAAiB;CAGrC;AAED,qBAAa,iBAAkB,SAAQ,UAAU;gBACnC,OAAO,SAAc;CAGlC;AAED;;;;;GAKG;AACH,qBAAa,SAAU,SAAQ,UAAU;gBAC3B,OAAO,SAAgC;CAGpD;AAED;;;;;GAKG;AACH,qBAAa,qBAAsB,SAAQ,UAAU;IACnD,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC;gBAEd,UAAU,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE;CAWjD;AAED;;;;;;;GAOG;AACH,qBAAa,0BAA2B,SAAQ,UAAU;IACxD,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;gBAEhB,UAAU,EAAE,MAAM;CAS/B;AAED;;;;;;;;;;GAUG;AACH,qBAAa,2BAA4B,SAAQ,UAAU;IACzD,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;gBAER,UAAU,EAAE,MAAM,EAAE,EAAE,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAW7D;AAED;;;GAGG;AACH,qBAAa,oBAAqB,SAAQ,UAAU;gBACtC,OAAO,SAA8B;CAGlD;AAED;;;;;GAKG;AACH,qBAAa,gBAAiB,SAAQ,UAAU;IAC9C,QAAQ,CAAC,iBAAiB,CAAC,EAAE,MAAM,CAAC;gBAExB,iBAAiB,CAAC,EAAE,MAAM;CAIvC;AAED,wBAAgB,YAAY,CAAC,GAAG,EAAE,OAAO,GAAG,GAAG,IAAI,UAAU,CAE5D;AAED,MAAM,WAAW,iBAAiB;IAChC,KAAK,EAAE;QACL,IAAI,EAAE,cAAc,CAAC;QACrB,OAAO,EAAE,MAAM,CAAC;QAChB,OAAO,CAAC,EAAE,OAAO,CAAC;KACnB,CAAC;CACH;AAED,wBAAgB,cAAc,CAAC,GAAG,EAAE,UAAU,GAAG,iBAAiB,CAyBjE"}