stitchkit 0.54.0 → 0.55.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.
- package/README.md +4 -1
- package/dist/browser/socket-io.d.ts +11 -1
- package/dist/browser/socket-io.d.ts.map +1 -1
- package/dist/cli.js +14 -9
- package/dist/contract/file-ref.d.ts +13 -0
- package/dist/contract/file-ref.d.ts.map +1 -0
- package/dist/contract/index.d.ts +1 -0
- package/dist/contract/index.d.ts.map +1 -1
- package/dist/contract/index.js +21 -17
- package/dist/files/boundary.d.ts +52 -0
- package/dist/files/boundary.d.ts.map +1 -0
- package/dist/files.d.ts +3 -0
- package/dist/files.d.ts.map +1 -0
- package/dist/files.js +16 -0
- package/dist/{index-7vb44hy8.js → index-0gv7k0ra.js} +127 -92
- package/dist/index-1bx83sw4.js +4 -0
- package/dist/index-1k16zv57.js +269 -0
- package/dist/index-6k1937bx.js +20 -0
- package/dist/{index-bmnhqtya.js → index-7eq9va6e.js} +1 -4
- package/dist/{index-yxpe3phd.js → index-cby4ar3v.js} +1 -18
- package/dist/index-h60df7rj.js +110 -0
- package/dist/{index-yez419px.js → index-js7yexng.js} +19 -6
- package/dist/index-k4dftwf7.js +66 -0
- package/dist/{index-z7761jk2.js → index-npye5kt7.js} +16 -22
- package/dist/{index-b15rtha1.js → index-pzc32v75.js} +61 -3
- package/dist/{index-e1es808r.js → index-qh4xevf5.js} +1 -1
- package/dist/{index-gvha32jh.js → index-qx84bqzk.js} +2 -2
- package/dist/{index-pfqjb5xy.js → index-rgd18hx3.js} +23 -5
- package/dist/index-sbdmyz75.js +18 -0
- package/dist/{index-173tvqcp.js → index-v4bbq3p4.js} +9 -114
- package/dist/index.js +162 -35
- package/dist/node.js +30 -27
- package/dist/observability/index.js +28 -25
- package/dist/react.js +2 -2
- package/dist/realtime/contract.d.ts +9 -0
- package/dist/realtime/contract.d.ts.map +1 -1
- package/dist/realtime/index.d.ts +2 -1
- package/dist/realtime/index.d.ts.map +1 -1
- package/dist/realtime/request.d.ts +21 -0
- package/dist/realtime/request.d.ts.map +1 -0
- package/dist/realtime/socket.d.ts +3 -0
- package/dist/realtime/socket.d.ts.map +1 -1
- package/dist/remote.d.ts +9 -0
- package/dist/remote.d.ts.map +1 -0
- package/dist/remote.js +79 -0
- package/dist/server/context-contribution.d.ts +10 -0
- package/dist/server/context-contribution.d.ts.map +1 -0
- package/dist/server/context.d.ts.map +1 -1
- package/dist/server/index.d.ts +2 -1
- package/dist/server/index.d.ts.map +1 -1
- package/dist/server/index.js +133 -88
- package/dist/server/lifecycle.d.ts +4 -0
- package/dist/server/lifecycle.d.ts.map +1 -0
- package/dist/server/middleware/auth.d.ts +35 -7
- package/dist/server/middleware/auth.d.ts.map +1 -1
- package/dist/server/types.d.ts +1 -1
- package/dist/server/types.d.ts.map +1 -1
- package/dist/testing/surface-conformance.d.ts +47 -0
- package/dist/testing/surface-conformance.d.ts.map +1 -0
- package/dist/testing/surface-manifest.d.ts +156 -0
- package/dist/testing/surface-manifest.d.ts.map +1 -0
- package/dist/testing.d.ts +2 -0
- package/dist/testing.d.ts.map +1 -1
- package/dist/testing.js +366 -3
- package/dist/tools/agent.d.ts.map +1 -1
- package/dist/tools/async-operation.d.ts +168 -0
- package/dist/tools/async-operation.d.ts.map +1 -0
- package/dist/tools/cli-args.d.ts +1 -1
- package/dist/tools/cli-args.d.ts.map +1 -1
- package/dist/tools/cli-format.d.ts +2 -2
- package/dist/tools/cli-format.d.ts.map +1 -1
- package/dist/tools/cli-wait.d.ts +11 -2
- package/dist/tools/cli-wait.d.ts.map +1 -1
- package/dist/tools/cli.d.ts +2 -0
- package/dist/tools/cli.d.ts.map +1 -1
- package/dist/tools/define-download-tool.d.ts +6 -5
- package/dist/tools/define-download-tool.d.ts.map +1 -1
- package/dist/tools/define-upload-tool.d.ts +3 -1
- package/dist/tools/define-upload-tool.d.ts.map +1 -1
- package/dist/tools/define-wait-tool.d.ts +1 -1
- package/dist/tools/define-wait-tool.d.ts.map +1 -1
- package/dist/tools/download-core.d.ts +5 -10
- package/dist/tools/download-core.d.ts.map +1 -1
- package/dist/tools/lifecycle.d.ts +4 -0
- package/dist/tools/lifecycle.d.ts.map +1 -0
- package/dist/tools/mount-download.d.ts +5 -4
- package/dist/tools/mount-download.d.ts.map +1 -1
- package/dist/tools/mount-upload.d.ts +4 -2
- package/dist/tools/mount-upload.d.ts.map +1 -1
- package/dist/tools/upload-core.d.ts +3 -2
- package/dist/tools/upload-core.d.ts.map +1 -1
- package/dist/tools/view-file.d.ts +4 -3
- package/dist/tools/view-file.d.ts.map +1 -1
- package/dist/tools/wait-core.d.ts +6 -1
- package/dist/tools/wait-core.d.ts.map +1 -1
- package/dist/tools.d.ts +3 -2
- package/dist/tools.d.ts.map +1 -1
- package/dist/tools.js +385 -244
- package/llms-full.txt +417 -27
- package/package.json +10 -2
package/README.md
CHANGED
|
@@ -85,9 +85,12 @@ Server code imports server entrypoints:
|
|
|
85
85
|
import { createServer, createHandler, implement } from 'stitchkit/server'
|
|
86
86
|
import { createSocketIOServer, createAuthHook } from 'stitchkit/server'
|
|
87
87
|
import { createMcpHandler, mountAgent } from 'stitchkit/tools'
|
|
88
|
+
import { implementRemote } from 'stitchkit/remote'
|
|
88
89
|
```
|
|
89
90
|
|
|
90
|
-
The root `stitchkit` entrypoint is browser-safe. Server
|
|
91
|
+
The root `stitchkit` entrypoint is browser-safe. Server, tool and peer-free
|
|
92
|
+
remote-proxy code live behind `stitchkit/server`, `stitchkit/tools` and
|
|
93
|
+
`stitchkit/remote` respectively.
|
|
91
94
|
|
|
92
95
|
## Quick Start
|
|
93
96
|
|
|
@@ -22,7 +22,8 @@
|
|
|
22
22
|
*/
|
|
23
23
|
import type { EventsMap } from '@socket.io/component-emitter';
|
|
24
24
|
import type { StitchLogger } from '../logger';
|
|
25
|
-
import type { RealtimeContract, RealtimeEventRegistry, RealtimeRejectedEventHook } from '../realtime/contract';
|
|
25
|
+
import type { RealtimeAcknowledgedEvent, RealtimeAcknowledgement, RealtimeContract, RealtimeEventRegistry, RealtimeRejectedEventHook, RealtimeRequestArguments } from '../realtime/contract';
|
|
26
|
+
import { type RealtimeRequestOptions } from '../realtime/request';
|
|
26
27
|
import { type ValidatedRealtimeSocket } from '../realtime/socket';
|
|
27
28
|
/**
|
|
28
29
|
* Socket.IO event map — `{ event: (...args) => void }`. Aliases Socket.IO's
|
|
@@ -143,6 +144,11 @@ export interface SocketIOClient<TServerEvents extends SocketEventMap, TClientEve
|
|
|
143
144
|
* of an unordered backlog of stale emits.
|
|
144
145
|
*/
|
|
145
146
|
emit<E extends keyof TClientEvents & string>(event: E, ...args: Parameters<TClientEvents[E]>): boolean;
|
|
147
|
+
/**
|
|
148
|
+
* Low-level native Socket.IO acknowledgement request. Contract-aware callers
|
|
149
|
+
* should use `createRealtimeClient().request()`, which validates both sides.
|
|
150
|
+
*/
|
|
151
|
+
emitWithAck(event: string, args: unknown[], options: RealtimeRequestOptions): Promise<unknown>;
|
|
146
152
|
/**
|
|
147
153
|
* Subscribe to connection up/down changes. Returns an unsubscribe. On a
|
|
148
154
|
* disconnect the listener also receives the Socket.IO **reason** (e.g.
|
|
@@ -156,6 +162,10 @@ export interface RealtimeClient<TServerToClient extends RealtimeEventRegistry, T
|
|
|
156
162
|
connect(): void;
|
|
157
163
|
disconnect(): void;
|
|
158
164
|
readonly connected: boolean;
|
|
165
|
+
request<TEvent extends RealtimeAcknowledgedEvent<TClientToServer>>(event: TEvent, ...args: [
|
|
166
|
+
...RealtimeRequestArguments<TClientToServer[TEvent]>,
|
|
167
|
+
options: RealtimeRequestOptions
|
|
168
|
+
]): Promise<RealtimeAcknowledgement<TClientToServer[TEvent]>>;
|
|
159
169
|
onConnectionChange(listener: (connected: boolean, reason?: string) => void): () => void;
|
|
160
170
|
}
|
|
161
171
|
export interface RealtimeClientOptions<TServerToClient extends RealtimeEventRegistry> extends SocketIOClientConfig<{
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"socket-io.d.ts","sourceRoot":"","sources":["../../src/browser/socket-io.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,8BAA8B,CAAC;AAC9D,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,WAAW,CAAC;AAC9C,OAAO,KAAK,EACV,gBAAgB,EAChB,qBAAqB,EACrB,yBAAyB,
|
|
1
|
+
{"version":3,"file":"socket-io.d.ts","sourceRoot":"","sources":["../../src/browser/socket-io.ts"],"names":[],"mappings":"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"}
|
package/dist/cli.js
CHANGED
|
@@ -5,15 +5,20 @@ import {
|
|
|
5
5
|
emitResult,
|
|
6
6
|
parseCliArgs,
|
|
7
7
|
pollUntilDone
|
|
8
|
-
} from "./index-
|
|
9
|
-
import"./index-
|
|
10
|
-
import"./index-
|
|
11
|
-
import"./index-
|
|
8
|
+
} from "./index-0gv7k0ra.js";
|
|
9
|
+
import"./index-sbdmyz75.js";
|
|
10
|
+
import"./index-k4dftwf7.js";
|
|
11
|
+
import"./index-cby4ar3v.js";
|
|
12
|
+
import"./index-v4bbq3p4.js";
|
|
13
|
+
import"./index-h60df7rj.js";
|
|
14
|
+
import"./index-6k1937bx.js";
|
|
15
|
+
import"./index-7eq9va6e.js";
|
|
16
|
+
import"./index-1bx83sw4.js";
|
|
12
17
|
export {
|
|
13
|
-
|
|
14
|
-
parseCliArgs,
|
|
15
|
-
emitResult,
|
|
16
|
-
defineCliCommand,
|
|
18
|
+
DEFAULT_EXIT_CODES,
|
|
17
19
|
createCli,
|
|
18
|
-
|
|
20
|
+
defineCliCommand,
|
|
21
|
+
emitResult,
|
|
22
|
+
parseCliArgs,
|
|
23
|
+
pollUntilDone
|
|
19
24
|
};
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
/** Canonical POSIX-style path relative to a managed file boundary. */
|
|
3
|
+
export declare const ManagedFilePathSchema: z.ZodString;
|
|
4
|
+
/** Transport-safe identity and metadata for a file owned by a managed boundary. */
|
|
5
|
+
export declare const ManagedFileRefSchema: z.ZodObject<{
|
|
6
|
+
path: z.ZodString;
|
|
7
|
+
size: z.ZodNumber;
|
|
8
|
+
mediaType: z.ZodOptional<z.ZodString>;
|
|
9
|
+
name: z.ZodOptional<z.ZodString>;
|
|
10
|
+
}, z.core.$strip>;
|
|
11
|
+
export type ManagedFilePath = z.infer<typeof ManagedFilePathSchema>;
|
|
12
|
+
export type ManagedFileRef = z.infer<typeof ManagedFileRefSchema>;
|
|
13
|
+
//# sourceMappingURL=file-ref.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"file-ref.d.ts","sourceRoot":"","sources":["../../src/contract/file-ref.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAWxB,sEAAsE;AACtE,eAAO,MAAM,qBAAqB,aAE6C,CAAC;AAEhF,mFAAmF;AACnF,eAAO,MAAM,oBAAoB;;;;;iBAK/B,CAAC;AAEH,MAAM,MAAM,eAAe,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,qBAAqB,CAAC,CAAC;AACpE,MAAM,MAAM,cAAc,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,oBAAoB,CAAC,CAAC"}
|
package/dist/contract/index.d.ts
CHANGED
|
@@ -2,5 +2,6 @@ export { ALL_TRANSPORTS, type BodyHttpSuccessStatus, type ClientRequestOptions,
|
|
|
2
2
|
export { AppError, appError, badRequest, conflict, type ErrorEnvelope, forbidden, isStitchErrorCode, notFound, rateLimited, STITCH_ERROR_STATUS, type StitchErrorCode, unauthorized, } from './errors';
|
|
3
3
|
export { type DefinedAppError, type DefinedErrors, defineErrors, type ErrorDefinition, type ErrorDefinitions, type ErrorDetailsOutput, type ErrorDetailsSchema, type ErrorFactories, type ErrorFactory, type ErrorFactoryArguments, type FrozenErrorDefinitions, } from './errors-factory';
|
|
4
4
|
export { type ContractFactoryConfig, type ContractFactoryToolExposure, createContractFactory, type ExplicitScopedDefineContract, type ExplicitToolExposureEndpoints, type FactoryScopedEndpoint, type ScopedContractDef, type ScopedDefineContract, } from './factory';
|
|
5
|
+
export { type ManagedFilePath, ManagedFilePathSchema, type ManagedFileRef, ManagedFileRefSchema, } from './file-ref';
|
|
5
6
|
export { decodeCursor, encodeCursor, type Paginated, paginatedSchema, } from './pagination';
|
|
6
7
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/contract/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,cAAc,EACd,KAAK,qBAAqB,EAC1B,KAAK,oBAAoB,EACzB,KAAK,WAAW,EAChB,KAAK,YAAY,EACjB,cAAc,EACd,KAAK,WAAW,EAChB,KAAK,UAAU,EACf,KAAK,wBAAwB,EAC7B,KAAK,iBAAiB,EACtB,KAAK,oBAAoB,EACzB,KAAK,uBAAuB,EAC5B,KAAK,cAAc,EACnB,KAAK,cAAc,EACnB,KAAK,cAAc,EACnB,KAAK,eAAe,EACpB,KAAK,UAAU,EACf,KAAK,iBAAiB,EACtB,KAAK,cAAc,EACnB,KAAK,aAAa,EAClB,KAAK,eAAe,EACpB,KAAK,sBAAsB,EAC3B,KAAK,mBAAmB,EACxB,KAAK,aAAa,EAClB,KAAK,mBAAmB,EACxB,KAAK,gBAAgB,EACrB,KAAK,cAAc,EACnB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,WAAW,EAChB,KAAK,SAAS,EACd,KAAK,eAAe,EACpB,KAAK,WAAW,EAChB,KAAK,eAAe,EACpB,KAAK,eAAe,GACrB,MAAM,UAAU,CAAC;AAClB,OAAO,EACL,QAAQ,EACR,QAAQ,EACR,UAAU,EACV,QAAQ,EACR,KAAK,aAAa,EAClB,SAAS,EACT,iBAAiB,EACjB,QAAQ,EACR,WAAW,EACX,mBAAmB,EACnB,KAAK,eAAe,EACpB,YAAY,GACb,MAAM,UAAU,CAAC;AAClB,OAAO,EACL,KAAK,eAAe,EACpB,KAAK,aAAa,EAClB,YAAY,EACZ,KAAK,eAAe,EACpB,KAAK,gBAAgB,EACrB,KAAK,kBAAkB,EACvB,KAAK,kBAAkB,EACvB,KAAK,cAAc,EACnB,KAAK,YAAY,EACjB,KAAK,qBAAqB,EAC1B,KAAK,sBAAsB,GAC5B,MAAM,kBAAkB,CAAC;AAC1B,OAAO,EACL,KAAK,qBAAqB,EAC1B,KAAK,2BAA2B,EAChC,qBAAqB,EACrB,KAAK,4BAA4B,EACjC,KAAK,6BAA6B,EAClC,KAAK,qBAAqB,EAC1B,KAAK,iBAAiB,EACtB,KAAK,oBAAoB,GAC1B,MAAM,WAAW,CAAC;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/contract/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,cAAc,EACd,KAAK,qBAAqB,EAC1B,KAAK,oBAAoB,EACzB,KAAK,WAAW,EAChB,KAAK,YAAY,EACjB,cAAc,EACd,KAAK,WAAW,EAChB,KAAK,UAAU,EACf,KAAK,wBAAwB,EAC7B,KAAK,iBAAiB,EACtB,KAAK,oBAAoB,EACzB,KAAK,uBAAuB,EAC5B,KAAK,cAAc,EACnB,KAAK,cAAc,EACnB,KAAK,cAAc,EACnB,KAAK,eAAe,EACpB,KAAK,UAAU,EACf,KAAK,iBAAiB,EACtB,KAAK,cAAc,EACnB,KAAK,aAAa,EAClB,KAAK,eAAe,EACpB,KAAK,sBAAsB,EAC3B,KAAK,mBAAmB,EACxB,KAAK,aAAa,EAClB,KAAK,mBAAmB,EACxB,KAAK,gBAAgB,EACrB,KAAK,cAAc,EACnB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,WAAW,EAChB,KAAK,SAAS,EACd,KAAK,eAAe,EACpB,KAAK,WAAW,EAChB,KAAK,eAAe,EACpB,KAAK,eAAe,GACrB,MAAM,UAAU,CAAC;AAClB,OAAO,EACL,QAAQ,EACR,QAAQ,EACR,UAAU,EACV,QAAQ,EACR,KAAK,aAAa,EAClB,SAAS,EACT,iBAAiB,EACjB,QAAQ,EACR,WAAW,EACX,mBAAmB,EACnB,KAAK,eAAe,EACpB,YAAY,GACb,MAAM,UAAU,CAAC;AAClB,OAAO,EACL,KAAK,eAAe,EACpB,KAAK,aAAa,EAClB,YAAY,EACZ,KAAK,eAAe,EACpB,KAAK,gBAAgB,EACrB,KAAK,kBAAkB,EACvB,KAAK,kBAAkB,EACvB,KAAK,cAAc,EACnB,KAAK,YAAY,EACjB,KAAK,qBAAqB,EAC1B,KAAK,sBAAsB,GAC5B,MAAM,kBAAkB,CAAC;AAC1B,OAAO,EACL,KAAK,qBAAqB,EAC1B,KAAK,2BAA2B,EAChC,qBAAqB,EACrB,KAAK,4BAA4B,EACjC,KAAK,6BAA6B,EAClC,KAAK,qBAAqB,EAC1B,KAAK,iBAAiB,EACtB,KAAK,oBAAoB,GAC1B,MAAM,WAAW,CAAC;AACnB,OAAO,EACL,KAAK,eAAe,EACpB,qBAAqB,EACrB,KAAK,cAAc,EACnB,oBAAoB,GACrB,MAAM,YAAY,CAAC;AAEpB,OAAO,EACL,YAAY,EACZ,YAAY,EACZ,KAAK,SAAS,EACd,eAAe,GAChB,MAAM,cAAc,CAAC"}
|
package/dist/contract/index.js
CHANGED
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
import {
|
|
2
2
|
ALL_TRANSPORTS,
|
|
3
3
|
AppError,
|
|
4
|
+
ManagedFilePathSchema,
|
|
5
|
+
ManagedFileRefSchema,
|
|
4
6
|
STITCH_ERROR_STATUS,
|
|
5
7
|
appError,
|
|
6
8
|
badRequest,
|
|
@@ -16,24 +18,26 @@ import {
|
|
|
16
18
|
paginatedSchema,
|
|
17
19
|
rateLimited,
|
|
18
20
|
unauthorized
|
|
19
|
-
} from "../index-
|
|
21
|
+
} from "../index-rgd18hx3.js";
|
|
20
22
|
import"../index-tss6bk5c.js";
|
|
21
23
|
export {
|
|
22
|
-
|
|
23
|
-
rateLimited,
|
|
24
|
-
paginatedSchema,
|
|
25
|
-
notFound,
|
|
26
|
-
isStitchErrorCode,
|
|
27
|
-
forbidden,
|
|
28
|
-
encodeCursor,
|
|
29
|
-
defineErrors,
|
|
30
|
-
defineContract,
|
|
31
|
-
decodeCursor,
|
|
32
|
-
createContractFactory,
|
|
33
|
-
conflict,
|
|
34
|
-
badRequest,
|
|
35
|
-
appError,
|
|
36
|
-
STITCH_ERROR_STATUS,
|
|
24
|
+
ALL_TRANSPORTS,
|
|
37
25
|
AppError,
|
|
38
|
-
|
|
26
|
+
ManagedFilePathSchema,
|
|
27
|
+
ManagedFileRefSchema,
|
|
28
|
+
STITCH_ERROR_STATUS,
|
|
29
|
+
appError,
|
|
30
|
+
badRequest,
|
|
31
|
+
conflict,
|
|
32
|
+
createContractFactory,
|
|
33
|
+
decodeCursor,
|
|
34
|
+
defineContract,
|
|
35
|
+
defineErrors,
|
|
36
|
+
encodeCursor,
|
|
37
|
+
forbidden,
|
|
38
|
+
isStitchErrorCode,
|
|
39
|
+
notFound,
|
|
40
|
+
paginatedSchema,
|
|
41
|
+
rateLimited,
|
|
42
|
+
unauthorized
|
|
39
43
|
};
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import { type ManagedFileRef } from '../contract/file-ref';
|
|
2
|
+
export type ManagedFileErrorCode = 'FILE_INVALID_PATH' | 'FILE_NOT_FOUND' | 'FILE_NOT_REGULAR' | 'FILE_OUTSIDE_ROOT' | 'FILE_TOO_LARGE' | 'FILE_EXISTS' | 'FILE_INSPECTION_REJECTED' | 'FILE_IO_ERROR';
|
|
3
|
+
export declare class ManagedFileError extends Error {
|
|
4
|
+
readonly code: ManagedFileErrorCode;
|
|
5
|
+
constructor(code: ManagedFileErrorCode, message: string, options?: ErrorOptions);
|
|
6
|
+
}
|
|
7
|
+
export interface ManagedFileInspectionInput {
|
|
8
|
+
prefix: Uint8Array;
|
|
9
|
+
declaredMediaType?: string;
|
|
10
|
+
name: string;
|
|
11
|
+
}
|
|
12
|
+
export interface ManagedFileInspection {
|
|
13
|
+
mediaType?: string;
|
|
14
|
+
name?: string;
|
|
15
|
+
}
|
|
16
|
+
export type ManagedFileInspector = (input: ManagedFileInspectionInput) => ManagedFileInspection | Promise<ManagedFileInspection>;
|
|
17
|
+
export interface ManagedFileBoundaryConfig {
|
|
18
|
+
/** Existing directory owned exclusively by the application or trusted OS actor. */
|
|
19
|
+
root: string;
|
|
20
|
+
maxReadBytes?: number;
|
|
21
|
+
maxWriteBytes?: number;
|
|
22
|
+
inspectionBytes?: number;
|
|
23
|
+
inspect?: ManagedFileInspector;
|
|
24
|
+
onCleanupError?: (error: unknown) => void;
|
|
25
|
+
}
|
|
26
|
+
export interface ManagedFileReadOptions {
|
|
27
|
+
maxBytes?: number;
|
|
28
|
+
signal?: AbortSignal;
|
|
29
|
+
}
|
|
30
|
+
export interface ManagedFileWriteOptions {
|
|
31
|
+
replace?: boolean;
|
|
32
|
+
durable?: boolean;
|
|
33
|
+
maxBytes?: number;
|
|
34
|
+
mediaType?: string;
|
|
35
|
+
name?: string;
|
|
36
|
+
signal?: AbortSignal;
|
|
37
|
+
}
|
|
38
|
+
export interface ManagedFileSource {
|
|
39
|
+
ref: ManagedFileRef;
|
|
40
|
+
bytes: Uint8Array;
|
|
41
|
+
}
|
|
42
|
+
export interface ManagedFileBoundary {
|
|
43
|
+
read(path: string, options?: ManagedFileReadOptions): Promise<ManagedFileSource>;
|
|
44
|
+
write(path: string, source: Uint8Array | ReadableStream<Uint8Array>, options?: ManagedFileWriteOptions): Promise<ManagedFileRef>;
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* Bind one existing application-owned directory as a portable Node/Bun file boundary.
|
|
48
|
+
* Concurrent replacement by another filesystem actor is intentionally outside this
|
|
49
|
+
* portable threat model; use OS-specific descriptor-relative isolation for that case.
|
|
50
|
+
*/
|
|
51
|
+
export declare function createManagedFileBoundary(config: ManagedFileBoundaryConfig): Promise<ManagedFileBoundary>;
|
|
52
|
+
//# sourceMappingURL=boundary.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"boundary.d.ts","sourceRoot":"","sources":["../../src/files/boundary.ts"],"names":[],"mappings":"AAIA,OAAO,EAEL,KAAK,cAAc,EAEpB,MAAM,sBAAsB,CAAC;AAO9B,MAAM,MAAM,oBAAoB,GAC5B,mBAAmB,GACnB,gBAAgB,GAChB,kBAAkB,GAClB,mBAAmB,GACnB,gBAAgB,GAChB,aAAa,GACb,0BAA0B,GAC1B,eAAe,CAAC;AAEpB,qBAAa,gBAAiB,SAAQ,KAAK;aAEvB,IAAI,EAAE,oBAAoB;IAD5C,YACkB,IAAI,EAAE,oBAAoB,EAC1C,OAAO,EAAE,MAAM,EACf,OAAO,CAAC,EAAE,YAAY,EAIvB;CACF;AAED,MAAM,WAAW,0BAA0B;IACzC,MAAM,EAAE,UAAU,CAAC;IACnB,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,IAAI,EAAE,MAAM,CAAC;CACd;AAED,MAAM,WAAW,qBAAqB;IACpC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,MAAM,MAAM,oBAAoB,GAAG,CACjC,KAAK,EAAE,0BAA0B,KAC9B,qBAAqB,GAAG,OAAO,CAAC,qBAAqB,CAAC,CAAC;AAE5D,MAAM,WAAW,yBAAyB;IACxC,mFAAmF;IACnF,IAAI,EAAE,MAAM,CAAC;IACb,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB,OAAO,CAAC,EAAE,oBAAoB,CAAC;IAC/B,cAAc,CAAC,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,IAAI,CAAC;CAC3C;AAED,MAAM,WAAW,sBAAsB;IACrC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,MAAM,CAAC,EAAE,WAAW,CAAC;CACtB;AAED,MAAM,WAAW,uBAAuB;IACtC,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,WAAW,CAAC;CACtB;AAED,MAAM,WAAW,iBAAiB;IAChC,GAAG,EAAE,cAAc,CAAC;IACpB,KAAK,EAAE,UAAU,CAAC;CACnB;AAED,MAAM,WAAW,mBAAmB;IAClC,IAAI,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,sBAAsB,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAAC;IACjF,KAAK,CACH,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,UAAU,GAAG,cAAc,CAAC,UAAU,CAAC,EAC/C,OAAO,CAAC,EAAE,uBAAuB,GAChC,OAAO,CAAC,cAAc,CAAC,CAAC;CAC5B;AAyID;;;;GAIG;AACH,wBAAsB,yBAAyB,CAC7C,MAAM,EAAE,yBAAyB,GAChC,OAAO,CAAC,mBAAmB,CAAC,CAqJ9B"}
|
package/dist/files.d.ts
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
export { type ManagedFilePath, ManagedFilePathSchema, type ManagedFileRef, ManagedFileRefSchema, } from './contract/file-ref';
|
|
2
|
+
export { createManagedFileBoundary, type ManagedFileBoundary, type ManagedFileBoundaryConfig, ManagedFileError, type ManagedFileErrorCode, type ManagedFileInspection, type ManagedFileInspectionInput, type ManagedFileInspector, type ManagedFileReadOptions, type ManagedFileSource, type ManagedFileWriteOptions, } from './files/boundary';
|
|
3
|
+
//# sourceMappingURL=files.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"files.d.ts","sourceRoot":"","sources":["../src/files.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,KAAK,eAAe,EACpB,qBAAqB,EACrB,KAAK,cAAc,EACnB,oBAAoB,GACrB,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EACL,yBAAyB,EACzB,KAAK,mBAAmB,EACxB,KAAK,yBAAyB,EAC9B,gBAAgB,EAChB,KAAK,oBAAoB,EACzB,KAAK,qBAAqB,EAC1B,KAAK,0BAA0B,EAC/B,KAAK,oBAAoB,EACzB,KAAK,sBAAsB,EAC3B,KAAK,iBAAiB,EACtB,KAAK,uBAAuB,GAC7B,MAAM,kBAAkB,CAAC"}
|
package/dist/files.js
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import {
|
|
2
|
+
ManagedFileError,
|
|
3
|
+
createManagedFileBoundary
|
|
4
|
+
} from "./index-1k16zv57.js";
|
|
5
|
+
import"./index-sbdmyz75.js";
|
|
6
|
+
import {
|
|
7
|
+
ManagedFilePathSchema,
|
|
8
|
+
ManagedFileRefSchema
|
|
9
|
+
} from "./index-6k1937bx.js";
|
|
10
|
+
import"./index-1bx83sw4.js";
|
|
11
|
+
export {
|
|
12
|
+
ManagedFileError,
|
|
13
|
+
ManagedFilePathSchema,
|
|
14
|
+
ManagedFileRefSchema,
|
|
15
|
+
createManagedFileBoundary
|
|
16
|
+
};
|
|
@@ -1,23 +1,33 @@
|
|
|
1
1
|
import {
|
|
2
|
-
isWithinDir
|
|
2
|
+
isWithinDir
|
|
3
|
+
} from "./index-sbdmyz75.js";
|
|
4
|
+
import {
|
|
5
|
+
assertToolName,
|
|
6
|
+
assertUniqueToolName,
|
|
7
|
+
hasUsableChars,
|
|
8
|
+
toToolName
|
|
9
|
+
} from "./index-k4dftwf7.js";
|
|
10
|
+
import {
|
|
3
11
|
jsonSchemaFields,
|
|
4
12
|
toJsonSchema
|
|
5
|
-
} from "./index-
|
|
13
|
+
} from "./index-cby4ar3v.js";
|
|
6
14
|
import {
|
|
7
|
-
AppError,
|
|
8
|
-
STITCH_ERROR_STATUS,
|
|
9
15
|
formatZodError,
|
|
10
16
|
getRequestContext,
|
|
11
|
-
isStitchErrorCode,
|
|
12
|
-
isUnsafeKey,
|
|
13
17
|
normalizeError,
|
|
14
18
|
runWithRequestContext,
|
|
15
|
-
safeJsonParse,
|
|
16
19
|
validateDeclaredOutput
|
|
17
|
-
} from "./index-
|
|
20
|
+
} from "./index-v4bbq3p4.js";
|
|
21
|
+
import {
|
|
22
|
+
AppError,
|
|
23
|
+
STITCH_ERROR_STATUS,
|
|
24
|
+
isStitchErrorCode,
|
|
25
|
+
isUnsafeKey,
|
|
26
|
+
safeJsonParse
|
|
27
|
+
} from "./index-h60df7rj.js";
|
|
18
28
|
import {
|
|
19
29
|
isRecord
|
|
20
|
-
} from "./index-
|
|
30
|
+
} from "./index-7eq9va6e.js";
|
|
21
31
|
|
|
22
32
|
// src/tools/coerce.ts
|
|
23
33
|
import { z } from "zod";
|
|
@@ -769,71 +779,6 @@ async function runToolMethod(method, toolName, rawArgs, context, hooks, lifecycl
|
|
|
769
779
|
}
|
|
770
780
|
}
|
|
771
781
|
|
|
772
|
-
// src/tools/names.ts
|
|
773
|
-
var SINGULAR_EXCEPTIONS = new Set([
|
|
774
|
-
"analytics",
|
|
775
|
-
"status",
|
|
776
|
-
"stats",
|
|
777
|
-
"settings",
|
|
778
|
-
"media",
|
|
779
|
-
"progress",
|
|
780
|
-
"news"
|
|
781
|
-
]);
|
|
782
|
-
var TOOL_NAME_RE = /^[a-zA-Z0-9_-]{1,64}$/;
|
|
783
|
-
function normalizeService(value) {
|
|
784
|
-
return value.replace(/[^a-zA-Z0-9_]/g, "_");
|
|
785
|
-
}
|
|
786
|
-
function normalizeMethod(value) {
|
|
787
|
-
return value.replace(/[^a-zA-Z0-9_-]/g, "_");
|
|
788
|
-
}
|
|
789
|
-
function singularize(name) {
|
|
790
|
-
if (SINGULAR_EXCEPTIONS.has(name))
|
|
791
|
-
return name;
|
|
792
|
-
if (name.endsWith("ies"))
|
|
793
|
-
return `${name.slice(0, -3)}y`;
|
|
794
|
-
if (name.endsWith("s") && !name.endsWith("ss"))
|
|
795
|
-
return name.slice(0, -1);
|
|
796
|
-
return name;
|
|
797
|
-
}
|
|
798
|
-
function singularizeTail(name) {
|
|
799
|
-
const cut = name.lastIndexOf("_");
|
|
800
|
-
if (cut === -1)
|
|
801
|
-
return singularize(name);
|
|
802
|
-
return `${name.slice(0, cut + 1)}${singularize(name.slice(cut + 1))}`;
|
|
803
|
-
}
|
|
804
|
-
function hasUsableChars(value) {
|
|
805
|
-
return /[a-zA-Z0-9]/.test(value);
|
|
806
|
-
}
|
|
807
|
-
function assertToolName(name, serviceName, key) {
|
|
808
|
-
const where = `service "${serviceName}", method "${key}"`;
|
|
809
|
-
if (!TOOL_NAME_RE.test(name)) {
|
|
810
|
-
const why = name.length > 64 ? `is ${name.length} characters (max 64) — set an explicit \`toolName\`` : "must match [a-zA-Z0-9_-]";
|
|
811
|
-
throw new Error(`Tool name "${name}" (${where}) ${why}`);
|
|
812
|
-
}
|
|
813
|
-
}
|
|
814
|
-
function toToolName(serviceName, methodName) {
|
|
815
|
-
const normalized = normalizeService(serviceName);
|
|
816
|
-
const singular = singularizeTail(normalized);
|
|
817
|
-
const method = normalizeMethod(methodName);
|
|
818
|
-
if (method === "list")
|
|
819
|
-
return `list_${normalized}`;
|
|
820
|
-
if (method === "get")
|
|
821
|
-
return `get_${singular}`;
|
|
822
|
-
if (method === "create")
|
|
823
|
-
return `create_${singular}`;
|
|
824
|
-
if (method === "update")
|
|
825
|
-
return `update_${singular}`;
|
|
826
|
-
if (method === "delete")
|
|
827
|
-
return `delete_${singular}`;
|
|
828
|
-
const snake = method.replace(/([A-Z])/g, "_$1").toLowerCase();
|
|
829
|
-
return `${snake}_${singular}`.replace(/^_/, "");
|
|
830
|
-
}
|
|
831
|
-
function assertUniqueToolName(name, taken, surface) {
|
|
832
|
-
if (taken) {
|
|
833
|
-
throw new Error(`Duplicate ${surface} "${name}" across mounted operations`);
|
|
834
|
-
}
|
|
835
|
-
}
|
|
836
|
-
|
|
837
782
|
// src/tools/presentation.ts
|
|
838
783
|
import { z as z3 } from "zod";
|
|
839
784
|
function withoutDialect(schema) {
|
|
@@ -1494,19 +1439,21 @@ var DEFAULT_EXIT_CODES = {
|
|
|
1494
1439
|
CONFLICT: 5,
|
|
1495
1440
|
RATE_LIMITED: 6,
|
|
1496
1441
|
TIMEOUT: 7,
|
|
1442
|
+
WAIT_FAILED: 1,
|
|
1497
1443
|
INTERNAL_SERVER_ERROR: 1
|
|
1498
1444
|
};
|
|
1499
1445
|
function emitResult(result, writers, opts) {
|
|
1500
1446
|
if (result.ok) {
|
|
1501
1447
|
if (result.data === undefined)
|
|
1502
1448
|
return 0;
|
|
1503
|
-
const
|
|
1504
|
-
writers.stdout(`${
|
|
1449
|
+
const text2 = opts.json ? JSON.stringify(result.data) : JSON.stringify(result.data, null, 2);
|
|
1450
|
+
writers.stdout(`${text2}
|
|
1505
1451
|
`);
|
|
1506
1452
|
return 0;
|
|
1507
1453
|
}
|
|
1508
1454
|
const error = formatToolError(result, opts.toolName, opts.errorHint);
|
|
1509
|
-
|
|
1455
|
+
const text = opts.json ? JSON.stringify(error) : JSON.stringify(error, null, 2);
|
|
1456
|
+
writers.stderr(`${text}
|
|
1510
1457
|
`);
|
|
1511
1458
|
const codes = opts.exitCodes ?? DEFAULT_EXIT_CODES;
|
|
1512
1459
|
return codes[result.code] ?? 1;
|
|
@@ -1515,6 +1462,13 @@ function emitResult(result, writers, opts) {
|
|
|
1515
1462
|
// src/tools/wait-core.ts
|
|
1516
1463
|
var DEFAULT_BACKOFF = [2, 3, 5, 5, 8, 10];
|
|
1517
1464
|
var DEFAULT_TIMEOUT = 600;
|
|
1465
|
+
|
|
1466
|
+
class WaitTimeoutError extends Error {
|
|
1467
|
+
constructor() {
|
|
1468
|
+
super("wait deadline elapsed before the first snapshot");
|
|
1469
|
+
this.name = "WaitTimeoutError";
|
|
1470
|
+
}
|
|
1471
|
+
}
|
|
1518
1472
|
var defaultSleep = (ms, signal) => {
|
|
1519
1473
|
signal?.throwIfAborted();
|
|
1520
1474
|
return new Promise((resolve, reject) => {
|
|
@@ -1544,52 +1498,104 @@ async function pollUntil(params) {
|
|
|
1544
1498
|
const lastBackoff = backoff[backoff.length - 1] ?? 5;
|
|
1545
1499
|
const timeoutSec = params.timeoutSec ?? DEFAULT_TIMEOUT;
|
|
1546
1500
|
const sleep = params.sleepFn ?? defaultSleep;
|
|
1547
|
-
const
|
|
1501
|
+
const now = params.nowFn ?? (() => performance.now());
|
|
1502
|
+
const startedAt = now();
|
|
1503
|
+
const deadline = startedAt + timeoutSec * 1000;
|
|
1504
|
+
let last;
|
|
1548
1505
|
for (let attempt = 0;; attempt++) {
|
|
1549
1506
|
params.signal?.throwIfAborted();
|
|
1550
|
-
const
|
|
1507
|
+
const remainingBeforePoll = Math.max(0, deadline - now());
|
|
1508
|
+
if (remainingBeforePoll === 0 && last) {
|
|
1509
|
+
return { state: last.state, timedOut: true };
|
|
1510
|
+
}
|
|
1511
|
+
const deadlineController = new AbortController;
|
|
1512
|
+
const onCallerAbort = () => deadlineController.abort(params.signal?.reason);
|
|
1513
|
+
params.signal?.addEventListener("abort", onCallerAbort, { once: true });
|
|
1514
|
+
const deadlineTimer = setTimeout(() => deadlineController.abort(new WaitTimeoutError), remainingBeforePoll);
|
|
1515
|
+
deadlineTimer.unref?.();
|
|
1516
|
+
let state;
|
|
1517
|
+
try {
|
|
1518
|
+
state = await params.poll(deadlineController.signal);
|
|
1519
|
+
} catch (error) {
|
|
1520
|
+
if (params.signal?.aborted)
|
|
1521
|
+
throw params.signal.reason ?? error;
|
|
1522
|
+
if (deadlineController.signal.aborted && now() >= deadline) {
|
|
1523
|
+
if (last)
|
|
1524
|
+
return { state: last.state, timedOut: true };
|
|
1525
|
+
throw new WaitTimeoutError;
|
|
1526
|
+
}
|
|
1527
|
+
throw error;
|
|
1528
|
+
} finally {
|
|
1529
|
+
clearTimeout(deadlineTimer);
|
|
1530
|
+
params.signal?.removeEventListener("abort", onCallerAbort);
|
|
1531
|
+
}
|
|
1551
1532
|
params.signal?.throwIfAborted();
|
|
1533
|
+
last = { state };
|
|
1552
1534
|
if (params.done(state))
|
|
1553
1535
|
return { state, timedOut: false };
|
|
1554
|
-
const
|
|
1536
|
+
const elapsedMs = now() - startedAt;
|
|
1537
|
+
const elapsedSec = elapsedMs / 1000;
|
|
1555
1538
|
params.onTick?.(attempt + 1, elapsedSec);
|
|
1556
1539
|
if (elapsedSec >= timeoutSec)
|
|
1557
1540
|
return { state, timedOut: true };
|
|
1558
1541
|
const waitSec = backoff[Math.min(attempt, backoff.length - 1)] ?? lastBackoff;
|
|
1559
|
-
await sleep(waitSec * 1000, params.signal);
|
|
1542
|
+
await sleep(Math.min(waitSec * 1000, Math.max(0, deadline - now())), params.signal);
|
|
1560
1543
|
}
|
|
1561
1544
|
}
|
|
1562
1545
|
function runWaitOperation(params) {
|
|
1563
1546
|
return pollUntil({
|
|
1564
|
-
poll: () => params.poll(params.input,
|
|
1547
|
+
poll: (signal) => params.poll(params.input, signal),
|
|
1565
1548
|
done: params.done,
|
|
1566
1549
|
backoff: params.backoff,
|
|
1567
1550
|
timeoutSec: params.timeoutSec,
|
|
1568
1551
|
sleepFn: params.sleepFn,
|
|
1569
1552
|
onTick: params.onTick,
|
|
1570
|
-
signal: params.signal
|
|
1553
|
+
signal: params.signal,
|
|
1554
|
+
nowFn: params.nowFn
|
|
1571
1555
|
});
|
|
1572
1556
|
}
|
|
1573
1557
|
|
|
1574
1558
|
// src/tools/cli-wait.ts
|
|
1575
1559
|
var DEFAULT_TIMEOUT2 = 600;
|
|
1560
|
+
function waitFailure(tool, result) {
|
|
1561
|
+
return {
|
|
1562
|
+
ok: false,
|
|
1563
|
+
code: "WAIT_FAILED",
|
|
1564
|
+
details: {
|
|
1565
|
+
message: `"${tool}" reached a terminal failed state`,
|
|
1566
|
+
result
|
|
1567
|
+
}
|
|
1568
|
+
};
|
|
1569
|
+
}
|
|
1576
1570
|
async function pollUntilDone(params) {
|
|
1577
1571
|
const { initial, wait, call } = params;
|
|
1578
1572
|
if (!initial.ok)
|
|
1579
1573
|
return initial;
|
|
1574
|
+
if (wait.failed?.(initial.data))
|
|
1575
|
+
return waitFailure(wait.tool, initial.data);
|
|
1580
1576
|
if (wait.done(initial.data))
|
|
1581
1577
|
return initial;
|
|
1582
1578
|
const pollArgs = wait.poll(initial.data);
|
|
1583
1579
|
if (!pollArgs)
|
|
1584
1580
|
return initial;
|
|
1585
1581
|
const timeoutSec = params.timeoutSec ?? wait.timeout ?? DEFAULT_TIMEOUT2;
|
|
1582
|
+
let failedState;
|
|
1586
1583
|
const { state, timedOut } = await pollUntil({
|
|
1587
1584
|
poll: () => call(wait.tool, pollArgs),
|
|
1588
|
-
done: (result) =>
|
|
1585
|
+
done: (result) => {
|
|
1586
|
+
if (!result.ok)
|
|
1587
|
+
return true;
|
|
1588
|
+
if (wait.failed?.(result.data)) {
|
|
1589
|
+
failedState = result;
|
|
1590
|
+
return true;
|
|
1591
|
+
}
|
|
1592
|
+
return wait.done(result.data);
|
|
1593
|
+
},
|
|
1589
1594
|
backoff: wait.backoff,
|
|
1590
1595
|
timeoutSec,
|
|
1591
1596
|
sleepFn: params.sleepFn,
|
|
1592
|
-
onTick: params.onTick
|
|
1597
|
+
onTick: params.onTick,
|
|
1598
|
+
signal: params.signal
|
|
1593
1599
|
});
|
|
1594
1600
|
if (timedOut) {
|
|
1595
1601
|
return {
|
|
@@ -1598,6 +1604,8 @@ async function pollUntilDone(params) {
|
|
|
1598
1604
|
details: { message: `Timed out after ${timeoutSec}s waiting for "${wait.tool}"` }
|
|
1599
1605
|
};
|
|
1600
1606
|
}
|
|
1607
|
+
if (state === failedState && state.ok)
|
|
1608
|
+
return waitFailure(wait.tool, state.data);
|
|
1601
1609
|
return state;
|
|
1602
1610
|
}
|
|
1603
1611
|
|
|
@@ -1961,7 +1969,7 @@ function collectToolSurface({
|
|
|
1961
1969
|
|
|
1962
1970
|
// src/tools/cli.ts
|
|
1963
1971
|
var GLOBAL_OPTIONS = [
|
|
1964
|
-
["--json", "Emit
|
|
1972
|
+
["--json", "Emit compact success/error JSON records (for scripts)"],
|
|
1965
1973
|
["--wait", "Block-poll an async result to a terminal state"],
|
|
1966
1974
|
["--wait-timeout <s>", "Override the --wait timeout in seconds"],
|
|
1967
1975
|
["--output-dir <dir>", "Download result media into a directory"],
|
|
@@ -2058,15 +2066,41 @@ function renderTopHelp(name, version, commands) {
|
|
|
2058
2066
|
`;
|
|
2059
2067
|
}
|
|
2060
2068
|
function renderCommandHelp(name, command, descriptor) {
|
|
2061
|
-
const lines = [descriptor.description, "", `Usage: ${name} ${command} [args] [--flags]`, ""];
|
|
2062
2069
|
const fields = jsonSchemaFields(descriptor.presentationSchema);
|
|
2070
|
+
const fieldsByName = new Map(fields.map((field) => [field.name, field]));
|
|
2071
|
+
const positionals = [];
|
|
2072
|
+
for (const [fieldName, info] of describeSchemaFields(descriptor.argumentSchema)) {
|
|
2073
|
+
if (info.kind === "boolean")
|
|
2074
|
+
continue;
|
|
2075
|
+
const field = fieldsByName.get(fieldName);
|
|
2076
|
+
if (field)
|
|
2077
|
+
positionals.push(field);
|
|
2078
|
+
}
|
|
2079
|
+
const positionalSyntax = new Map(positionals.map((field) => [
|
|
2080
|
+
field.name,
|
|
2081
|
+
field.required ? `<${field.name}>` : `[${field.name}]`
|
|
2082
|
+
]));
|
|
2083
|
+
const usage = [
|
|
2084
|
+
`Usage: ${name} ${command}`,
|
|
2085
|
+
...positionals.map((field) => positionalSyntax.get(field.name) ?? field.name),
|
|
2086
|
+
"[--flags]"
|
|
2087
|
+
].join(" ");
|
|
2088
|
+
const lines = [descriptor.description, "", usage, ""];
|
|
2063
2089
|
if (fields.length > 0) {
|
|
2064
2090
|
lines.push("Arguments:");
|
|
2065
|
-
const
|
|
2091
|
+
const labels = new Map(fields.map((field) => {
|
|
2092
|
+
const positional = positionalSyntax.get(field.name);
|
|
2093
|
+
return [
|
|
2094
|
+
field.name,
|
|
2095
|
+
positional ? `${positional} | --${field.name}` : `--${field.name}`
|
|
2096
|
+
];
|
|
2097
|
+
}));
|
|
2098
|
+
const width = Math.max(...fields.map((field) => labels.get(field.name)?.length ?? 0));
|
|
2066
2099
|
for (const f of fields) {
|
|
2067
2100
|
const req = f.required ? " (required)" : "";
|
|
2068
2101
|
const desc = f.description ? ` — ${f.description}` : "";
|
|
2069
|
-
|
|
2102
|
+
const label = labels.get(f.name) ?? `--${f.name}`;
|
|
2103
|
+
lines.push(` ${padRight(label, width)} <${typeLabel(f.schema)}>${req}${desc}`);
|
|
2070
2104
|
}
|
|
2071
2105
|
lines.push("");
|
|
2072
2106
|
}
|
|
@@ -2302,7 +2336,7 @@ async function createCli(config) {
|
|
|
2302
2336
|
}
|
|
2303
2337
|
const runTool = createToolRunner({
|
|
2304
2338
|
source: "cli",
|
|
2305
|
-
context: config.context?.(managed.auth),
|
|
2339
|
+
context: { ...config.context?.(managed.auth), signal: config.signal },
|
|
2306
2340
|
hooks: config.hooks,
|
|
2307
2341
|
lifecycle: config.lifecycle,
|
|
2308
2342
|
errorHint: config.errorHint,
|
|
@@ -2332,7 +2366,8 @@ async function createCli(config) {
|
|
|
2332
2366
|
},
|
|
2333
2367
|
timeoutSec: options.waitTimeout,
|
|
2334
2368
|
onTick: options.quiet ? undefined : (attempt) => stderr(`waiting… (poll ${attempt})
|
|
2335
|
-
`)
|
|
2369
|
+
`),
|
|
2370
|
+
signal: config.signal
|
|
2336
2371
|
});
|
|
2337
2372
|
}
|
|
2338
2373
|
let downloadsOk = true;
|
|
@@ -2348,4 +2383,4 @@ async function createCli(config) {
|
|
|
2348
2383
|
return exit(downloadsOk ? exitCode : 1);
|
|
2349
2384
|
}
|
|
2350
2385
|
|
|
2351
|
-
export { coerceJsonArgs, toolResultFromError, toolErrorFromResult, executeToolMethod,
|
|
2386
|
+
export { coerceJsonArgs, toolResultFromError, toolErrorFromResult, executeToolMethod, flattenToolJsonSchema, buildToolPresentationSchema, isObjectPresentationSchema, presentationMetadata, collectTools, createToolRunner, formatToolError, defineRuntimeTool, createRuntimeToolFactory, collectToolSurface, WaitTimeoutError, runWaitOperation, fetchGuarded, fetchPinnedDocument, readCapped, parseCliArgs, defineCliCommand, DEFAULT_EXIT_CODES, emitResult, pollUntilDone, createCli };
|