apps 0.0.1-beta.1 → 0.0.1-beta.11
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/README.md +65 -43
- package/framework-reference.json +1 -1
- package/js/browser-XIPJGLH2.js +65 -0
- package/js/{chunk-SATWJKN6.js → chunk-27F7W2LG.js} +1 -1
- package/js/{chunk-HDJH3RPR.js → chunk-57RKNWL2.js} +2 -2
- package/js/{chunk-2HHMABB6.js → chunk-5T57N25Q.js} +61 -13
- package/js/{chunk-FW5HBOIK.js → chunk-CDL5PM2Q.js} +307 -169
- package/js/{chunk-X7SFGU4Q.js → chunk-EFAPIRVB.js} +28 -9
- package/js/chunk-GPFVWWDZ.js +209 -0
- package/js/{chunk-OHRT55C4.js → chunk-IJX4CYZO.js} +3 -6
- package/js/{chunk-ZTFQHGEB.js → chunk-IPI4MFSN.js} +3 -5
- package/js/{chunk-YEJOQEII.js → chunk-JU7VHODU.js} +1 -1
- package/js/{chunk-IHQ4ML7K.js → chunk-KRSCJDTW.js} +586 -111
- package/js/chunk-KUMBKVJD.js +39 -0
- package/js/{chunk-EVJUVWN2.js → chunk-M3B3DE4K.js} +2 -2
- package/js/{chunk-ZJWDMTE3.js → chunk-MKWZPDR6.js} +3 -3
- package/js/{chunk-BMOIAIVR.js → chunk-N7YDVXYJ.js} +49 -1
- package/js/chunk-NKLWZJLE.js +172 -0
- package/js/{chunk-ZCAMUXSG.js → chunk-ODEIDRGW.js} +3 -4
- package/js/{chunk-M6ZRRIBI.js → chunk-PJJ24GU7.js} +1 -1
- package/js/{chunk-FZJOYIZO.js → chunk-PZB6T6KU.js} +1 -1
- package/js/chunk-R3EV5FTO.js +97 -0
- package/js/{chunk-KOXMLKTM.js → chunk-RELFXUOO.js} +308 -316
- package/js/{chunk-6YBRWRK3.js → chunk-RFVIONFX.js} +43 -14
- package/js/{chunk-RBAC33PQ.js → chunk-TYVDBQSI.js} +58 -83
- package/js/{chunk-QKHR7BMF.js → chunk-UK573G7W.js} +1 -1
- package/js/{chunk-NCYXZN2G.js → chunk-UVL56Z6E.js} +390 -23
- package/js/{chunk-4LPG6RCH.js → chunk-VFZKSM3T.js} +5 -25
- package/js/{chunk-6IIO4NPI.js → chunk-WVVV4TX2.js} +21 -9
- package/js/{chunk-G7IE6BKC.js → chunk-YBRC463S.js} +8 -8
- package/js/chunk-Z2QY3YTF.js +507 -0
- package/js/{chunk-PLCMJREA.js → chunk-ZQINWV4W.js} +60 -20
- package/js/client.js +10 -26
- package/js/contracts.js +70 -15
- package/js/effect.js +19 -19
- package/js/es-APDZKREY.js +40968 -0
- package/js/graphql.js +34 -39
- package/js/host.js +23 -23
- package/js/index.js +199 -195
- package/js/mcp/effect.js +21 -21
- package/js/mcp/stdio.js +25 -25
- package/js/mcp.js +60 -44
- package/js/openapi.js +826 -41682
- package/js/react.js +3 -3
- package/js/skills/effect.js +3 -4
- package/js/skills.js +53 -17
- package/js/storage/facet.js +4 -4
- package/js/ui/auth/contracts.js +8 -9
- package/js/ui/auth.js +16 -14
- package/js/ui/contracts.js +4 -4
- package/js/ui/serving.js +9 -8
- package/package.json +1 -1
- package/runtime.json +1 -1
- package/types/app-cache/src/contracts/cache.d.ts +42 -2
- package/types/app-cache/src/index.d.ts +59 -1
- package/types/app-data/src/contracts/database.d.ts +33 -6
- package/types/app-data/src/implementation/schema.d.ts +2 -17
- package/types/apps/src/contracts/app.d.ts +7 -6
- package/types/apps/src/contracts/cache.d.ts +4 -1
- package/types/apps/src/contracts/failure.d.ts +25 -0
- package/types/apps/src/contracts/host.d.ts +34 -679
- package/types/apps/src/contracts/mcp.d.ts +16 -0
- package/types/apps/src/contracts/openapi.d.ts +11 -1
- package/types/apps/src/contracts/operations.d.ts +0 -5
- package/types/apps/src/contracts/protocol-version.d.ts +6 -0
- package/types/apps/src/contracts/protocols/1.d.ts +1589 -0
- package/types/apps/src/contracts/protocols/2.d.ts +668 -0
- package/types/apps/src/contracts/protocols/3.d.ts +676 -0
- package/types/apps/src/contracts/protocols/4.d.ts +1229 -0
- package/types/apps/src/contracts/protocols/5.d.ts +1090 -0
- package/types/apps/src/contracts/provider.d.ts +56 -5
- package/types/apps/src/contracts/router.d.ts +59 -0
- package/types/apps/src/contracts/skills.d.ts +17 -8
- package/types/apps/src/contracts/storage.d.ts +3 -3
- package/types/apps/src/contracts/ui-auth.d.ts +6 -14
- package/types/apps/src/contracts/workflows.d.ts +34 -3
- package/types/apps/src/graphql.d.ts +1 -3
- package/types/apps/src/implementation/account-router.d.ts +12 -0
- package/types/apps/src/implementation/app.d.ts +5 -4
- package/types/apps/src/implementation/cache.d.ts +3 -1
- package/types/apps/src/implementation/catalog-cache.d.ts +9 -2
- package/types/apps/src/implementation/elicitation.d.ts +1 -1
- package/types/apps/src/implementation/failure-detail.d.ts +25 -0
- package/types/apps/src/implementation/graphql-catalog.d.ts +1 -4
- package/types/apps/src/implementation/mcp-catalog.d.ts +1 -4
- package/types/apps/src/implementation/mcp-client.d.ts +35 -19
- package/types/apps/src/implementation/mcp.d.ts +35 -19
- package/types/apps/src/implementation/openapi-compile.d.ts +3 -2
- package/types/apps/src/implementation/openapi-document.d.ts +0 -2
- package/types/apps/src/implementation/openapi-names.d.ts +18 -0
- package/types/apps/src/implementation/openapi-request.d.ts +0 -1
- package/types/apps/src/implementation/openapi-source.d.ts +7 -7
- package/types/apps/src/implementation/operations.d.ts +26 -3
- package/types/apps/src/implementation/protocol-operations.d.ts +3 -4
- package/types/apps/src/implementation/provider.d.ts +9 -4
- package/types/apps/src/implementation/router-catalog.d.ts +225 -0
- package/types/apps/src/implementation/router.d.ts +59 -0
- package/types/apps/src/implementation/schema.d.ts +5 -6
- package/types/apps/src/implementation/storage.d.ts +5 -3
- package/types/apps/src/implementation/swagger-client.d.ts +28 -0
- package/types/apps/src/implementation/ui-auth.d.ts +11 -5
- package/types/apps/src/implementation/ui-serving.d.ts +4 -2
- package/types/apps/src/implementation/webhooks.d.ts +1 -1
- package/types/apps/src/implementation/workflow-context.d.ts +11 -3
- package/types/apps/src/index.d.ts +21 -6
- package/types/apps/src/mcp-stdio.d.ts +2 -5
- package/types/apps/src/mcp.d.ts +5 -4
- package/types/apps/src/openapi.d.ts +6 -6
- package/types/apps/src/skills.d.ts +6 -3
- package/types/apps/src/ui-auth.d.ts +2 -2
- package/types/telemetry/src/browser-operations.d.ts +5 -2
- package/js/chunk-PZ36XMXW.js +0 -93
- package/js/chunk-SWPD52J7.js +0 -35
- package/js/chunk-TE4KO4HI.js +0 -47
- package/js/chunk-W7D7WVSY.js +0 -18
- package/types/apps/src/contracts/dynamic-tools.d.ts +0 -13
- package/types/apps/src/implementation/account-operations.d.ts +0 -151
- package/types/apps/src/implementation/dynamic-tools.d.ts +0 -8
|
@@ -0,0 +1,507 @@
|
|
|
1
|
+
import {
|
|
2
|
+
skillFromFiles
|
|
3
|
+
} from "./chunk-IPI4MFSN.js";
|
|
4
|
+
import {
|
|
5
|
+
joinPath,
|
|
6
|
+
mergeMeta
|
|
7
|
+
} from "./chunk-GPFVWWDZ.js";
|
|
8
|
+
import {
|
|
9
|
+
parseProviderError
|
|
10
|
+
} from "./chunk-MKWZPDR6.js";
|
|
11
|
+
import {
|
|
12
|
+
ApiErrorResponse,
|
|
13
|
+
HostDeclarationInvalid,
|
|
14
|
+
HostEvaluationFailed,
|
|
15
|
+
HostedRouter,
|
|
16
|
+
HostedTool,
|
|
17
|
+
HostedToolSummary,
|
|
18
|
+
McpError,
|
|
19
|
+
maxFailureMessageLength
|
|
20
|
+
} from "./chunk-KRSCJDTW.js";
|
|
21
|
+
import {
|
|
22
|
+
AppDatabaseError
|
|
23
|
+
} from "./chunk-N7YDVXYJ.js";
|
|
24
|
+
import {
|
|
25
|
+
SkillLoadFailed,
|
|
26
|
+
skillFormatLimits
|
|
27
|
+
} from "./chunk-JU7VHODU.js";
|
|
28
|
+
import {
|
|
29
|
+
jsonSchemaDocument
|
|
30
|
+
} from "./chunk-5T57N25Q.js";
|
|
31
|
+
import {
|
|
32
|
+
AppStorageError,
|
|
33
|
+
AppStorageUnavailable
|
|
34
|
+
} from "./chunk-PZB6T6KU.js";
|
|
35
|
+
import {
|
|
36
|
+
AccountId,
|
|
37
|
+
HttpUrl,
|
|
38
|
+
JsonObject
|
|
39
|
+
} from "./chunk-27F7W2LG.js";
|
|
40
|
+
import {
|
|
41
|
+
Cause_exports,
|
|
42
|
+
Effect_exports,
|
|
43
|
+
Option_exports,
|
|
44
|
+
Predicate_exports,
|
|
45
|
+
Redacted_exports,
|
|
46
|
+
Result_exports,
|
|
47
|
+
Schema_exports
|
|
48
|
+
} from "./chunk-CDL5PM2Q.js";
|
|
49
|
+
|
|
50
|
+
// src/contracts/openapi.ts
|
|
51
|
+
var OpenapiErrorResponse = Schema_exports.Struct({
|
|
52
|
+
code: ApiErrorResponse.fields.code,
|
|
53
|
+
status: ApiErrorResponse.fields.status,
|
|
54
|
+
message: Schema_exports.Union([
|
|
55
|
+
Schema_exports.Struct({ source: Schema_exports.Literal("body") }),
|
|
56
|
+
Schema_exports.Struct({ source: Schema_exports.Literal("schema"), value: ApiErrorResponse.fields.message })
|
|
57
|
+
]),
|
|
58
|
+
schema: JsonObject
|
|
59
|
+
});
|
|
60
|
+
var OpenapiParameter = Schema_exports.Struct({
|
|
61
|
+
name: Schema_exports.String,
|
|
62
|
+
in: Schema_exports.Literals(["path", "query", "header", "cookie"]),
|
|
63
|
+
required: Schema_exports.optionalKey(Schema_exports.Boolean),
|
|
64
|
+
schema: Schema_exports.optionalKey(JsonObject),
|
|
65
|
+
style: Schema_exports.optionalKey(Schema_exports.String),
|
|
66
|
+
explode: Schema_exports.optionalKey(Schema_exports.Boolean),
|
|
67
|
+
allowReserved: Schema_exports.optionalKey(Schema_exports.Boolean),
|
|
68
|
+
allowEmptyValue: Schema_exports.optionalKey(Schema_exports.Boolean),
|
|
69
|
+
content: Schema_exports.optionalKey(JsonObject)
|
|
70
|
+
});
|
|
71
|
+
var OpenapiRequestBody = Schema_exports.Struct({
|
|
72
|
+
required: Schema_exports.optionalKey(Schema_exports.Boolean),
|
|
73
|
+
content: Schema_exports.Record(
|
|
74
|
+
Schema_exports.String,
|
|
75
|
+
Schema_exports.Struct({
|
|
76
|
+
schema: Schema_exports.optionalKey(JsonObject),
|
|
77
|
+
encoding: Schema_exports.optionalKey(JsonObject)
|
|
78
|
+
})
|
|
79
|
+
)
|
|
80
|
+
});
|
|
81
|
+
var OpenapiOperation = Schema_exports.Struct({
|
|
82
|
+
/** The tool name after `queries.` or `mutations.`, grouped as `<group>.<leaf>`. */
|
|
83
|
+
name: Schema_exports.NonEmptyString,
|
|
84
|
+
/** The document's operationId, when it declares one. `kinds` overrides are keyed by it. */
|
|
85
|
+
operationId: Schema_exports.optionalKey(Schema_exports.String),
|
|
86
|
+
description: Schema_exports.String,
|
|
87
|
+
method: Schema_exports.Literals(["GET", "POST", "PUT", "PATCH", "DELETE", "HEAD", "OPTIONS"]),
|
|
88
|
+
path: Schema_exports.String,
|
|
89
|
+
baseUrl: HttpUrl,
|
|
90
|
+
openapi: Schema_exports.String,
|
|
91
|
+
securitySchemes: Schema_exports.Record(Schema_exports.String, JsonObject),
|
|
92
|
+
/** The resolved OpenAPI Operation Object; Executor schemas remain separate. */
|
|
93
|
+
request: Schema_exports.Struct({
|
|
94
|
+
parameters: Schema_exports.Array(OpenapiParameter),
|
|
95
|
+
requestBody: Schema_exports.optionalKey(OpenapiRequestBody),
|
|
96
|
+
security: Schema_exports.Array(Schema_exports.Record(Schema_exports.String, Schema_exports.Array(Schema_exports.String))),
|
|
97
|
+
responses: Schema_exports.Record(Schema_exports.String, JsonObject)
|
|
98
|
+
}),
|
|
99
|
+
/** Streams remain in the metadata but cannot run through a single-result tool call. */
|
|
100
|
+
streaming: Schema_exports.optionalKey(Schema_exports.Literal(true)),
|
|
101
|
+
/** The operation's OpenAPI tags, shown to agents as labels within its router. */
|
|
102
|
+
tags: Schema_exports.optionalKey(Schema_exports.Array(Schema_exports.NonEmptyString)),
|
|
103
|
+
input: JsonObject,
|
|
104
|
+
outputSchema: Schema_exports.optionalKey(JsonObject),
|
|
105
|
+
errorResponses: Schema_exports.optionalKey(Schema_exports.Array(OpenapiErrorResponse))
|
|
106
|
+
});
|
|
107
|
+
var CredentialBinding = Schema_exports.Struct({
|
|
108
|
+
scheme: Schema_exports.String,
|
|
109
|
+
field: Schema_exports.String,
|
|
110
|
+
part: Schema_exports.Literals(["value", "username", "password"]),
|
|
111
|
+
prefix: Schema_exports.String
|
|
112
|
+
});
|
|
113
|
+
var OpenapiAccount = Schema_exports.Struct({
|
|
114
|
+
id: Schema_exports.optional(AccountId),
|
|
115
|
+
method: Schema_exports.String,
|
|
116
|
+
fields: Schema_exports.Record(Schema_exports.String, Schema_exports.Unknown)
|
|
117
|
+
});
|
|
118
|
+
var OpenapiParameterDefaults = Schema_exports.Struct({
|
|
119
|
+
path: Schema_exports.optionalKey(Schema_exports.Record(Schema_exports.String, Schema_exports.String)),
|
|
120
|
+
query: Schema_exports.optionalKey(Schema_exports.Record(Schema_exports.String, Schema_exports.String)),
|
|
121
|
+
headers: Schema_exports.optionalKey(Schema_exports.Record(Schema_exports.String, Schema_exports.String))
|
|
122
|
+
});
|
|
123
|
+
var OpenapiToolsOptions = Schema_exports.Struct({
|
|
124
|
+
operations: Schema_exports.Array(OpenapiOperation),
|
|
125
|
+
/**
|
|
126
|
+
* Component schemas stored once per app and referenced as `#/$defs/<name>`. Operations
|
|
127
|
+
* generated before shared definitions carry their own `$defs` and omit this.
|
|
128
|
+
*/
|
|
129
|
+
definitions: Schema_exports.optional(Schema_exports.Record(Schema_exports.String, JsonObject)),
|
|
130
|
+
methods: Schema_exports.Record(Schema_exports.String, Schema_exports.Array(CredentialBinding)),
|
|
131
|
+
oauth: Schema_exports.Array(Schema_exports.String),
|
|
132
|
+
account: Schema_exports.optional(OpenapiAccount),
|
|
133
|
+
parameterDefaults: Schema_exports.optional(OpenapiParameterDefaults),
|
|
134
|
+
signal: Schema_exports.optional(Schema_exports.instanceOf(AbortSignal)),
|
|
135
|
+
fetch: Schema_exports.optional(
|
|
136
|
+
Schema_exports.declare((value) => typeof value === "function")
|
|
137
|
+
)
|
|
138
|
+
});
|
|
139
|
+
var OpenapiError = class extends Schema_exports.TaggedError()("OpenapiError", {
|
|
140
|
+
reason: Schema_exports.Literals(["invalid_definition", "invalid_input", "request"]),
|
|
141
|
+
status: Schema_exports.optional(Schema_exports.Number)
|
|
142
|
+
}) {
|
|
143
|
+
};
|
|
144
|
+
var defaultOpenapiResponseLimits = {
|
|
145
|
+
maxBodyBytes: 16777216,
|
|
146
|
+
readTimeoutMs: 3e4
|
|
147
|
+
};
|
|
148
|
+
var isOpenapiTextMedia = (type) => /^(?:text\/|application\/(?:[\w.-]+\+)?(?:json|xml)|application\/(?:javascript|x-ndjson|x-www-form-urlencoded))/i.test(
|
|
149
|
+
type
|
|
150
|
+
);
|
|
151
|
+
var isOpenapiFileSchema = (shape) => shape.contentMediaType !== void 0 && shape.contentEncoding === void 0 || shape.type === "string" && shape.format === "binary";
|
|
152
|
+
var openapiBinaryResultSchema = {
|
|
153
|
+
type: "object",
|
|
154
|
+
properties: {
|
|
155
|
+
base64: { type: "string", contentEncoding: "base64" },
|
|
156
|
+
contentType: { type: "string" }
|
|
157
|
+
},
|
|
158
|
+
required: ["base64", "contentType"],
|
|
159
|
+
additionalProperties: false
|
|
160
|
+
};
|
|
161
|
+
var openapiMediaKind = (type) => type.includes("json") && !type.includes("ndjson") ? "json" : type === "application/x-www-form-urlencoded" ? "form" : type === "multipart/form-data" ? "multipart" : isOpenapiTextMedia(type) ? "text" : "binary";
|
|
162
|
+
|
|
163
|
+
// src/implementation/failure-detail.ts
|
|
164
|
+
var storageMessages = {
|
|
165
|
+
schema: "The app's database schema is invalid.",
|
|
166
|
+
schema_changed: "The app's database schema changed during this operation. Retry it.",
|
|
167
|
+
table: "The operation used a table the app's database schema does not declare.",
|
|
168
|
+
index: "The operation used an index the table does not declare, or used it incorrectly.",
|
|
169
|
+
range: "The index range is invalid for the declared index.",
|
|
170
|
+
value: "A value does not match the table's declared field schema.",
|
|
171
|
+
readonly: "Queries cannot write. Move writes into a mutation.",
|
|
172
|
+
cursor: "The pagination cursor is invalid or belongs to a different query.",
|
|
173
|
+
limit: "The operation exceeded a per-invocation app data limit.",
|
|
174
|
+
closed: "The database session closed before this operation finished.",
|
|
175
|
+
storage: "App storage failed to complete the operation.",
|
|
176
|
+
replay: "A workflow step replayed with different input than its first run."
|
|
177
|
+
};
|
|
178
|
+
var minimumSecretLength = 6;
|
|
179
|
+
var secretValues = (value, found) => {
|
|
180
|
+
if (typeof value === "string") {
|
|
181
|
+
if (value.length >= minimumSecretLength) found.add(value);
|
|
182
|
+
} else if (Array.isArray(value)) for (const item of value) secretValues(item, found);
|
|
183
|
+
else if (Predicate_exports.isObject(value))
|
|
184
|
+
for (const item of Object.values(value)) secretValues(item, found);
|
|
185
|
+
return found;
|
|
186
|
+
};
|
|
187
|
+
var accountFieldSecrets = (accounts) => {
|
|
188
|
+
const found = /* @__PURE__ */ new Set();
|
|
189
|
+
if (Predicate_exports.isObject(accounts)) {
|
|
190
|
+
for (const slot of Object.values(accounts))
|
|
191
|
+
for (const account of Array.isArray(slot) ? slot : [slot])
|
|
192
|
+
if (Predicate_exports.hasProperty(account, "fields")) secretValues(account.fields, found);
|
|
193
|
+
}
|
|
194
|
+
return [...found].sort((a, b) => b.length - a.length);
|
|
195
|
+
};
|
|
196
|
+
var accountSecrets = (accounts) => accountFieldSecrets(Redacted_exports.value(accounts));
|
|
197
|
+
var boundFailureMessage = (message, secrets) => {
|
|
198
|
+
let redacted = message;
|
|
199
|
+
for (const secret of secrets) redacted = redacted.split(secret).join("[redacted]");
|
|
200
|
+
return redacted.length <= maxFailureMessageLength ? redacted : `${redacted.slice(0, maxFailureMessageLength - 1)}\u2026`;
|
|
201
|
+
};
|
|
202
|
+
var errorName = (error) => (error.name.length > 0 ? error.name : "Error").slice(0, 128);
|
|
203
|
+
var ownMessage = (error) => {
|
|
204
|
+
const cause = error.cause;
|
|
205
|
+
const suffix = cause instanceof Error && cause.message.length > 0 ? ` (caused by ${errorName(cause)}: ${cause.message})` : "";
|
|
206
|
+
return error.message.length > 0 ? `${error.message}${suffix}` : void 0;
|
|
207
|
+
};
|
|
208
|
+
var describeFailure = (error) => error instanceof Error ? `${errorName(error)}: ${ownMessage(error) ?? "(no message)"}` : typeof error === "string" ? error : `A non-Error ${error === null ? "null" : typeof error} value was thrown`;
|
|
209
|
+
var failureDetail = (error, secrets) => {
|
|
210
|
+
if (Schema_exports.is(AppDatabaseError)(error))
|
|
211
|
+
return {
|
|
212
|
+
source: "storage",
|
|
213
|
+
errorName: "AppDatabaseError",
|
|
214
|
+
code: error.reason,
|
|
215
|
+
message: boundFailureMessage(ownMessage(error) ?? storageMessages[error.reason], secrets)
|
|
216
|
+
};
|
|
217
|
+
if (Schema_exports.is(AppStorageUnavailable)(error))
|
|
218
|
+
return {
|
|
219
|
+
source: "storage",
|
|
220
|
+
errorName: "AppStorageUnavailable",
|
|
221
|
+
message: "App storage is not available on this host."
|
|
222
|
+
};
|
|
223
|
+
if (Schema_exports.is(AppStorageError)(error))
|
|
224
|
+
return {
|
|
225
|
+
source: "storage",
|
|
226
|
+
errorName: "AppStorageError",
|
|
227
|
+
message: "App storage failed to complete the operation."
|
|
228
|
+
};
|
|
229
|
+
if (Schema_exports.is(OpenapiError)(error))
|
|
230
|
+
return {
|
|
231
|
+
source: "service",
|
|
232
|
+
errorName: "OpenapiError",
|
|
233
|
+
code: error.reason,
|
|
234
|
+
message: error.reason === "request" ? error.status === void 0 ? "The API request failed before a response arrived." : `The API responded with HTTP ${error.status}, which its OpenAPI document does not declare as an error with a message.` : error.reason === "invalid_input" ? "The input could not be encoded as a request for this API operation." : "The API's OpenAPI definition for this operation is invalid."
|
|
235
|
+
};
|
|
236
|
+
if (error instanceof Error)
|
|
237
|
+
return {
|
|
238
|
+
source: "app",
|
|
239
|
+
errorName: errorName(error),
|
|
240
|
+
message: boundFailureMessage(
|
|
241
|
+
ownMessage(error) ?? `${errorName(error)} was thrown without a message.`,
|
|
242
|
+
secrets
|
|
243
|
+
)
|
|
244
|
+
};
|
|
245
|
+
if (typeof error === "string")
|
|
246
|
+
return { source: "app", errorName: "string", message: boundFailureMessage(error, secrets) };
|
|
247
|
+
return {
|
|
248
|
+
source: "app",
|
|
249
|
+
errorName: typeof error,
|
|
250
|
+
message: `A non-Error ${error === null ? "null" : typeof error} value was thrown.`
|
|
251
|
+
};
|
|
252
|
+
};
|
|
253
|
+
|
|
254
|
+
// src/implementation/router-catalog.ts
|
|
255
|
+
var safeFailure = (error, secrets) => {
|
|
256
|
+
const provider = parseProviderError(error);
|
|
257
|
+
if (Option_exports.isSome(provider)) return provider.value;
|
|
258
|
+
const skills = Schema_exports.decodeUnknownOption(SkillLoadFailed)(error);
|
|
259
|
+
if (Option_exports.isSome(skills)) {
|
|
260
|
+
const { reason, message, status } = skills.value;
|
|
261
|
+
return new SkillLoadFailed({
|
|
262
|
+
reason,
|
|
263
|
+
...message ? { message } : {},
|
|
264
|
+
...status === void 0 ? {} : { status }
|
|
265
|
+
});
|
|
266
|
+
}
|
|
267
|
+
const mcp = Schema_exports.decodeUnknownOption(McpError)(error);
|
|
268
|
+
if (Option_exports.isSome(mcp)) {
|
|
269
|
+
const { phase, reason, status } = mcp.value;
|
|
270
|
+
return new McpError({ phase, reason, ...status === void 0 ? {} : { status } });
|
|
271
|
+
}
|
|
272
|
+
if (Schema_exports.is(HostDeclarationInvalid)(error)) return error;
|
|
273
|
+
return new HostEvaluationFailed(failureDetail(error, secrets));
|
|
274
|
+
};
|
|
275
|
+
var sourced = (work, secrets) => Effect_exports.suspend(work).pipe(
|
|
276
|
+
Effect_exports.catchCause(
|
|
277
|
+
(cause) => Cause_exports.hasInterrupts(cause) ? Effect_exports.interrupt : Effect_exports.fail(safeFailure(Cause_exports.squash(cause), secrets))
|
|
278
|
+
)
|
|
279
|
+
);
|
|
280
|
+
var routerMeta = (node, secrets) => node.kind === "router" ? Effect_exports.succeed(node.meta) : node.meta === void 0 ? Effect_exports.succeed(node.overrides) : sourced(node.meta, secrets).pipe(Effect_exports.map((meta) => mergeMeta(meta, node.overrides)));
|
|
281
|
+
var routerSkillPrefix = "tools";
|
|
282
|
+
var plainSegment = /^[a-z][a-z0-9]*$/;
|
|
283
|
+
var pathHash = (path) => {
|
|
284
|
+
let hash = 2166136261;
|
|
285
|
+
for (let index = 0; index < path.length; index++)
|
|
286
|
+
hash = Math.imul(hash ^ path.charCodeAt(index), 16777619) >>> 0;
|
|
287
|
+
return hash.toString().padStart(10, "0");
|
|
288
|
+
};
|
|
289
|
+
var routerSkillName = (path) => {
|
|
290
|
+
if (path === "") return routerSkillPrefix;
|
|
291
|
+
const segments = path.split(".");
|
|
292
|
+
const plain = [routerSkillPrefix, ...segments].join("-");
|
|
293
|
+
if (segments.every((segment) => plainSegment.test(segment)) && plain.length <= skillFormatLimits.nameCharacters)
|
|
294
|
+
return plain;
|
|
295
|
+
const hash = pathHash(path);
|
|
296
|
+
const slug = path.toLowerCase().replace(/[^a-z0-9]+/g, "-").slice(0, skillFormatLimits.nameCharacters - routerSkillPrefix.length - hash.length - 2).replace(/^-+|-+$/g, "");
|
|
297
|
+
return [routerSkillPrefix, slug, hash].filter((part) => part !== "").join("-");
|
|
298
|
+
};
|
|
299
|
+
var entry = (path, meta, error) => Schema_exports.decodeUnknownEffect(HostedRouter)({
|
|
300
|
+
path,
|
|
301
|
+
...meta?.title === void 0 ? {} : { title: meta.title },
|
|
302
|
+
...meta?.description === void 0 ? {} : { description: meta.description },
|
|
303
|
+
...meta?.icons === void 0 ? {} : { icons: meta.icons },
|
|
304
|
+
...meta?.tags === void 0 ? {} : { tags: meta.tags },
|
|
305
|
+
...meta?.instructions === void 0 ? {} : { skill: routerSkillName(path) },
|
|
306
|
+
...error === void 0 ? {} : { error }
|
|
307
|
+
}).pipe(Effect_exports.mapError(() => new HostDeclarationInvalid()));
|
|
308
|
+
var invalid = (work) => work.pipe(
|
|
309
|
+
Effect_exports.catchCause(
|
|
310
|
+
(cause) => Cause_exports.hasInterrupts(cause) ? Effect_exports.interrupt : Effect_exports.fail(new HostDeclarationInvalid())
|
|
311
|
+
)
|
|
312
|
+
);
|
|
313
|
+
var summaryFields = (name, router, operation, schedules) => {
|
|
314
|
+
const readOnly = operation.kind === "query";
|
|
315
|
+
return {
|
|
316
|
+
name,
|
|
317
|
+
...router === "" ? {} : { router },
|
|
318
|
+
...schedules === void 0 ? {} : { schedules },
|
|
319
|
+
description: operation.description ?? `${readOnly ? "Query" : "Mutate"} ${name}`,
|
|
320
|
+
...operation.title === void 0 ? {} : { title: operation.title },
|
|
321
|
+
readOnly,
|
|
322
|
+
annotations: { ...operation.annotations, readOnlyHint: readOnly }
|
|
323
|
+
};
|
|
324
|
+
};
|
|
325
|
+
var operationSummary = (name, router, operation, schedules) => invalid(
|
|
326
|
+
Schema_exports.decodeUnknownEffect(HostedToolSummary)(
|
|
327
|
+
summaryFields(name, router, operation, schedules)
|
|
328
|
+
)
|
|
329
|
+
);
|
|
330
|
+
var operationDescription = (name, router, operation, schedules) => invalid(
|
|
331
|
+
Effect_exports.gen(function* () {
|
|
332
|
+
return yield* Schema_exports.decodeUnknownEffect(HostedTool)({
|
|
333
|
+
...summaryFields(name, router, operation, schedules),
|
|
334
|
+
inputSchema: yield* jsonSchemaDocument(operation.input),
|
|
335
|
+
...operation.output === void 0 ? operation.outputSchema === void 0 ? {} : { outputSchema: operation.outputSchema } : { outputSchema: yield* jsonSchemaDocument(operation.output) },
|
|
336
|
+
...operation._meta === void 0 ? {} : { _meta: operation._meta }
|
|
337
|
+
});
|
|
338
|
+
})
|
|
339
|
+
);
|
|
340
|
+
var fixedRouter = (operations, meta) => ({
|
|
341
|
+
kind: "dynamic",
|
|
342
|
+
...meta === void 0 ? {} : { meta: () => Effect_exports.succeed(meta) },
|
|
343
|
+
list: () => Effect_exports.forEach(
|
|
344
|
+
Object.entries(operations),
|
|
345
|
+
([name, operation]) => operationDescription(name, "", operation)
|
|
346
|
+
),
|
|
347
|
+
summaries: () => Effect_exports.forEach(
|
|
348
|
+
Object.entries(operations),
|
|
349
|
+
([name, operation]) => operationSummary(name, "", operation)
|
|
350
|
+
),
|
|
351
|
+
describe: (name) => {
|
|
352
|
+
const operation = Object.hasOwn(operations, name) ? operations[name] : void 0;
|
|
353
|
+
return operation === void 0 ? Effect_exports.succeed(void 0) : operationDescription(name, "", operation);
|
|
354
|
+
},
|
|
355
|
+
resolve: (name) => Effect_exports.succeed(Object.hasOwn(operations, name) ? operations[name] : void 0)
|
|
356
|
+
});
|
|
357
|
+
var within = (wanted, path) => [...wanted].flatMap(
|
|
358
|
+
(name) => path === "" ? [name] : name.startsWith(`${path}.`) ? [name.slice(path.length + 1)] : []
|
|
359
|
+
);
|
|
360
|
+
var readCatalog = (root, options) => Effect_exports.gen(function* () {
|
|
361
|
+
const tools = [];
|
|
362
|
+
const routers = [];
|
|
363
|
+
const { wanted, secrets } = options;
|
|
364
|
+
const readSource = (source, path, relative) => Effect_exports.gen(function* () {
|
|
365
|
+
const describe = source.describe;
|
|
366
|
+
const [meta, listed] = yield* Effect_exports.all(
|
|
367
|
+
[
|
|
368
|
+
routerMeta(source, secrets),
|
|
369
|
+
options.summary && source.summaries !== void 0 ? sourced(source.summaries, secrets) : relative !== void 0 && describe !== void 0 ? sourced(
|
|
370
|
+
() => Effect_exports.forEach(relative, (name) => describe(name), {
|
|
371
|
+
concurrency: "unbounded"
|
|
372
|
+
}),
|
|
373
|
+
secrets
|
|
374
|
+
).pipe(Effect_exports.map((tools2) => tools2.filter((tool) => tool !== void 0))) : sourced(source.list, secrets)
|
|
375
|
+
],
|
|
376
|
+
{ concurrency: "unbounded" }
|
|
377
|
+
);
|
|
378
|
+
const parsed = yield* Schema_exports.decodeUnknownEffect(
|
|
379
|
+
Schema_exports.Array(options.summary ? HostedToolSummary : HostedTool)
|
|
380
|
+
)(listed).pipe(Effect_exports.mapError(() => new HostDeclarationInvalid()));
|
|
381
|
+
const names = /* @__PURE__ */ new Set();
|
|
382
|
+
const found = [];
|
|
383
|
+
for (const tool of parsed) {
|
|
384
|
+
if (names.has(tool.name)) return yield* new HostDeclarationInvalid();
|
|
385
|
+
names.add(tool.name);
|
|
386
|
+
if (relative !== void 0 && !relative.includes(tool.name)) continue;
|
|
387
|
+
const readOnly = tool.readOnly === true;
|
|
388
|
+
found.push({
|
|
389
|
+
...tool,
|
|
390
|
+
name: joinPath(path, tool.name),
|
|
391
|
+
...path === "" ? {} : { router: path },
|
|
392
|
+
readOnly,
|
|
393
|
+
annotations: { ...tool.annotations, readOnlyHint: readOnly }
|
|
394
|
+
});
|
|
395
|
+
}
|
|
396
|
+
return { meta, found };
|
|
397
|
+
});
|
|
398
|
+
const include = (source, path, relative) => Effect_exports.gen(function* () {
|
|
399
|
+
if (path === "") {
|
|
400
|
+
const { meta, found } = yield* readSource(source, path, relative);
|
|
401
|
+
tools.push(...found);
|
|
402
|
+
return { meta, error: void 0 };
|
|
403
|
+
}
|
|
404
|
+
const result = yield* Effect_exports.result(readSource(source, path, relative));
|
|
405
|
+
if (Result_exports.isFailure(result)) return { meta: source.overrides, error: result.failure };
|
|
406
|
+
tools.push(...result.success.found);
|
|
407
|
+
return { meta: result.success.meta, error: void 0 };
|
|
408
|
+
});
|
|
409
|
+
const visit = (node, path) => Effect_exports.gen(function* () {
|
|
410
|
+
if (path !== "" || wanted === void 0 && node.meta !== void 0)
|
|
411
|
+
routers.push(yield* entry(path, node.meta));
|
|
412
|
+
for (const [key, child] of Object.entries(node.children)) {
|
|
413
|
+
const name = joinPath(path, key);
|
|
414
|
+
switch (child.kind) {
|
|
415
|
+
case "query":
|
|
416
|
+
case "mutation":
|
|
417
|
+
if (options.scheduled === true && options.schedules(name).length === 0) break;
|
|
418
|
+
if (wanted === void 0 || wanted.has(name))
|
|
419
|
+
tools.push(
|
|
420
|
+
options.summary ? yield* operationSummary(name, path, child, options.schedules(name)) : yield* operationDescription(name, path, child, options.schedules(name))
|
|
421
|
+
);
|
|
422
|
+
break;
|
|
423
|
+
case "router":
|
|
424
|
+
if (wanted === void 0 || within(wanted, name).length > 0)
|
|
425
|
+
yield* visit(child, name);
|
|
426
|
+
break;
|
|
427
|
+
case "dynamic": {
|
|
428
|
+
if (options.scheduled === true) break;
|
|
429
|
+
const relative = wanted === void 0 ? void 0 : within(wanted, name);
|
|
430
|
+
if (relative !== void 0 && relative.length === 0) break;
|
|
431
|
+
const read = yield* include(child, name, relative);
|
|
432
|
+
routers.push(yield* entry(name, read.meta, read.error));
|
|
433
|
+
}
|
|
434
|
+
}
|
|
435
|
+
}
|
|
436
|
+
});
|
|
437
|
+
if (root?.kind === "router") yield* visit(root, "");
|
|
438
|
+
else if (root?.kind === "dynamic" && options.scheduled !== true) {
|
|
439
|
+
const read = yield* include(root, "", wanted === void 0 ? void 0 : [...wanted]);
|
|
440
|
+
if (wanted === void 0 && read.meta !== void 0)
|
|
441
|
+
routers.push(yield* entry("", read.meta));
|
|
442
|
+
}
|
|
443
|
+
return { tools, routers };
|
|
444
|
+
});
|
|
445
|
+
var routerSkills = (root) => Effect_exports.gen(function* () {
|
|
446
|
+
const nodes = [];
|
|
447
|
+
const collect = (node, path) => {
|
|
448
|
+
nodes.push({ path, node });
|
|
449
|
+
if (node.kind === "router") {
|
|
450
|
+
for (const [key, child] of Object.entries(node.children))
|
|
451
|
+
if (child.kind === "router" || child.kind === "dynamic")
|
|
452
|
+
collect(child, joinPath(path, key));
|
|
453
|
+
}
|
|
454
|
+
};
|
|
455
|
+
if (root !== void 0) collect(root, "");
|
|
456
|
+
const skills = yield* Effect_exports.forEach(
|
|
457
|
+
nodes,
|
|
458
|
+
({ path, node }) => (
|
|
459
|
+
// Skills that fail are skipped, so their failures are never reported.
|
|
460
|
+
routerMeta(node, []).pipe(
|
|
461
|
+
Effect_exports.flatMap((meta) => routerSkill(path, meta)),
|
|
462
|
+
Effect_exports.orElseSucceed(() => void 0)
|
|
463
|
+
)
|
|
464
|
+
),
|
|
465
|
+
{ concurrency: "unbounded" }
|
|
466
|
+
);
|
|
467
|
+
const names = /* @__PURE__ */ new Set();
|
|
468
|
+
return skills.filter((skill) => {
|
|
469
|
+
if (skill === void 0 || names.has(skill.name)) return false;
|
|
470
|
+
names.add(skill.name);
|
|
471
|
+
return true;
|
|
472
|
+
});
|
|
473
|
+
});
|
|
474
|
+
var routerSkill = (path, meta) => Effect_exports.gen(function* () {
|
|
475
|
+
if (meta?.instructions === void 0) return void 0;
|
|
476
|
+
const name = routerSkillName(path);
|
|
477
|
+
const description = ([meta.description, meta.title].find((text) => text !== void 0 && text.trim() !== "") ?? (path === "" ? "How to use this app's tools" : `How to use the ${path} tools`)).slice(0, skillFormatLimits.descriptionCharacters);
|
|
478
|
+
const content = `---
|
|
479
|
+
name: ${name}
|
|
480
|
+
description: ${JSON.stringify(description)}
|
|
481
|
+
---
|
|
482
|
+
|
|
483
|
+
${meta.instructions}
|
|
484
|
+
`;
|
|
485
|
+
return yield* skillFromFiles([{ path: "SKILL.md", content }], { name });
|
|
486
|
+
});
|
|
487
|
+
|
|
488
|
+
export {
|
|
489
|
+
OpenapiErrorResponse,
|
|
490
|
+
OpenapiParameter,
|
|
491
|
+
OpenapiRequestBody,
|
|
492
|
+
OpenapiOperation,
|
|
493
|
+
OpenapiToolsOptions,
|
|
494
|
+
OpenapiError,
|
|
495
|
+
defaultOpenapiResponseLimits,
|
|
496
|
+
isOpenapiTextMedia,
|
|
497
|
+
isOpenapiFileSchema,
|
|
498
|
+
openapiBinaryResultSchema,
|
|
499
|
+
openapiMediaKind,
|
|
500
|
+
accountSecrets,
|
|
501
|
+
boundFailureMessage,
|
|
502
|
+
describeFailure,
|
|
503
|
+
failureDetail,
|
|
504
|
+
fixedRouter,
|
|
505
|
+
readCatalog,
|
|
506
|
+
routerSkills
|
|
507
|
+
};
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
import {
|
|
2
2
|
AppDatabaseError,
|
|
3
|
+
DatabaseFieldReserved,
|
|
4
|
+
DatabaseLimitExceeded,
|
|
3
5
|
DatabaseLimits,
|
|
4
6
|
DatabaseOperation,
|
|
5
7
|
DatabaseSchema,
|
|
@@ -8,18 +10,21 @@ import {
|
|
|
8
10
|
Row,
|
|
9
11
|
RowMetadata,
|
|
10
12
|
defaultDatabaseLimits,
|
|
11
|
-
defaultDatabaseRuntimeLimits
|
|
12
|
-
|
|
13
|
+
defaultDatabaseRuntimeLimits,
|
|
14
|
+
reservedFieldNames
|
|
15
|
+
} from "./chunk-N7YDVXYJ.js";
|
|
13
16
|
import {
|
|
17
|
+
Cause_exports,
|
|
14
18
|
Clock_exports,
|
|
15
19
|
Effect_exports,
|
|
16
20
|
Encoding_exports,
|
|
17
21
|
Schema_exports,
|
|
18
22
|
Semaphore_exports
|
|
19
|
-
} from "./chunk-
|
|
23
|
+
} from "./chunk-CDL5PM2Q.js";
|
|
20
24
|
|
|
21
25
|
// ../app-data/src/implementation/schema.ts
|
|
22
|
-
var metadata =
|
|
26
|
+
var metadata = new Set(reservedFieldNames);
|
|
27
|
+
var reserved = (name) => metadata.has(name);
|
|
23
28
|
var indexesFor = (table) => [{ name: "by_creation", fields: [] }, ...table.indexes].map((index) => ({
|
|
24
29
|
name: index.name,
|
|
25
30
|
fields: [
|
|
@@ -33,23 +38,25 @@ var validScalar = (field, value) => field.kind === "number" ? typeof value === "
|
|
|
33
38
|
return point !== void 0 && point >= 55296 && point <= 57343;
|
|
34
39
|
});
|
|
35
40
|
var parseDatabaseSchema = (input) => Schema_exports.decodeUnknownEffect(DatabaseSchema)(input).pipe(
|
|
41
|
+
Effect_exports.mapError(() => new AppDatabaseError({ reason: "schema" })),
|
|
36
42
|
Effect_exports.flatMap(
|
|
37
43
|
(schema) => Effect_exports.gen(function* () {
|
|
38
|
-
for (const table of Object.
|
|
39
|
-
|
|
44
|
+
for (const [name, table] of Object.entries(schema)) {
|
|
45
|
+
const field = Object.keys(table.fields).find(reserved);
|
|
46
|
+
if (field !== void 0) return yield* new DatabaseFieldReserved({ table: name, field });
|
|
47
|
+
if (new Set(table.indexes.map((index) => index.name)).size !== table.indexes.length)
|
|
40
48
|
return yield* new AppDatabaseError({ reason: "schema" });
|
|
41
|
-
for (const
|
|
42
|
-
if ((
|
|
49
|
+
for (const field2 of Object.values(table.fields)) {
|
|
50
|
+
if ((field2.kind === "id" ? field2.references === void 0 : field2.references !== void 0) || field2.default !== void 0 && !validScalar(field2, field2.default) || field2.references !== void 0 && !Object.hasOwn(schema, field2.references))
|
|
43
51
|
return yield* new AppDatabaseError({ reason: "schema" });
|
|
44
52
|
}
|
|
45
53
|
for (const index of table.indexes)
|
|
46
|
-
if (index.name === "by_creation" || new Set(index.fields).size !== index.fields.length || index.fields.some((
|
|
54
|
+
if (index.name === "by_creation" || new Set(index.fields).size !== index.fields.length || index.fields.some((name2) => fieldFor(table, name2) === void 0))
|
|
47
55
|
return yield* new AppDatabaseError({ reason: "schema" });
|
|
48
56
|
}
|
|
49
57
|
return schema;
|
|
50
58
|
})
|
|
51
|
-
)
|
|
52
|
-
Effect_exports.mapError(() => new AppDatabaseError({ reason: "schema" }))
|
|
59
|
+
)
|
|
53
60
|
);
|
|
54
61
|
var canonicalSchema = (schema) => JSON.stringify(
|
|
55
62
|
Object.fromEntries(
|
|
@@ -248,7 +255,12 @@ var decodeBody = Schema_exports.decodeUnknownEffect(Schema_exports.fromJsonStrin
|
|
|
248
255
|
var storageError = () => new AppDatabaseError({ reason: "storage" });
|
|
249
256
|
var makeSqliteDatabase = (options) => Effect_exports.gen(function* () {
|
|
250
257
|
const { sql, crypto } = options;
|
|
251
|
-
const schema = yield* parseDatabaseSchema(options.schema)
|
|
258
|
+
const schema = yield* parseDatabaseSchema(options.schema).pipe(
|
|
259
|
+
Effect_exports.catchTag(
|
|
260
|
+
"DatabaseFieldReserved",
|
|
261
|
+
() => Effect_exports.fail(new AppDatabaseError({ reason: "schema" }))
|
|
262
|
+
)
|
|
263
|
+
);
|
|
252
264
|
const limits = yield* Schema_exports.decodeUnknownEffect(DatabaseLimits)(
|
|
253
265
|
options.limits ?? defaultDatabaseLimits
|
|
254
266
|
).pipe(Effect_exports.mapError(() => new AppDatabaseError({ reason: "limit" })));
|
|
@@ -295,7 +307,13 @@ var makeSqliteDatabase = (options) => Effect_exports.gen(function* () {
|
|
|
295
307
|
};
|
|
296
308
|
const charge = (name, amount) => Effect_exports.suspend(() => {
|
|
297
309
|
used[name] += amount;
|
|
298
|
-
return used[name] > limits[name] ? Effect_exports.fail(
|
|
310
|
+
return used[name] > limits[name] ? Effect_exports.fail(
|
|
311
|
+
new DatabaseLimitExceeded({
|
|
312
|
+
limit: name,
|
|
313
|
+
maximum: limits[name],
|
|
314
|
+
requested: used[name]
|
|
315
|
+
})
|
|
316
|
+
) : Effect_exports.void;
|
|
299
317
|
});
|
|
300
318
|
const get = (table, id) => Effect_exports.gen(function* () {
|
|
301
319
|
yield* charge("directGets", 1);
|
|
@@ -312,8 +330,13 @@ var makeSqliteDatabase = (options) => Effect_exports.gen(function* () {
|
|
|
312
330
|
const store = (tableName, table, row) => Effect_exports.gen(function* () {
|
|
313
331
|
const meta = yield* Schema_exports.decodeUnknownEffect(RowMetadata)(row);
|
|
314
332
|
const body = JSON.stringify(row);
|
|
315
|
-
|
|
316
|
-
|
|
333
|
+
const bytes = new TextEncoder().encode(body).length;
|
|
334
|
+
if (bytes > limits.valueBytes)
|
|
335
|
+
return yield* new DatabaseLimitExceeded({
|
|
336
|
+
limit: "valueBytes",
|
|
337
|
+
maximum: limits.valueBytes,
|
|
338
|
+
requested: bytes
|
|
339
|
+
});
|
|
317
340
|
const keys = yield* Effect_exports.forEach(
|
|
318
341
|
indexesFor(table),
|
|
319
342
|
(index) => encodeIndexKey(
|
|
@@ -384,9 +407,14 @@ var makeSqliteDatabase = (options) => Effect_exports.gen(function* () {
|
|
|
384
407
|
const bounds = yield* queryBounds(table, plan, limits.indexBytes);
|
|
385
408
|
reads.add(tableName);
|
|
386
409
|
yield* charge("scanCalls", 1);
|
|
387
|
-
const
|
|
388
|
-
const count = terminal.kind === "first" ? 1 : terminal.kind === "take" ? terminal.count : terminal.kind === "paginate" ? terminal.numItems :
|
|
389
|
-
if (
|
|
410
|
+
const remaining = terminal.kind === "count" ? limits.rowsRead - used.rowsRead : limits.rowsReturned - used.rowsReturned;
|
|
411
|
+
const count = terminal.kind === "first" ? 1 : terminal.kind === "take" ? terminal.count : terminal.kind === "paginate" ? terminal.numItems : remaining;
|
|
412
|
+
if ((terminal.kind === "take" || terminal.kind === "paginate") && count > limits.rowsReturned)
|
|
413
|
+
return yield* new DatabaseLimitExceeded({
|
|
414
|
+
limit: "pageSize",
|
|
415
|
+
maximum: limits.rowsReturned,
|
|
416
|
+
requested: count
|
|
417
|
+
});
|
|
390
418
|
if (count === 0 && terminal.kind === "take") return [];
|
|
391
419
|
const query = yield* fingerprint(
|
|
392
420
|
crypto,
|
|
@@ -412,7 +440,10 @@ var makeSqliteDatabase = (options) => Effect_exports.gen(function* () {
|
|
|
412
440
|
plan.order === "asc" ? sql`i.sort_key > ${position}` : sql`i.sort_key < ${position}`
|
|
413
441
|
);
|
|
414
442
|
const direction = plan.order === "asc" ? sql.literal("ASC") : sql.literal("DESC");
|
|
415
|
-
const limit =
|
|
443
|
+
const limit = Math.min(
|
|
444
|
+
terminal.kind === "first" || terminal.kind === "take" ? count : count + 1,
|
|
445
|
+
remaining + 1
|
|
446
|
+
);
|
|
416
447
|
if (terminal.kind === "count") {
|
|
417
448
|
const rows2 = yield* sql`SELECT i.sort_key FROM app_indexes i WHERE ${sql.and(predicates)} ORDER BY i.sort_key ${direction} LIMIT ${limit}`.pipe(
|
|
418
449
|
Effect_exports.flatMap(Schema_exports.decodeUnknownEffect(Schema_exports.Array(CountRow)))
|
|
@@ -436,7 +467,11 @@ var makeSqliteDatabase = (options) => Effect_exports.gen(function* () {
|
|
|
436
467
|
)
|
|
437
468
|
);
|
|
438
469
|
if (terminal.kind === "collect" && rows.length > count)
|
|
439
|
-
return yield* new
|
|
470
|
+
return yield* new DatabaseLimitExceeded({
|
|
471
|
+
limit: "rowsReturned",
|
|
472
|
+
maximum: limits.rowsReturned,
|
|
473
|
+
requested: used.rowsReturned + rows.length
|
|
474
|
+
});
|
|
440
475
|
const page = rows.slice(0, count);
|
|
441
476
|
yield* charge("rowsReturned", page.length);
|
|
442
477
|
const values = yield* Effect_exports.forEach(page, (row) => decodeBody(row.body));
|
|
@@ -502,6 +537,11 @@ var makeSqliteDatabase = (options) => Effect_exports.gen(function* () {
|
|
|
502
537
|
})
|
|
503
538
|
};
|
|
504
539
|
return yield* Effect_exports.suspend(() => work(session)).pipe(
|
|
540
|
+
// A failed database call poisons the session. Report that failure even when
|
|
541
|
+
// authored code caught it or threw something else in its place.
|
|
542
|
+
Effect_exports.catchCause(
|
|
543
|
+
(cause) => failed === void 0 || Cause_exports.hasInterrupts(cause) ? Effect_exports.failCause(cause) : Effect_exports.fail(failed)
|
|
544
|
+
),
|
|
505
545
|
Effect_exports.tap(
|
|
506
546
|
() => gate.withPermits(1)(
|
|
507
547
|
Effect_exports.suspend(() => failed === void 0 ? Effect_exports.void : Effect_exports.fail(failed))
|