@lunora/errors 1.0.0-alpha.1 → 1.0.0-alpha.3
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/LICENSE.md +6 -0
- package/dist/index.d.mts +33 -4
- package/dist/index.d.ts +33 -4
- package/dist/index.mjs +5 -5
- package/dist/packem_shared/{ERROR_CATALOG-D3knuUQT.mjs → ERROR_CATALOG-CoCPcAHf.mjs} +25 -8
- package/dist/packem_shared/{LunoraError-bpS_TPIe.mjs → LunoraError-CwQSmeL3.mjs} +1 -1
- package/dist/packem_shared/{invariant-DLXTsHpj.mjs → invariant-DawIQfjN.mjs} +1 -1
- package/dist/packem_shared/{isLunoraError-BvsoKcWE.mjs → isLunoraError-CSQtYMrF.mjs} +1 -1
- package/dist/packem_shared/{toErrorBody-DihI5p4Q.mjs → toErrorBody-CyqyVwGF.mjs} +2 -2
- package/package.json +1 -1
package/LICENSE.md
CHANGED
|
@@ -103,3 +103,9 @@ Unless required by applicable law or agreed to in writing, software distributed
|
|
|
103
103
|
under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
|
|
104
104
|
CONDITIONS OF ANY KIND, either express or implied. See the License for the
|
|
105
105
|
specific language governing permissions and limitations under the License.
|
|
106
|
+
|
|
107
|
+
<!-- DEPENDENCIES -->
|
|
108
|
+
<!-- /DEPENDENCIES -->
|
|
109
|
+
|
|
110
|
+
<!-- TYPE_DEPENDENCIES -->
|
|
111
|
+
<!-- /TYPE_DEPENDENCIES -->
|
package/dist/index.d.mts
CHANGED
|
@@ -59,9 +59,9 @@ declare const ERROR_CATALOG: {
|
|
|
59
59
|
readonly title: "Conflict";
|
|
60
60
|
};
|
|
61
61
|
readonly NOT_UNIQUE: {
|
|
62
|
-
readonly hint: readonly ["
|
|
62
|
+
readonly hint: readonly ["`.unique()` matched more than one document — it expects the query to identify at most one row.", "", "- If several matches are legitimate, use `.first()` (take one) or `.collect()` (take all) instead.", "- Otherwise tighten the query (e.g. filter on a unique/indexed field) so it can only match one row."];
|
|
63
63
|
readonly status: 400;
|
|
64
|
-
readonly title: "
|
|
64
|
+
readonly title: "Query matched more than one document";
|
|
65
65
|
};
|
|
66
66
|
readonly VALIDATION_ERROR: {
|
|
67
67
|
readonly status: 400;
|
|
@@ -125,6 +125,23 @@ declare const ERROR_CATALOG: {
|
|
|
125
125
|
readonly status: 403;
|
|
126
126
|
readonly title: "RLS policy required";
|
|
127
127
|
};
|
|
128
|
+
readonly RUN_DEPTH_EXCEEDED: {
|
|
129
|
+
readonly internal: true;
|
|
130
|
+
readonly status: 500;
|
|
131
|
+
readonly title: "Run depth exceeded";
|
|
132
|
+
};
|
|
133
|
+
readonly MIGRATION_NOT_FOUND: {
|
|
134
|
+
readonly status: 404;
|
|
135
|
+
readonly title: "Data migration not found";
|
|
136
|
+
};
|
|
137
|
+
readonly UNKNOWN_TABLE: {
|
|
138
|
+
readonly status: 404;
|
|
139
|
+
readonly title: "Unknown table";
|
|
140
|
+
};
|
|
141
|
+
readonly GLOBAL_TABLE_NOT_EDITABLE: {
|
|
142
|
+
readonly status: 400;
|
|
143
|
+
readonly title: "Global table is not editable";
|
|
144
|
+
};
|
|
128
145
|
readonly SHARD_ERROR: {
|
|
129
146
|
readonly status: 503;
|
|
130
147
|
readonly title: "Shard error";
|
|
@@ -136,20 +153,25 @@ declare const ERROR_CATALOG: {
|
|
|
136
153
|
readonly OFFLINE_IDENTITY_CHANGED: {
|
|
137
154
|
readonly status: 409;
|
|
138
155
|
readonly title: "Offline identity changed";
|
|
139
|
-
}; /** Package-specific codes. Build-time
|
|
156
|
+
}; /** Package-specific codes. Build-time-only — never cross the RPC wire, so deliberately not `internal`. */
|
|
140
157
|
readonly CODEGEN_DIAGNOSTIC: {
|
|
141
158
|
readonly status: 500;
|
|
142
159
|
readonly title: "Codegen diagnostic";
|
|
143
160
|
};
|
|
161
|
+
/** Build-time-only — never crosses the RPC wire, so deliberately not `internal`. */
|
|
144
162
|
readonly SCHEMA_SNAPSHOT_PARSE: {
|
|
145
163
|
readonly status: 500;
|
|
146
164
|
readonly title: "Schema snapshot parse error";
|
|
147
165
|
};
|
|
166
|
+
/** Runtime-reachable (env.ts): message enumerates failing env key names — redact on the wire. */
|
|
148
167
|
readonly ENV_INVALID: {
|
|
168
|
+
readonly internal: true;
|
|
149
169
|
readonly status: 500;
|
|
150
170
|
readonly title: "Invalid environment";
|
|
151
171
|
};
|
|
172
|
+
/** Runtime-reachable (auth/middleware.ts): message carries auth-wiring guidance — redact on the wire. */
|
|
152
173
|
readonly AUTH_HEADERS_MISSING: {
|
|
174
|
+
readonly internal: true;
|
|
153
175
|
readonly status: 500;
|
|
154
176
|
readonly title: "Auth headers missing";
|
|
155
177
|
};
|
|
@@ -290,8 +312,15 @@ interface LunoraErrorLike extends Error {
|
|
|
290
312
|
docsUrl?: string;
|
|
291
313
|
hint?: ErrorHint;
|
|
292
314
|
status: number;
|
|
315
|
+
/** Wire brand that distinguishes real `LunoraError`s from foreign errors. */
|
|
316
|
+
type: "VisulimaError";
|
|
293
317
|
}
|
|
294
|
-
/**
|
|
318
|
+
/**
|
|
319
|
+
* True when `error` carries the Lunora transport shape (string `code` + numeric
|
|
320
|
+
* `status` + the `VisulimaError` brand). The `type` brand is what distinguishes
|
|
321
|
+
* a real `LunoraError` (or its wire-decoded twin) from a foreign error that
|
|
322
|
+
* happens to carry `code`/`status` — see plan 119 for the full rationale.
|
|
323
|
+
*/
|
|
295
324
|
declare const isLunoraError: (error: unknown) => error is LunoraErrorLike;
|
|
296
325
|
/** Throw an `INTERNAL` {@link LunoraError} when `condition` is falsy. */
|
|
297
326
|
declare const invariant: (condition: unknown, message: string) => asserts condition;
|
package/dist/index.d.ts
CHANGED
|
@@ -59,9 +59,9 @@ declare const ERROR_CATALOG: {
|
|
|
59
59
|
readonly title: "Conflict";
|
|
60
60
|
};
|
|
61
61
|
readonly NOT_UNIQUE: {
|
|
62
|
-
readonly hint: readonly ["
|
|
62
|
+
readonly hint: readonly ["`.unique()` matched more than one document — it expects the query to identify at most one row.", "", "- If several matches are legitimate, use `.first()` (take one) or `.collect()` (take all) instead.", "- Otherwise tighten the query (e.g. filter on a unique/indexed field) so it can only match one row."];
|
|
63
63
|
readonly status: 400;
|
|
64
|
-
readonly title: "
|
|
64
|
+
readonly title: "Query matched more than one document";
|
|
65
65
|
};
|
|
66
66
|
readonly VALIDATION_ERROR: {
|
|
67
67
|
readonly status: 400;
|
|
@@ -125,6 +125,23 @@ declare const ERROR_CATALOG: {
|
|
|
125
125
|
readonly status: 403;
|
|
126
126
|
readonly title: "RLS policy required";
|
|
127
127
|
};
|
|
128
|
+
readonly RUN_DEPTH_EXCEEDED: {
|
|
129
|
+
readonly internal: true;
|
|
130
|
+
readonly status: 500;
|
|
131
|
+
readonly title: "Run depth exceeded";
|
|
132
|
+
};
|
|
133
|
+
readonly MIGRATION_NOT_FOUND: {
|
|
134
|
+
readonly status: 404;
|
|
135
|
+
readonly title: "Data migration not found";
|
|
136
|
+
};
|
|
137
|
+
readonly UNKNOWN_TABLE: {
|
|
138
|
+
readonly status: 404;
|
|
139
|
+
readonly title: "Unknown table";
|
|
140
|
+
};
|
|
141
|
+
readonly GLOBAL_TABLE_NOT_EDITABLE: {
|
|
142
|
+
readonly status: 400;
|
|
143
|
+
readonly title: "Global table is not editable";
|
|
144
|
+
};
|
|
128
145
|
readonly SHARD_ERROR: {
|
|
129
146
|
readonly status: 503;
|
|
130
147
|
readonly title: "Shard error";
|
|
@@ -136,20 +153,25 @@ declare const ERROR_CATALOG: {
|
|
|
136
153
|
readonly OFFLINE_IDENTITY_CHANGED: {
|
|
137
154
|
readonly status: 409;
|
|
138
155
|
readonly title: "Offline identity changed";
|
|
139
|
-
}; /** Package-specific codes. Build-time
|
|
156
|
+
}; /** Package-specific codes. Build-time-only — never cross the RPC wire, so deliberately not `internal`. */
|
|
140
157
|
readonly CODEGEN_DIAGNOSTIC: {
|
|
141
158
|
readonly status: 500;
|
|
142
159
|
readonly title: "Codegen diagnostic";
|
|
143
160
|
};
|
|
161
|
+
/** Build-time-only — never crosses the RPC wire, so deliberately not `internal`. */
|
|
144
162
|
readonly SCHEMA_SNAPSHOT_PARSE: {
|
|
145
163
|
readonly status: 500;
|
|
146
164
|
readonly title: "Schema snapshot parse error";
|
|
147
165
|
};
|
|
166
|
+
/** Runtime-reachable (env.ts): message enumerates failing env key names — redact on the wire. */
|
|
148
167
|
readonly ENV_INVALID: {
|
|
168
|
+
readonly internal: true;
|
|
149
169
|
readonly status: 500;
|
|
150
170
|
readonly title: "Invalid environment";
|
|
151
171
|
};
|
|
172
|
+
/** Runtime-reachable (auth/middleware.ts): message carries auth-wiring guidance — redact on the wire. */
|
|
152
173
|
readonly AUTH_HEADERS_MISSING: {
|
|
174
|
+
readonly internal: true;
|
|
153
175
|
readonly status: 500;
|
|
154
176
|
readonly title: "Auth headers missing";
|
|
155
177
|
};
|
|
@@ -290,8 +312,15 @@ interface LunoraErrorLike extends Error {
|
|
|
290
312
|
docsUrl?: string;
|
|
291
313
|
hint?: ErrorHint;
|
|
292
314
|
status: number;
|
|
315
|
+
/** Wire brand that distinguishes real `LunoraError`s from foreign errors. */
|
|
316
|
+
type: "VisulimaError";
|
|
293
317
|
}
|
|
294
|
-
/**
|
|
318
|
+
/**
|
|
319
|
+
* True when `error` carries the Lunora transport shape (string `code` + numeric
|
|
320
|
+
* `status` + the `VisulimaError` brand). The `type` brand is what distinguishes
|
|
321
|
+
* a real `LunoraError` (or its wire-decoded twin) from a foreign error that
|
|
322
|
+
* happens to carry `code`/`status` — see plan 119 for the full rationale.
|
|
323
|
+
*/
|
|
295
324
|
declare const isLunoraError: (error: unknown) => error is LunoraErrorLike;
|
|
296
325
|
/** Throw an `INTERNAL` {@link LunoraError} when `condition` is falsy. */
|
|
297
326
|
declare const invariant: (condition: unknown, message: string) => asserts condition;
|
package/dist/index.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
export { LunoraError } from './packem_shared/LunoraError-
|
|
2
|
-
export { ERROR_CATALOG, MESSAGE_SOLUTIONS, findSolutionByMessage, flattenHint, isInternalCode, resolveHint } from './packem_shared/ERROR_CATALOG-
|
|
3
|
-
export { isLunoraError } from './packem_shared/isLunoraError-
|
|
4
|
-
export { invariant, unreachable } from './packem_shared/invariant-
|
|
5
|
-
export { toErrorBody } from './packem_shared/toErrorBody-
|
|
1
|
+
export { LunoraError } from './packem_shared/LunoraError-CwQSmeL3.mjs';
|
|
2
|
+
export { ERROR_CATALOG, MESSAGE_SOLUTIONS, findSolutionByMessage, flattenHint, isInternalCode, resolveHint } from './packem_shared/ERROR_CATALOG-CoCPcAHf.mjs';
|
|
3
|
+
export { isLunoraError } from './packem_shared/isLunoraError-CSQtYMrF.mjs';
|
|
4
|
+
export { invariant, unreachable } from './packem_shared/invariant-DawIQfjN.mjs';
|
|
5
|
+
export { toErrorBody } from './packem_shared/toErrorBody-CyqyVwGF.mjs';
|
|
@@ -14,13 +14,13 @@ const ERROR_CATALOG = {
|
|
|
14
14
|
},
|
|
15
15
|
NOT_UNIQUE: {
|
|
16
16
|
hint: [
|
|
17
|
-
"
|
|
17
|
+
"`.unique()` matched more than one document — it expects the query to identify at most one row.",
|
|
18
18
|
"",
|
|
19
|
-
"- If
|
|
20
|
-
|
|
19
|
+
"- If several matches are legitimate, use `.first()` (take one) or `.collect()` (take all) instead.",
|
|
20
|
+
"- Otherwise tighten the query (e.g. filter on a unique/indexed field) so it can only match one row."
|
|
21
21
|
],
|
|
22
22
|
status: 400,
|
|
23
|
-
title: "
|
|
23
|
+
title: "Query matched more than one document"
|
|
24
24
|
},
|
|
25
25
|
VALIDATION_ERROR: { status: 400, title: "Validation failed" },
|
|
26
26
|
TOO_MANY_REQUESTS: { status: 429, title: "Too many requests" },
|
|
@@ -48,14 +48,21 @@ const ERROR_CATALOG = {
|
|
|
48
48
|
status: 403,
|
|
49
49
|
title: "RLS policy required"
|
|
50
50
|
},
|
|
51
|
+
RUN_DEPTH_EXCEEDED: { internal: true, status: 500, title: "Run depth exceeded" },
|
|
52
|
+
MIGRATION_NOT_FOUND: { status: 404, title: "Data migration not found" },
|
|
53
|
+
UNKNOWN_TABLE: { status: 404, title: "Unknown table" },
|
|
54
|
+
GLOBAL_TABLE_NOT_EDITABLE: { status: 400, title: "Global table is not editable" },
|
|
51
55
|
SHARD_ERROR: { status: 503, title: "Shard error" },
|
|
52
56
|
SHARD_UNAVAILABLE: { status: 503, title: "Shard unavailable" },
|
|
53
57
|
OFFLINE_IDENTITY_CHANGED: { status: 409, title: "Offline identity changed" },
|
|
54
|
-
/** Package-specific codes. Build-time
|
|
58
|
+
/** Package-specific codes. Build-time-only — never cross the RPC wire, so deliberately not `internal`. */
|
|
55
59
|
CODEGEN_DIAGNOSTIC: { status: 500, title: "Codegen diagnostic" },
|
|
60
|
+
/** Build-time-only — never crosses the RPC wire, so deliberately not `internal`. */
|
|
56
61
|
SCHEMA_SNAPSHOT_PARSE: { status: 500, title: "Schema snapshot parse error" },
|
|
57
|
-
|
|
58
|
-
|
|
62
|
+
/** Runtime-reachable (env.ts): message enumerates failing env key names — redact on the wire. */
|
|
63
|
+
ENV_INVALID: { internal: true, status: 500, title: "Invalid environment" },
|
|
64
|
+
/** Runtime-reachable (auth/middleware.ts): message carries auth-wiring guidance — redact on the wire. */
|
|
65
|
+
AUTH_HEADERS_MISSING: { internal: true, status: 500, title: "Auth headers missing" },
|
|
59
66
|
/**
|
|
60
67
|
* Upstream Cloudflare API failures surfaced from an action. The message
|
|
61
68
|
* carries the upstream response body (Cloudflare's own error text — trusted
|
|
@@ -167,7 +174,17 @@ const MESSAGE_SOLUTIONS = [
|
|
|
167
174
|
test: (message) => message.includes("not exported by your worker entry")
|
|
168
175
|
},
|
|
169
176
|
{
|
|
170
|
-
|
|
177
|
+
// Deliberately NOT ERROR_CATALOG.NOT_UNIQUE.hint: that code (and hint)
|
|
178
|
+
// describes the read-side `.unique()` multi-match, while this matcher
|
|
179
|
+
// fires on the WRITE-path message ("unique constraint violation on
|
|
180
|
+
// <table>") thrown as a CONFLICT by an insert/patch breaching a
|
|
181
|
+
// `unique` index — a different error class needing insert remediation.
|
|
182
|
+
body: [
|
|
183
|
+
"A row with the same value already exists in a `unique` index.",
|
|
184
|
+
"",
|
|
185
|
+
"- If you meant to upsert, use `ctx.db.<table>().upsert(...)` (or `.patch(...)` an existing row) instead of `.insert(...)`.",
|
|
186
|
+
`- Otherwise pick a value that isn't already taken, and consider surfacing a friendly "already exists" message to the user.`
|
|
187
|
+
].join("\n"),
|
|
171
188
|
header: "Unique constraint violation",
|
|
172
189
|
id: "lunora-runtime-unique",
|
|
173
190
|
test: (message) => message.includes("unique constraint violation on")
|
|
@@ -3,7 +3,7 @@ const isLunoraError = (error) => {
|
|
|
3
3
|
return false;
|
|
4
4
|
}
|
|
5
5
|
const candidate = error;
|
|
6
|
-
return typeof candidate.code === "string" && typeof candidate.status === "number";
|
|
6
|
+
return candidate.type === "VisulimaError" && typeof candidate.code === "string" && typeof candidate.status === "number";
|
|
7
7
|
};
|
|
8
8
|
|
|
9
9
|
export { isLunoraError };
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { isInternalCode, resolveHint } from './ERROR_CATALOG-
|
|
2
|
-
import { isLunoraError } from './isLunoraError-
|
|
1
|
+
import { isInternalCode, resolveHint } from './ERROR_CATALOG-CoCPcAHf.mjs';
|
|
2
|
+
import { isLunoraError } from './isLunoraError-CSQtYMrF.mjs';
|
|
3
3
|
|
|
4
4
|
const toErrorBody = (error, options = {}) => {
|
|
5
5
|
const redactedMessage = options.redactedMessage ?? "Internal error";
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@lunora/errors",
|
|
3
|
-
"version": "1.0.0-alpha.
|
|
3
|
+
"version": "1.0.0-alpha.3",
|
|
4
4
|
"description": "Unified error layer for Lunora: one LunoraError base + a central catalog of codes, statuses, and actionable hints, rendered across CLI, overlay, Studio, and the client",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"cloudflare",
|