dsh-plugin-guide 0.3.2 → 0.3.4
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.es.md +5 -1
- package/README.hi.md +5 -1
- package/README.md +5 -1
- package/README.pt.md +5 -1
- package/README.zh.md +5 -1
- package/dist/dsh-plugin-dev.js +3 -3
- package/guide/plugin-dev-guide.md +2 -2
- package/guide/quick-reference.es.md +2 -2
- package/guide/quick-reference.hi.md +1 -1
- package/guide/quick-reference.md +2 -2
- package/guide/quick-reference.pt.md +2 -2
- package/guide/quick-reference.zh-CN.md +2 -2
- package/package.json +3 -3
- package/references/official-docs/AGENTS.md +3 -3
- package/references/official-docs/SNAPSHOT.md +4 -4
- package/references/official-docs/THIRD_PARTY_NOTICES.md +4 -6
- package/references/official-docs/docs/agent-lifecycle.i18n.yaml +2 -2
- package/references/official-docs/docs/agent-lifecycle.md +5 -3
- package/references/official-docs/docs/agent-lifecycle.zh.md +5 -3
- package/references/official-docs/docs/architecture.i18n.yaml +2 -2
- package/references/official-docs/docs/architecture.md +9 -4
- package/references/official-docs/docs/architecture.zh.md +9 -4
- package/references/official-docs/docs/capability-seams.i18n.yaml +2 -2
- package/references/official-docs/docs/capability-seams.md +8 -1
- package/references/official-docs/docs/capability-seams.zh.md +8 -1
- package/references/official-docs/docs/config-catalog.i18n.yaml +2 -2
- package/references/official-docs/docs/config-catalog.md +104 -68
- package/references/official-docs/docs/config-catalog.zh.md +101 -65
- package/references/official-docs/docs/cookbook/adding-a-package.i18n.yaml +2 -2
- package/references/official-docs/docs/cookbook/adding-a-package.md +1 -1
- package/references/official-docs/docs/cookbook/adding-a-package.zh.md +1 -1
- package/references/official-docs/docs/cookbook/extension-cookbook.i18n.yaml +2 -2
- package/references/official-docs/docs/cookbook/extension-cookbook.md +12 -10
- package/references/official-docs/docs/cookbook/extension-cookbook.zh.md +12 -10
- package/references/official-docs/docs/deepseek-llm-api-wire-extensions.i18n.yaml +2 -2
- package/references/official-docs/docs/deepseek-llm-api-wire-extensions.md +16 -12
- package/references/official-docs/docs/deepseek-llm-api-wire-extensions.zh.md +16 -12
- package/references/official-docs/docs/event-producer-consumer.i18n.yaml +2 -2
- package/references/official-docs/docs/event-producer-consumer.md +30 -29
- package/references/official-docs/docs/event-producer-consumer.zh.md +35 -34
- package/references/official-docs/docs/module-graph.i18n.yaml +2 -2
- package/references/official-docs/docs/module-graph.md +214 -360
- package/references/official-docs/docs/module-graph.zh.md +214 -360
- package/references/official-docs/docs/persistence-catalog.i18n.yaml +2 -2
- package/references/official-docs/docs/persistence-catalog.md +74 -64
- package/references/official-docs/docs/persistence-catalog.zh.md +72 -62
- package/references/official-docs/docs/subsystems/agent-team.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/agent-team.md +4 -3
- package/references/official-docs/docs/subsystems/agent-team.zh.md +4 -3
- package/references/official-docs/docs/subsystems/attachment.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/attachment.md +157 -4
- package/references/official-docs/docs/subsystems/attachment.zh.md +157 -4
- package/references/official-docs/docs/subsystems/code-runtime.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/code-runtime.md +7 -3
- package/references/official-docs/docs/subsystems/code-runtime.zh.md +7 -3
- package/references/official-docs/docs/subsystems/commands.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/commands.md +25 -16
- package/references/official-docs/docs/subsystems/commands.zh.md +25 -16
- package/references/official-docs/docs/subsystems/compaction.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/compaction.md +9 -9
- package/references/official-docs/docs/subsystems/compaction.zh.md +9 -9
- package/references/official-docs/docs/subsystems/conversation.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/conversation.md +4 -4
- package/references/official-docs/docs/subsystems/conversation.zh.md +4 -4
- package/references/official-docs/docs/subsystems/core.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/core.md +66 -4
- package/references/official-docs/docs/subsystems/core.zh.md +66 -4
- package/references/official-docs/docs/subsystems/feedback.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/feedback.md +2 -2
- package/references/official-docs/docs/subsystems/feedback.zh.md +2 -2
- package/references/official-docs/docs/subsystems/llm-streaming.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/llm-streaming.md +23 -2
- package/references/official-docs/docs/subsystems/llm-streaming.zh.md +23 -2
- package/references/official-docs/docs/subsystems/persistence.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/persistence.md +183 -191
- package/references/official-docs/docs/subsystems/persistence.zh.md +183 -191
- package/references/official-docs/docs/subsystems/schedule.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/schedule.md +1 -1
- package/references/official-docs/docs/subsystems/schedule.zh.md +1 -1
- package/references/official-docs/docs/subsystems/session-projection.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/session-projection.md +40 -17
- package/references/official-docs/docs/subsystems/session-projection.zh.md +40 -17
- package/references/official-docs/docs/subsystems/session-query.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/session-query.md +19 -13
- package/references/official-docs/docs/subsystems/session-query.zh.md +19 -13
- package/references/official-docs/docs/subsystems/session-reference.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/session-reference.md +25 -1
- package/references/official-docs/docs/subsystems/session-reference.zh.md +25 -1
- package/references/official-docs/docs/subsystems/session-telemetry.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/session-telemetry.md +6 -5
- package/references/official-docs/docs/subsystems/session-telemetry.zh.md +6 -5
- package/references/official-docs/docs/subsystems/session-title.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/session-title.md +5 -5
- package/references/official-docs/docs/subsystems/session-title.zh.md +5 -5
- package/references/official-docs/docs/subsystems/session.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/session.md +143 -71
- package/references/official-docs/docs/subsystems/session.zh.md +143 -71
- package/references/official-docs/docs/subsystems/slots.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/slots.md +1 -0
- package/references/official-docs/docs/subsystems/slots.zh.md +1 -0
- package/references/official-docs/docs/subsystems/storage.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/storage.md +28 -5
- package/references/official-docs/docs/subsystems/storage.zh.md +28 -5
- package/references/official-docs/docs/subsystems/subagent.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/subagent.md +32 -88
- package/references/official-docs/docs/subsystems/subagent.zh.md +31 -87
- package/references/official-docs/docs/subsystems/token-meter.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/token-meter.md +2 -2
- package/references/official-docs/docs/subsystems/token-meter.zh.md +2 -2
- package/references/official-docs/docs/subsystems/web-client.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/web-client.md +1 -1
- package/references/official-docs/docs/subsystems/web-client.zh.md +1 -1
- package/references/official-docs/docs/subsystems/workspace.i18n.yaml +2 -2
- package/references/official-docs/docs/subsystems/workspace.md +8 -8
- package/references/official-docs/docs/subsystems/workspace.zh.md +8 -8
- package/references/official-docs/docs/testing.i18n.yaml +2 -2
- package/references/official-docs/docs/testing.md +2 -2
- package/references/official-docs/docs/testing.zh.md +2 -2
- package/references/official-docs/docs/tool-catalog.i18n.yaml +2 -2
- package/references/official-docs/docs/tool-catalog.md +9 -63
- package/references/official-docs/docs/tool-catalog.zh.md +8 -62
- package/references/official-docs/docs/user/guide/network-proxy.i18n.yaml +6 -0
- package/references/official-docs/docs/user/guide/network-proxy.md +85 -0
- package/references/official-docs/docs/user/guide/network-proxy.zh.md +85 -0
- package/references/official-docs/docs/user/guide/providers.i18n.yaml +2 -2
- package/references/official-docs/docs/user/guide/providers.md +70 -17
- package/references/official-docs/docs/user/guide/providers.zh.md +70 -17
- package/references/official-docs/docs/web-styling.i18n.yaml +2 -2
- package/references/official-docs/docs/web-styling.md +4 -0
- package/references/official-docs/docs/web-styling.zh.md +4 -0
- package/references/official-docs/packages/AGENTS.md +2 -2
- package/references/official-docs/website-docs.ts +8 -0
- package/templates/js/README.es.md +1 -1
- package/templates/js/README.hi.md +1 -1
- package/templates/js/README.md +1 -1
- package/templates/js/README.pt.md +1 -1
- package/templates/js/README.zh.md +1 -1
- package/templates/ts/README.es.md +1 -1
- package/templates/ts/README.hi.md +1 -1
- package/templates/ts/README.md +1 -1
- package/templates/ts/README.pt.md +1 -1
- package/templates/ts/README.zh.md +1 -1
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
# Durable
|
|
1
|
+
# Durable Attachments
|
|
2
2
|
|
|
3
3
|
English | [中文](attachment.zh.md)
|
|
4
4
|
|
|
5
|
-
The attachment seam separates binary image ownership from the session log. A producer gives
|
|
5
|
+
The attachment seam separates binary image and generic-file ownership from the session log. A producer gives bytes to [`ctx.attachments`](#ctxattachments--attachmentstore-abstract-seam); the service publishes an immutable content-addressed reference only after the object is durable. Session events and model-visible attachment blocks contain that reference and metadata, never a browser object URL, host temporary path, provider URL, or base64 payload. The independent [`ctx.fileUploads`](#ctxfileuploads--fileuploads) service binds browser file transfers and staged receipts to the receiving Agent.
|
|
6
6
|
|
|
7
|
-
Unsent browser drafts may stay in memory and native clients may stage them in operating-system temporary storage. Once the host accepts a user message, its images move below `<DSH_HOME>/attachments/v1` before the user event is appended. Structured model image output follows the same persist-before-event rule.
|
|
7
|
+
Unsent browser drafts may stay in memory and native clients may stage them in operating-system temporary storage. Browser generic files become durable before they receive a staged prompt receipt. Once the host accepts a user message, its images move below `<DSH_HOME>/attachments/v1` before the user event is appended. Structured model image output follows the same persist-before-event rule.
|
|
8
8
|
|
|
9
9
|
Source: [`packages/attachment/attachment/src/types.ts`](../../packages/attachment/attachment/src/types.ts)
|
|
10
10
|
|
|
@@ -62,6 +62,38 @@ The reference records intrinsic dimensions and encoded length so clients can lay
|
|
|
62
62
|
|
|
63
63
|
## Commit and verified-read payloads
|
|
64
64
|
|
|
65
|
+
```ts type-equiv
|
|
66
|
+
/**
|
|
67
|
+
* Browser-submitted prompt content accepted by Host prompt endpoints; the
|
|
68
|
+
* accepting Host promotes image parts to durable references through
|
|
69
|
+
* `ctx.attachments.admitPromptContent()` before any message is created, so a wire caller can
|
|
70
|
+
* never cite an attachment it did not upload.
|
|
71
|
+
*/
|
|
72
|
+
type PromptContentPart =
|
|
73
|
+
| { readonly type: 'text'; readonly text: string }
|
|
74
|
+
| {
|
|
75
|
+
readonly type: 'image'
|
|
76
|
+
readonly mediaType: ImageMediaType
|
|
77
|
+
readonly data: string
|
|
78
|
+
readonly name?: string
|
|
79
|
+
}
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
```ts type-equiv
|
|
83
|
+
/** Host prompt content whose file receipts are resolved and whose image bytes await admission. */
|
|
84
|
+
type AttachmentAdmissionPart =
|
|
85
|
+
| PromptContentPart
|
|
86
|
+
| { readonly type: 'file'; readonly attachment: FileAttachmentRef }
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
```ts type-equiv
|
|
90
|
+
/** Host-admitted prompt content with every attachment represented by its durable reference. */
|
|
91
|
+
type AdmittedPromptContentPart =
|
|
92
|
+
| { readonly type: 'text'; readonly text: string }
|
|
93
|
+
| { readonly type: 'image'; readonly attachment: ImageAttachmentRef }
|
|
94
|
+
| { readonly type: 'file'; readonly attachment: FileAttachmentRef }
|
|
95
|
+
```
|
|
96
|
+
|
|
65
97
|
```ts type-equiv
|
|
66
98
|
/** Base64-encoded image upload accompanying one wire request. */
|
|
67
99
|
interface EncodedImageAttachment {
|
|
@@ -125,7 +157,7 @@ interface RequestImageAttachment {
|
|
|
125
157
|
}
|
|
126
158
|
```
|
|
127
159
|
|
|
128
|
-
`saveImage()` prepares and atomically commits a provider-independent normalized attachment before returning its `ImageAttachmentRef`. `saveImages()` prepares every validated attachment once before publishing the batch, so validation rejection leaves no partial objects and publication does not repeat decoding or quality selection. `
|
|
160
|
+
`saveImage()` prepares and atomically commits a provider-independent normalized attachment before returning its `ImageAttachmentRef`. `saveImages()` prepares every validated attachment once before publishing the batch, so validation rejection leaves no partial objects and publication does not repeat decoding or quality selection. `admitPromptContent()` accepts the complete ordered Host prompt after file receipt resolution, replaces base64 image uploads with durable references, and passes durable file references unchanged. `admitEncodedImages()` supports other wire entries and delegates count, aggregate-byte, and ordered batch admission to `saveImages()`. `admitEncodedFile()` gives encoded protocol adapters the same service-owned canonical-base64 admission, and `isAttachmentError()` lets those adapters recognize stable attachment failures without importing implementation helpers. `readImage()` verifies a normalized attachment from an authorized session path. `imageHostPath()` exposes only the provider-owned host object location; it does not decide whether the current tool execution world can read it. `readImageRequest()` derives and caches one deterministic request version under an exact route pixel and byte budget. That version contains encoded bytes and metadata but no execution-world path. New entries are fully decoded before publication, while cache hits use a bounded metadata probe. Callers use `Promise.all` over the singular method when they need an ordered batch. The local implementation lazily encodes preferred candidates, singleflights equal request identities, lets each waiter cancel independently, stops shared work when no waiter remains, and bounds all transforms with its instance-level limiter, which defaults to two simultaneous transformations. The service is retention-neutral: resumed and forked sessions may share objects, so reference-aware garbage collection is deferred rather than tied to one session's deletion.
|
|
129
161
|
|
|
130
162
|
<!-- BEGIN GENERATED cordis-surface (gen-cordis-catalog.ts) — do not edit between markers -->
|
|
131
163
|
|
|
@@ -157,6 +189,30 @@ abstract validateImage(input: SaveImageAttachment): Promise<void>
|
|
|
157
189
|
*/
|
|
158
190
|
async saveImages(inputs: readonly SaveImageAttachment[]): Promise<readonly ImageAttachmentRef[]>
|
|
159
191
|
|
|
192
|
+
/**
|
|
193
|
+
* Admit one Host prompt and replace each uploaded image with its durable reference.
|
|
194
|
+
* Text and durable file references pass through unchanged. A prompt without image parts performs no storage operation.
|
|
195
|
+
* @param content - prompt parts in message order after file receipt resolution.
|
|
196
|
+
* @returns admitted prompt parts in the same order as `content`.
|
|
197
|
+
* @throws AttachmentError when the image batch is refused.
|
|
198
|
+
*/
|
|
199
|
+
async admitPromptContent( content: readonly AttachmentAdmissionPart[], ): Promise<AdmittedPromptContentPart[]>
|
|
200
|
+
|
|
201
|
+
/**
|
|
202
|
+
* Decode and durably commit one canonical base64 file upload.
|
|
203
|
+
* @param input - canonical base64 bytes and optional display name.
|
|
204
|
+
* @returns the durable content-addressed file reference.
|
|
205
|
+
* @throws AttachmentError when the encoding or storage operation is refused.
|
|
206
|
+
*/
|
|
207
|
+
admitEncodedFile(input: EncodedFileAttachment): Promise<FileAttachmentRef>
|
|
208
|
+
|
|
209
|
+
/**
|
|
210
|
+
* Identify a failure emitted by this attachment capability by its stable code.
|
|
211
|
+
* @param error - value caught from an attachment operation.
|
|
212
|
+
* @returns whether the value is an attachment failure.
|
|
213
|
+
*/
|
|
214
|
+
isAttachmentError(error: unknown): error is AttachmentError
|
|
215
|
+
|
|
160
216
|
/**
|
|
161
217
|
* Validate and durably commit one image before its owning session event is appended.
|
|
162
218
|
* The returned reference describes the persisted normalized image. When
|
|
@@ -184,6 +240,43 @@ abstract readImage(ref: ImageAttachmentRef, signal?: AbortSignal): Promise<Store
|
|
|
184
240
|
*/
|
|
185
241
|
imageHostPath(ref: ImageAttachmentRef): string | undefined
|
|
186
242
|
|
|
243
|
+
/**
|
|
244
|
+
* Durably commit one file byte-for-byte before its owning session event is
|
|
245
|
+
* appended. Files carry no admission limits: any byte content and length is
|
|
246
|
+
* accepted, and the stored object is the exact submitted bytes. Backends
|
|
247
|
+
* without verbatim file storage keep this default rejection.
|
|
248
|
+
* @param input - exact bytes and optional display name.
|
|
249
|
+
* @returns the durable content-addressed file reference.
|
|
250
|
+
*/
|
|
251
|
+
saveFile(input: SaveFileAttachment): Promise<FileAttachmentRef>
|
|
252
|
+
|
|
253
|
+
/**
|
|
254
|
+
* Durably commit one file byte-for-byte from bounded chunks. Providers must
|
|
255
|
+
* apply backpressure and must not collect the complete file in memory.
|
|
256
|
+
* Backends without streamed verbatim storage keep this default rejection.
|
|
257
|
+
* @param input - ordered exact bytes, optional cancellation, and display name.
|
|
258
|
+
* @returns the durable content-addressed file reference.
|
|
259
|
+
*/
|
|
260
|
+
saveFileStream(input: SaveFileStreamAttachment): Promise<FileAttachmentRef>
|
|
261
|
+
|
|
262
|
+
/**
|
|
263
|
+
* Read and verify one verbatim stored file as bounded chunks. Providers must
|
|
264
|
+
* not collect the complete file in memory. Backends without verbatim file
|
|
265
|
+
* reads keep this default rejection.
|
|
266
|
+
* @param ref - durable reference from the session log.
|
|
267
|
+
* @param signal - optional cancellation for backend reads and verification work.
|
|
268
|
+
* @returns exact file bytes in order; integrity failures reject the iteration.
|
|
269
|
+
*/
|
|
270
|
+
async *readFileStream( ref: FileAttachmentRef, signal?: AbortSignal, ): AsyncIterable<Uint8Array>
|
|
271
|
+
|
|
272
|
+
/**
|
|
273
|
+
* Locate the verbatim stored file object in the harness host filesystem.
|
|
274
|
+
* @param ref - durable file reference.
|
|
275
|
+
* @returns an absolute host path, or undefined when this backend is not host-file-backed.
|
|
276
|
+
* @throws an AttachmentError when the durable reference is invalid.
|
|
277
|
+
*/
|
|
278
|
+
fileHostPath(ref: FileAttachmentRef): string | undefined
|
|
279
|
+
|
|
187
280
|
/**
|
|
188
281
|
* Generate or read one deterministic model-request version from the stored normalized image.
|
|
189
282
|
* @param ref - durable provider-independent normalized attachment reference.
|
|
@@ -195,4 +288,64 @@ readImageRequest( ref: ImageAttachmentRef, policy: ImageRequestPolicy, signal?:
|
|
|
195
288
|
```
|
|
196
289
|
|
|
197
290
|
Source: [`packages/attachment/attachment/src/index.ts`](../../packages/attachment/attachment/src/index.ts)
|
|
291
|
+
|
|
292
|
+
<a id="ctxfileuploads--fileuploads"></a>
|
|
293
|
+
|
|
294
|
+
### `ctx.fileUploads` — `FileUploads`
|
|
295
|
+
|
|
296
|
+
Host service owning upload storage and Agent-scoped staged receipts.
|
|
297
|
+
|
|
298
|
+
```ts cordis-catalog
|
|
299
|
+
/**
|
|
300
|
+
* Register the ordinary-Session resolver used when a raw upload addresses a cold Session.
|
|
301
|
+
* @param resolve - resolver that returns the exact live Agent or throws a Remote error.
|
|
302
|
+
* @returns disposer removing this resolver.
|
|
303
|
+
*/
|
|
304
|
+
registerAgentResolver(resolve: AgentResolver): () => void
|
|
305
|
+
|
|
306
|
+
/**
|
|
307
|
+
* Persist one encoded upload and stage it under the Agent receiver selected by Typert.
|
|
308
|
+
* @param agent - receiving Agent resolved from the Remote Agent scope.
|
|
309
|
+
* @param request - canonical base64 bytes and optional display name.
|
|
310
|
+
* @param signal - caller cancellation before storage begins.
|
|
311
|
+
* @returns the staged receipt and durable file reference.
|
|
312
|
+
*/
|
|
313
|
+
@Remote('upload') upload(agent: Agent, request: EncodedFileUploadRequest, signal: AbortSignal): Promise<FileUploadValue>
|
|
314
|
+
|
|
315
|
+
/**
|
|
316
|
+
* Persist raw chunks for one Session without aggregating the upload.
|
|
317
|
+
* @param request - Session identity, ordered bytes, cancellation, and optional display name.
|
|
318
|
+
* @returns the staged receipt and durable file reference.
|
|
319
|
+
*/
|
|
320
|
+
async uploadStream(request: { readonly sessionId: SessionId readonly data: AsyncIterable<Uint8Array> readonly signal?: AbortSignal readonly name?: string }): Promise<FileUploadValue>
|
|
321
|
+
|
|
322
|
+
/**
|
|
323
|
+
* Resolve one staged receipt inside its receiving Agent scope.
|
|
324
|
+
* @param agent - receiving Agent.
|
|
325
|
+
* @param receiptId - opaque receipt minted for one completed upload.
|
|
326
|
+
* @returns durable file reference, or `undefined` for an unknown or foreign receipt.
|
|
327
|
+
*/
|
|
328
|
+
resolve(agent: Agent, receiptId: FileUploadReceiptId): FileAttachmentRef | undefined
|
|
329
|
+
|
|
330
|
+
/**
|
|
331
|
+
* Bind receipts while one prompt enters an Agent inbox.
|
|
332
|
+
* Disposal restores every prior binding unless the caller commits successful delivery.
|
|
333
|
+
* @param agent - receiving Agent.
|
|
334
|
+
* @param receiptIds - distinct staged receipts referenced by the prompt.
|
|
335
|
+
* @param requestId - prompt identity later observed in queue or history.
|
|
336
|
+
* @returns binding kept after commit until queue or history observation retires its receipts.
|
|
337
|
+
*/
|
|
338
|
+
bindPrompt( agent: Agent, receiptIds: readonly FileUploadReceiptId[], requestId: string, ): PromptFileBinding
|
|
339
|
+
|
|
340
|
+
/**
|
|
341
|
+
* Retire every receipt accepted by one removed queue occurrence.
|
|
342
|
+
* @param agent - receiving Agent.
|
|
343
|
+
* @param requestId - prompt identity carried by the queue occurrence.
|
|
344
|
+
*/
|
|
345
|
+
retirePrompt(agent: Agent, requestId: string): void
|
|
346
|
+
```
|
|
347
|
+
|
|
348
|
+
Types: [Agent](core.md) · [SessionId](core.md)
|
|
349
|
+
|
|
350
|
+
Source: [`packages/client/file-upload/src/index.ts`](../../packages/client/file-upload/src/index.ts)
|
|
198
351
|
<!-- END GENERATED cordis-surface -->
|
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
#
|
|
1
|
+
# 持久附件
|
|
2
2
|
|
|
3
3
|
[English](attachment.md) | 中文
|
|
4
4
|
|
|
5
|
-
附件 seam
|
|
5
|
+
附件 seam 将二进制图片和通用文件的所有权与会话日志分离。生产方把字节交给 [`ctx.attachments`](#ctxattachments--attachmentstore-abstract-seam);只有对象完成持久化后,该服务才会发布不可变的内容寻址引用。会话事件和模型可见的附件块包含该引用及其元数据,绝不包含浏览器对象 URL、宿主临时路径、提供方 URL 或 base64 数据。独立的 [`ctx.fileUploads`](#ctxfileuploads--fileuploads) 服务把浏览器文件传输与暂存凭证绑定到接收方 Agent。
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
未发送的浏览器草稿可以保留在内存中,原生客户端也可以将其暂存于操作系统临时存储。浏览器通用文件取得暂存 prompt 凭证前会完成持久化。宿主接受用户消息后,会先把消息中的图片移到 `<DSH_HOME>/attachments/v1` 下,再追加用户事件。结构化模型图片输出遵循同样的先持久化、后追加事件规则。
|
|
8
8
|
|
|
9
9
|
来源:[`packages/attachment/attachment/src/types.ts`](../../packages/attachment/attachment/src/types.ts)
|
|
10
10
|
|
|
@@ -62,6 +62,38 @@ interface ImageAttachmentLimits {
|
|
|
62
62
|
|
|
63
63
|
## 提交与经校验读取的数据
|
|
64
64
|
|
|
65
|
+
```ts type-equiv
|
|
66
|
+
/**
|
|
67
|
+
* Browser-submitted prompt content accepted by Host prompt endpoints; the
|
|
68
|
+
* accepting Host promotes image parts to durable references through
|
|
69
|
+
* `ctx.attachments.admitPromptContent()` before any message is created, so a wire caller can
|
|
70
|
+
* never cite an attachment it did not upload.
|
|
71
|
+
*/
|
|
72
|
+
type PromptContentPart =
|
|
73
|
+
| { readonly type: 'text'; readonly text: string }
|
|
74
|
+
| {
|
|
75
|
+
readonly type: 'image'
|
|
76
|
+
readonly mediaType: ImageMediaType
|
|
77
|
+
readonly data: string
|
|
78
|
+
readonly name?: string
|
|
79
|
+
}
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
```ts type-equiv
|
|
83
|
+
/** Host prompt content whose file receipts are resolved and whose image bytes await admission. */
|
|
84
|
+
type AttachmentAdmissionPart =
|
|
85
|
+
| PromptContentPart
|
|
86
|
+
| { readonly type: 'file'; readonly attachment: FileAttachmentRef }
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
```ts type-equiv
|
|
90
|
+
/** Host-admitted prompt content with every attachment represented by its durable reference. */
|
|
91
|
+
type AdmittedPromptContentPart =
|
|
92
|
+
| { readonly type: 'text'; readonly text: string }
|
|
93
|
+
| { readonly type: 'image'; readonly attachment: ImageAttachmentRef }
|
|
94
|
+
| { readonly type: 'file'; readonly attachment: FileAttachmentRef }
|
|
95
|
+
```
|
|
96
|
+
|
|
65
97
|
```ts type-equiv
|
|
66
98
|
/** Base64-encoded image upload accompanying one wire request. */
|
|
67
99
|
interface EncodedImageAttachment {
|
|
@@ -125,7 +157,7 @@ interface RequestImageAttachment {
|
|
|
125
157
|
}
|
|
126
158
|
```
|
|
127
159
|
|
|
128
|
-
`saveImage()` 准备并原子提交提供方无关的规范化附件,然后直接返回 `ImageAttachmentRef`。`saveImages()` 在发布批次前为每个成员各准备一次经过验证的附件,因此校验拒绝不会留下部分对象,发布也不会重复解码或选择质量。`
|
|
160
|
+
`saveImage()` 准备并原子提交提供方无关的规范化附件,然后直接返回 `ImageAttachmentRef`。`saveImages()` 在发布批次前为每个成员各准备一次经过验证的附件,因此校验拒绝不会留下部分对象,发布也不会重复解码或选择质量。`admitPromptContent()` 在文件凭证解析后接收完整且有序的 Host prompt,把 base64 图片上传替换为持久引用,并让持久文件引用原样通过。`admitEncodedImages()` 支持其他 wire 入口,把张数、聚合字节和有序批量准入交给 `saveImages()`。`admitEncodedFile()` 让编码协议适配器使用服务拥有的规范 base64 准入,`isAttachmentError()` 让这些适配器无需导入实现辅助函数即可识别稳定的附件错误。`readImage()` 校验来自已授权会话路径的规范化附件。`imageHostPath()` 只公开提供方所持对象的宿主位置,不判断当前工具执行环境能否读取它。`readImageRequest()` 按确切路由的像素和字节预算派生并缓存确定性请求版本。该版本包含编码字节和元数据,不包含执行环境路径。新条目在发布前完整解码,缓存命中只做有界元数据探测。调用方需要有序批次时,对单数方法使用 `Promise.all`。本地实现按需编码首选候选、合并相同请求身份的并发任务、允许每个等待方单独取消、没有等待方时停止共享任务,并通过实例级限流器限制全部变换,默认同时执行两项。该服务不规定保留策略:恢复和 fork 后的会话可能共享对象,因此基于引用的垃圾回收会延期实现,不与单个会话的删除绑定。
|
|
129
161
|
|
|
130
162
|
<!-- BEGIN GENERATED cordis-surface (gen-cordis-catalog.ts) — do not edit between markers -->
|
|
131
163
|
|
|
@@ -157,6 +189,30 @@ abstract validateImage(input: SaveImageAttachment): Promise<void>
|
|
|
157
189
|
*/
|
|
158
190
|
async saveImages(inputs: readonly SaveImageAttachment[]): Promise<readonly ImageAttachmentRef[]>
|
|
159
191
|
|
|
192
|
+
/**
|
|
193
|
+
* Admit one Host prompt and replace each uploaded image with its durable reference.
|
|
194
|
+
* Text and durable file references pass through unchanged. A prompt without image parts performs no storage operation.
|
|
195
|
+
* @param content - prompt parts in message order after file receipt resolution.
|
|
196
|
+
* @returns admitted prompt parts in the same order as `content`.
|
|
197
|
+
* @throws AttachmentError when the image batch is refused.
|
|
198
|
+
*/
|
|
199
|
+
async admitPromptContent( content: readonly AttachmentAdmissionPart[], ): Promise<AdmittedPromptContentPart[]>
|
|
200
|
+
|
|
201
|
+
/**
|
|
202
|
+
* Decode and durably commit one canonical base64 file upload.
|
|
203
|
+
* @param input - canonical base64 bytes and optional display name.
|
|
204
|
+
* @returns the durable content-addressed file reference.
|
|
205
|
+
* @throws AttachmentError when the encoding or storage operation is refused.
|
|
206
|
+
*/
|
|
207
|
+
admitEncodedFile(input: EncodedFileAttachment): Promise<FileAttachmentRef>
|
|
208
|
+
|
|
209
|
+
/**
|
|
210
|
+
* Identify a failure emitted by this attachment capability by its stable code.
|
|
211
|
+
* @param error - value caught from an attachment operation.
|
|
212
|
+
* @returns whether the value is an attachment failure.
|
|
213
|
+
*/
|
|
214
|
+
isAttachmentError(error: unknown): error is AttachmentError
|
|
215
|
+
|
|
160
216
|
/**
|
|
161
217
|
* Validate and durably commit one image before its owning session event is appended.
|
|
162
218
|
* The returned reference describes the persisted normalized image. When
|
|
@@ -184,6 +240,43 @@ abstract readImage(ref: ImageAttachmentRef, signal?: AbortSignal): Promise<Store
|
|
|
184
240
|
*/
|
|
185
241
|
imageHostPath(ref: ImageAttachmentRef): string | undefined
|
|
186
242
|
|
|
243
|
+
/**
|
|
244
|
+
* Durably commit one file byte-for-byte before its owning session event is
|
|
245
|
+
* appended. Files carry no admission limits: any byte content and length is
|
|
246
|
+
* accepted, and the stored object is the exact submitted bytes. Backends
|
|
247
|
+
* without verbatim file storage keep this default rejection.
|
|
248
|
+
* @param input - exact bytes and optional display name.
|
|
249
|
+
* @returns the durable content-addressed file reference.
|
|
250
|
+
*/
|
|
251
|
+
saveFile(input: SaveFileAttachment): Promise<FileAttachmentRef>
|
|
252
|
+
|
|
253
|
+
/**
|
|
254
|
+
* Durably commit one file byte-for-byte from bounded chunks. Providers must
|
|
255
|
+
* apply backpressure and must not collect the complete file in memory.
|
|
256
|
+
* Backends without streamed verbatim storage keep this default rejection.
|
|
257
|
+
* @param input - ordered exact bytes, optional cancellation, and display name.
|
|
258
|
+
* @returns the durable content-addressed file reference.
|
|
259
|
+
*/
|
|
260
|
+
saveFileStream(input: SaveFileStreamAttachment): Promise<FileAttachmentRef>
|
|
261
|
+
|
|
262
|
+
/**
|
|
263
|
+
* Read and verify one verbatim stored file as bounded chunks. Providers must
|
|
264
|
+
* not collect the complete file in memory. Backends without verbatim file
|
|
265
|
+
* reads keep this default rejection.
|
|
266
|
+
* @param ref - durable reference from the session log.
|
|
267
|
+
* @param signal - optional cancellation for backend reads and verification work.
|
|
268
|
+
* @returns exact file bytes in order; integrity failures reject the iteration.
|
|
269
|
+
*/
|
|
270
|
+
async *readFileStream( ref: FileAttachmentRef, signal?: AbortSignal, ): AsyncIterable<Uint8Array>
|
|
271
|
+
|
|
272
|
+
/**
|
|
273
|
+
* Locate the verbatim stored file object in the harness host filesystem.
|
|
274
|
+
* @param ref - durable file reference.
|
|
275
|
+
* @returns an absolute host path, or undefined when this backend is not host-file-backed.
|
|
276
|
+
* @throws an AttachmentError when the durable reference is invalid.
|
|
277
|
+
*/
|
|
278
|
+
fileHostPath(ref: FileAttachmentRef): string | undefined
|
|
279
|
+
|
|
187
280
|
/**
|
|
188
281
|
* Generate or read one deterministic model-request version from the stored normalized image.
|
|
189
282
|
* @param ref - durable provider-independent normalized attachment reference.
|
|
@@ -195,4 +288,64 @@ readImageRequest( ref: ImageAttachmentRef, policy: ImageRequestPolicy, signal?:
|
|
|
195
288
|
```
|
|
196
289
|
|
|
197
290
|
Source: [`packages/attachment/attachment/src/index.ts`](../../packages/attachment/attachment/src/index.ts)
|
|
291
|
+
|
|
292
|
+
<a id="ctxfileuploads--fileuploads"></a>
|
|
293
|
+
|
|
294
|
+
### `ctx.fileUploads` — `FileUploads`
|
|
295
|
+
|
|
296
|
+
Host service owning upload storage and Agent-scoped staged receipts.
|
|
297
|
+
|
|
298
|
+
```ts cordis-catalog
|
|
299
|
+
/**
|
|
300
|
+
* Register the ordinary-Session resolver used when a raw upload addresses a cold Session.
|
|
301
|
+
* @param resolve - resolver that returns the exact live Agent or throws a Remote error.
|
|
302
|
+
* @returns disposer removing this resolver.
|
|
303
|
+
*/
|
|
304
|
+
registerAgentResolver(resolve: AgentResolver): () => void
|
|
305
|
+
|
|
306
|
+
/**
|
|
307
|
+
* Persist one encoded upload and stage it under the Agent receiver selected by Typert.
|
|
308
|
+
* @param agent - receiving Agent resolved from the Remote Agent scope.
|
|
309
|
+
* @param request - canonical base64 bytes and optional display name.
|
|
310
|
+
* @param signal - caller cancellation before storage begins.
|
|
311
|
+
* @returns the staged receipt and durable file reference.
|
|
312
|
+
*/
|
|
313
|
+
@Remote('upload') upload(agent: Agent, request: EncodedFileUploadRequest, signal: AbortSignal): Promise<FileUploadValue>
|
|
314
|
+
|
|
315
|
+
/**
|
|
316
|
+
* Persist raw chunks for one Session without aggregating the upload.
|
|
317
|
+
* @param request - Session identity, ordered bytes, cancellation, and optional display name.
|
|
318
|
+
* @returns the staged receipt and durable file reference.
|
|
319
|
+
*/
|
|
320
|
+
async uploadStream(request: { readonly sessionId: SessionId readonly data: AsyncIterable<Uint8Array> readonly signal?: AbortSignal readonly name?: string }): Promise<FileUploadValue>
|
|
321
|
+
|
|
322
|
+
/**
|
|
323
|
+
* Resolve one staged receipt inside its receiving Agent scope.
|
|
324
|
+
* @param agent - receiving Agent.
|
|
325
|
+
* @param receiptId - opaque receipt minted for one completed upload.
|
|
326
|
+
* @returns durable file reference, or `undefined` for an unknown or foreign receipt.
|
|
327
|
+
*/
|
|
328
|
+
resolve(agent: Agent, receiptId: FileUploadReceiptId): FileAttachmentRef | undefined
|
|
329
|
+
|
|
330
|
+
/**
|
|
331
|
+
* Bind receipts while one prompt enters an Agent inbox.
|
|
332
|
+
* Disposal restores every prior binding unless the caller commits successful delivery.
|
|
333
|
+
* @param agent - receiving Agent.
|
|
334
|
+
* @param receiptIds - distinct staged receipts referenced by the prompt.
|
|
335
|
+
* @param requestId - prompt identity later observed in queue or history.
|
|
336
|
+
* @returns binding kept after commit until queue or history observation retires its receipts.
|
|
337
|
+
*/
|
|
338
|
+
bindPrompt( agent: Agent, receiptIds: readonly FileUploadReceiptId[], requestId: string, ): PromptFileBinding
|
|
339
|
+
|
|
340
|
+
/**
|
|
341
|
+
* Retire every receipt accepted by one removed queue occurrence.
|
|
342
|
+
* @param agent - receiving Agent.
|
|
343
|
+
* @param requestId - prompt identity carried by the queue occurrence.
|
|
344
|
+
*/
|
|
345
|
+
retirePrompt(agent: Agent, requestId: string): void
|
|
346
|
+
```
|
|
347
|
+
|
|
348
|
+
Types: [Agent](core.zh.md) · [SessionId](core.zh.md)
|
|
349
|
+
|
|
350
|
+
Source: [`packages/client/file-upload/src/index.ts`](../../packages/client/file-upload/src/index.ts)
|
|
198
351
|
<!-- END GENERATED cordis-surface -->
|
|
@@ -2,5 +2,5 @@
|
|
|
2
2
|
# side as of the last confirmed-consistent state. Both languages carry equal authority;
|
|
3
3
|
# after editing either side, bring the other along and re-record with:
|
|
4
4
|
# pnpm run verify-translation-pairing --write docs/subsystems/code-runtime.md
|
|
5
|
-
code-runtime.md:
|
|
6
|
-
code-runtime.zh.md:
|
|
5
|
+
code-runtime.md: 4c7fce42c363c7735d03fcb723bb5c5f1af12bb9
|
|
6
|
+
code-runtime.zh.md: f01e3bccef165a5aeb9130ac983b2e8ff63a81b0
|
|
@@ -52,7 +52,11 @@ interface CodeRunResult {
|
|
|
52
52
|
* rendered string; a failed or value-less run leaves this absent.
|
|
53
53
|
*/
|
|
54
54
|
value?: CodeJsonValue
|
|
55
|
-
/**
|
|
55
|
+
/**
|
|
56
|
+
* Captured text. Each source channel preserves emission order; interleaving
|
|
57
|
+
* across independent channels is backend-dependent. Bounded only as part of
|
|
58
|
+
* the outer result.
|
|
59
|
+
*/
|
|
56
60
|
logs: string[]
|
|
57
61
|
/** Present iff the run failed; see {@link CodeRunFailure} for the taxonomy. */
|
|
58
62
|
error?: CodeRunFailure
|
|
@@ -131,7 +135,7 @@ type CodeBindingFunction = (args: unknown) => Promise<CodeJsonValue>
|
|
|
131
135
|
|
|
132
136
|
## Captured output and the failure taxonomy
|
|
133
137
|
|
|
134
|
-
Logs are plain strings
|
|
138
|
+
Logs are plain strings. Each source channel preserves emission order, while interleaving across independent channels is backend-dependent because channel metadata is not part of the seam. The runtime captures the program's console and stream output, and consumers render only the text. Implementations cap the serialized outer log-array plus completion-value or failure-message payload; fixed result-envelope syntax and consumer presentation whitespace are not part of that variable-payload ledger. Overflow is an explicit failure rather than in-band value substitution.
|
|
135
139
|
|
|
136
140
|
Failure kinds are **orthogonal outcomes reported independently** (per [defensive-patterns](../defensive-patterns.md)): a budget expiry is not an exception, an abort is not a timeout, and a substrate death (e.g. OOM) is neither:
|
|
137
141
|
|
|
@@ -158,7 +162,7 @@ interface CodeRunFailure {
|
|
|
158
162
|
|
|
159
163
|
## The service
|
|
160
164
|
|
|
161
|
-
`CodeRuntime` (`ctx.codeRuntime`, abstract — defined in [`packages/code-runtime/code-runtime/src/index.ts`](../../packages/code-runtime/code-runtime/src/index.ts)) is `run(request)` plus two readonly descriptors: `language` (what the program must be written in — `'typescript'` and `'python'` are the well-known values, those `dsh-tools` presents, and
|
|
165
|
+
`CodeRuntime` (`ctx.codeRuntime`, abstract — defined in [`packages/code-runtime/code-runtime/src/index.ts`](../../packages/code-runtime/code-runtime/src/index.ts)) is `run(request)` plus two readonly descriptors: `language` (what the program must be written in — `'typescript'` and `'python'` are the well-known values, those `dsh-tools` presents, the TypeScript backend released and the Python backend experimental and private (not published); a consumer generating language-specific presentation switches on it and fails loud on one it cannot present) and `isolation` (the execution substrate — `'worker-thread'`, `'process'`, `'container'`; a diagnostic label, **not a security claim**). Implementations must keep runs isolated from each other (no cross-run state) and dispose to quiescence: in-flight runs are terminated and awaited before teardown completes.
|
|
162
166
|
|
|
163
167
|
<!-- BEGIN GENERATED cordis-surface (gen-cordis-catalog.ts) — do not edit between markers -->
|
|
164
168
|
|
|
@@ -52,7 +52,11 @@ interface CodeRunResult {
|
|
|
52
52
|
* rendered string; a failed or value-less run leaves this absent.
|
|
53
53
|
*/
|
|
54
54
|
value?: CodeJsonValue
|
|
55
|
-
/**
|
|
55
|
+
/**
|
|
56
|
+
* Captured text. Each source channel preserves emission order; interleaving
|
|
57
|
+
* across independent channels is backend-dependent. Bounded only as part of
|
|
58
|
+
* the outer result.
|
|
59
|
+
*/
|
|
56
60
|
logs: string[]
|
|
57
61
|
/** Present iff the run failed; see {@link CodeRunFailure} for the taxonomy. */
|
|
58
62
|
error?: CodeRunFailure
|
|
@@ -131,7 +135,7 @@ type CodeBindingFunction = (args: unknown) => Promise<CodeJsonValue>
|
|
|
131
135
|
|
|
132
136
|
## 捕获的输出与失败分类体系
|
|
133
137
|
|
|
134
|
-
|
|
138
|
+
日志是纯字符串。每个来源通道保留自身的发出顺序;由于通道元数据不属于 seam,相互独立的通道如何交错由后端决定。运行时捕获程序的 console 与流输出,Consumer 只渲染文本。实现会对序列化后的外层日志数组,以及完成值或失败消息的组合载荷设置上限;固定的结果封装语法与 Consumer 展示空白不计入这份可变载荷计量。超限会显式失败,而不会在值中插入替代内容。
|
|
135
139
|
|
|
136
140
|
失败类型是**正交的结果,独立报告**(见 [defensive-patterns](../defensive-patterns.zh.md)):预算耗尽不是异常,中止不是超时,基底崩溃(如 OOM)也不是二者中的任何一个:
|
|
137
141
|
|
|
@@ -158,7 +162,7 @@ interface CodeRunFailure {
|
|
|
158
162
|
|
|
159
163
|
## 服务
|
|
160
164
|
|
|
161
|
-
`CodeRuntime`(`ctx.codeRuntime`,抽象服务,定义于 [`packages/code-runtime/code-runtime/src/index.ts`](../../packages/code-runtime/code-runtime/src/index.ts))由 `run(request)` 加两个只读描述符组成:`language`(程序必须使用的语言,已知值为 `'typescript'` 与 `'python'`,即 `dsh-tools`
|
|
165
|
+
`CodeRuntime`(`ctx.codeRuntime`,抽象服务,定义于 [`packages/code-runtime/code-runtime/src/index.ts`](../../packages/code-runtime/code-runtime/src/index.ts))由 `run(request)` 加两个只读描述符组成:`language`(程序必须使用的语言,已知值为 `'typescript'` 与 `'python'`,即 `dsh-tools` 能呈现的那些,TypeScript 后端已发布、Python 后端为实验性且私有(未发布);生成语言相关展示的 Consumer 据此切换,遇到无法展示的语言时应显式报错)和 `isolation`(执行基底,`'worker-thread'`、`'process'`、`'container'`;仅为诊断标签,**不构成安全承诺**)。实现必须保证各次运行彼此隔离(无跨运行状态),并在 dispose(资源释放)时等待系统完全停稳:teardown 要等到所有进行中的运行均已终止并结算后才完成。
|
|
162
166
|
|
|
163
167
|
<!-- BEGIN GENERATED cordis-surface (gen-cordis-catalog.ts) — do not edit between markers -->
|
|
164
168
|
|
|
@@ -2,5 +2,5 @@
|
|
|
2
2
|
# side as of the last confirmed-consistent state. Both languages carry equal authority;
|
|
3
3
|
# after editing either side, bring the other along and re-record with:
|
|
4
4
|
# pnpm run verify-translation-pairing --write docs/subsystems/commands.md
|
|
5
|
-
commands.md:
|
|
6
|
-
commands.zh.md:
|
|
5
|
+
commands.md: 4705048e06796792d8e013450b72035b1f87315b
|
|
6
|
+
commands.zh.md: f3af9f6e81745514efd1e073868292a02f90dca8
|
|
@@ -8,7 +8,7 @@ Source: [`packages/interaction/commands/src/index.ts`](../../packages/interactio
|
|
|
8
8
|
|
|
9
9
|
## Input metadata
|
|
10
10
|
|
|
11
|
-
The service exposes one optional unstructured-input descriptor: a hint plus an
|
|
11
|
+
The service exposes one optional unstructured-input descriptor: a hint plus an attachment-acceptance flag. Command availability follows plugin composition: every adapter consuming the registry sees every effective definition.
|
|
12
12
|
|
|
13
13
|
```ts type-equiv
|
|
14
14
|
/** Immutable metadata for a command's optional unstructured input. */
|
|
@@ -16,13 +16,13 @@ interface CommandInputDescriptor {
|
|
|
16
16
|
/** Placeholder shown before the user supplies free-form input. */
|
|
17
17
|
readonly hint: string
|
|
18
18
|
/**
|
|
19
|
-
* Whether composer
|
|
20
|
-
* false = the executor rejects an invocation carrying
|
|
19
|
+
* Whether composer attachments may accompany an invocation. Absent or
|
|
20
|
+
* false = the executor rejects an invocation carrying attachments and capable
|
|
21
21
|
* composers refuse the submission before dispatch. A declaring command's
|
|
22
22
|
* handler receives the admitted durable blocks and owns every further
|
|
23
23
|
* grammar decision, including rejecting sub-commands that cannot use them.
|
|
24
24
|
*/
|
|
25
|
-
readonly
|
|
25
|
+
readonly attachments?: boolean
|
|
26
26
|
}
|
|
27
27
|
```
|
|
28
28
|
|
|
@@ -64,13 +64,13 @@ interface CommandInvocation {
|
|
|
64
64
|
/** Exact text following the registered command name, including separator whitespace. */
|
|
65
65
|
readonly rawInput: string
|
|
66
66
|
/**
|
|
67
|
-
* Durably admitted image blocks accompanying this invocation, in submission
|
|
68
|
-
* order; empty unless the definition declares `input.
|
|
67
|
+
* Durably admitted image and file blocks accompanying this invocation, in submission
|
|
68
|
+
* order; empty unless the definition declares `input.attachments`. The handler
|
|
69
69
|
* owns their model-visible use — the registry never schedules them itself —
|
|
70
70
|
* and a handler whose grammar cannot use them in this invocation returns an
|
|
71
71
|
* error so the dispatching composer retains the originals.
|
|
72
72
|
*/
|
|
73
|
-
readonly attachments: readonly ImageBlock[]
|
|
73
|
+
readonly attachments: readonly (ImageBlock | FileBlock)[]
|
|
74
74
|
/** Cancellation signal owned by the dispatching UI request. */
|
|
75
75
|
readonly signal: AbortSignal
|
|
76
76
|
}
|
|
@@ -83,7 +83,7 @@ type CommandResult =
|
|
|
83
83
|
readonly kind: 'success'
|
|
84
84
|
readonly text?: string
|
|
85
85
|
/** Earlier authoritative domain event that owns a richer presentation. */
|
|
86
|
-
readonly sourceEventSeq?:
|
|
86
|
+
readonly sourceEventSeq?: SessionSeq
|
|
87
87
|
}
|
|
88
88
|
| { readonly kind: 'error'; readonly text: string }
|
|
89
89
|
```
|
|
@@ -138,6 +138,13 @@ Human-command registry. Plain-context definitions are global; definitions regist
|
|
|
138
138
|
*/
|
|
139
139
|
register(definition: CommandDefinition): () => void
|
|
140
140
|
|
|
141
|
+
/**
|
|
142
|
+
* Register the sole authority that resolves staged file receipts for command submissions.
|
|
143
|
+
* @param resolver - Session-aware receipt resolver.
|
|
144
|
+
* @returns disposer that removes this exact resolver.
|
|
145
|
+
*/
|
|
146
|
+
registerFileReceiptResolver(resolver: CommandFileReceiptResolver): () => void
|
|
147
|
+
|
|
141
148
|
/**
|
|
142
149
|
* List the effective immutable command descriptors for one agent.
|
|
143
150
|
* @param agent - exact receiving agent and scoped-layer key.
|
|
@@ -166,23 +173,25 @@ find(agent: Agent, name: string): CommandDefinition | undefined
|
|
|
166
173
|
* handler-failure path is contained so the handler's own error stays the
|
|
167
174
|
* reported failure.
|
|
168
175
|
*
|
|
169
|
-
*
|
|
170
|
-
* command that does not declare `input.
|
|
171
|
-
* and an exceeded
|
|
172
|
-
* the handler runs
|
|
176
|
+
* Attachment admission is enforced here, not in the composer: attachments sent to a
|
|
177
|
+
* command that does not declare `input.attachments`, an absent attachment store,
|
|
178
|
+
* and an exceeded image limit each settle as an error result before
|
|
179
|
+
* the handler runs. Validation rejection starts no attachment writes;
|
|
180
|
+
* a storage failure can leave only unreachable content-addressed objects
|
|
181
|
+
* for deferred collection.
|
|
173
182
|
*
|
|
174
183
|
* @param agent - exact receiving agent.
|
|
175
184
|
* @param line - complete slash-command line.
|
|
176
|
-
* @param
|
|
177
|
-
* submission order; empty for a plain invocation.
|
|
185
|
+
* @param submittedAttachments - encoded images and staged file receipts accompanying the line,
|
|
186
|
+
* in submission order; empty for a plain invocation.
|
|
178
187
|
* @param signal - cancellation signal owned by the UI request.
|
|
179
188
|
* @returns the settled execution (result + lifecycle pairing id), or
|
|
180
189
|
* `undefined` when syntax or name does not resolve.
|
|
181
190
|
*/
|
|
182
|
-
@Remote async execute( agent: Agent, line: string,
|
|
191
|
+
@Remote async execute( agent: Agent, line: string, submittedAttachments: readonly CommandSubmitAttachment[], signal: AbortSignal, ): Promise<CommandExecution | undefined>
|
|
183
192
|
```
|
|
184
193
|
|
|
185
|
-
Types: [Agent](core.md)
|
|
194
|
+
Types: [Agent](core.md)
|
|
186
195
|
|
|
187
196
|
Source: [`packages/interaction/commands/src/index.ts`](../../packages/interaction/commands/src/index.ts)
|
|
188
197
|
|