@orkestrel/agent 0.0.21 → 0.0.22

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.
@@ -1,16 +1,26 @@
1
+ import { ArrayShape } from '@orkestrel/contract';
2
+ import { BooleanShape } from '@orkestrel/contract';
1
3
  import type { BudgetInterface } from '@orkestrel/budget';
4
+ import { ContractInterface } from '@orkestrel/contract';
5
+ import type { ContractShape } from '@orkestrel/contract';
2
6
  import type { ControllerInterface } from '@orkestrel/workflow';
3
7
  import type { DriverInterface } from '@orkestrel/database';
4
8
  import type { EmitterErrorHandler } from '@orkestrel/emitter';
5
9
  import type { EmitterHooks } from '@orkestrel/emitter';
6
10
  import type { EmitterInterface } from '@orkestrel/emitter';
7
11
  import type { FileInterface } from '@orkestrel/workspace';
8
- import type { JSONValue } from '@orkestrel/contract';
12
+ import { JSONShape } from '@orkestrel/contract';
13
+ import { JSONValue } from '@orkestrel/contract';
14
+ import { LiteralShape } from '@orkestrel/contract';
15
+ import { NumberShape } from '@orkestrel/contract';
16
+ import { ObjectShape } from '@orkestrel/contract';
17
+ import { OptionalShape } from '@orkestrel/contract';
9
18
  import type { QueueContext } from '@orkestrel/queue';
10
19
  import type { QueueInterface } from '@orkestrel/queue';
11
20
  import type { QueueStoreInterface } from '@orkestrel/queue';
12
21
  import type { RunnerInterface } from '@orkestrel/workflow';
13
22
  import type { SchedulerInterface } from '@orkestrel/workflow';
23
+ import { StringShape } from '@orkestrel/contract';
14
24
  import type { TableInterface } from '@orkestrel/database';
15
25
  import type { TokenUsage } from '@orkestrel/budget';
16
26
  import type { ToolCall } from '@orkestrel/tool';
@@ -18,6 +28,7 @@ import type { ToolDefinition } from '@orkestrel/tool';
18
28
  import type { ToolInterface } from '@orkestrel/tool';
19
29
  import type { ToolManagerInterface } from '@orkestrel/tool';
20
30
  import type { ToolResult } from '@orkestrel/tool';
31
+ import { UnionShape } from '@orkestrel/contract';
21
32
  import type { WorkspaceManagerInterface } from '@orkestrel/workspace';
22
33
 
23
34
  /**
@@ -711,6 +722,126 @@ export declare interface AgentOptions {
711
722
  readonly strict?: boolean;
712
723
  }
713
724
 
725
+ /**
726
+ * Implements bounded HTTP streaming and result assembly behind concrete wire seams.
727
+ *
728
+ * @remarks
729
+ * Every call owns its parser, splitter, deadline, and accumulation. Success bodies
730
+ * have no size limit. A qwen3 implicit-open reclassification corrects the final
731
+ * content while content deltas already yielded cannot be recalled. A subclass fills
732
+ * `name`, `frame`, `body`, `read`, and `finish`; the constructor takes the `split`
733
+ * and `strict` switches to control reasoning separation and settled-result requirements.
734
+ *
735
+ * @example Writing a provider for a new wire
736
+ * ```ts
737
+ * import type {
738
+ * ProviderIncrement,
739
+ * ProviderOptions,
740
+ * ProviderParserInterface,
741
+ * ProviderRequest,
742
+ * } from '@orkestrel/agent'
743
+ * import { AgentProvider } from '@orkestrel/agent'
744
+ *
745
+ * class TextFrame implements ProviderParserInterface<string> {
746
+ * parse(chunk: string): readonly string[] {
747
+ * return [chunk]
748
+ * }
749
+ * clear(): void {} // Raw text retains no framing state.
750
+ * }
751
+ *
752
+ * interface TextOptions extends ProviderOptions {
753
+ * readonly url: string
754
+ * }
755
+ *
756
+ * class TextProvider extends AgentProvider<string> {
757
+ * readonly name = 'text'
758
+ * constructor(options: TextOptions) {
759
+ * super({ ...options, path: '/generate' })
760
+ * }
761
+ * frame(): ProviderParserInterface<string> {
762
+ * return new TextFrame()
763
+ * }
764
+ * body(request: ProviderRequest): object {
765
+ * return { messages: request.messages }
766
+ * }
767
+ * read(record: string): ProviderIncrement {
768
+ * return { content: record, thinking: '', tools: [] }
769
+ * }
770
+ * finish(_parser: ProviderParserInterface<string>): readonly string[] {
771
+ * return [] // Raw text retains no records at end of input.
772
+ * }
773
+ * }
774
+ * ```
775
+ */
776
+ export declare abstract class AgentProvider<TRecord = Readonly<Record<string, unknown>>> implements AgentProviderInterface<TRecord> {
777
+ #private;
778
+ constructor(input: AgentProviderInput);
779
+ /** Identifies the concrete backend. */
780
+ abstract readonly name: string;
781
+ /** Exposes the instance's minted UUID. */
782
+ get id(): string;
783
+ /** Exposes the context framing exactly as supplied. */
784
+ get format(): ContextFormat | undefined;
785
+ /** Creates fresh framing state for the call. */
786
+ abstract frame(): ProviderParserInterface<TRecord>;
787
+ /** Projects a domain request onto the concrete protocol's wire body. */
788
+ abstract body(request: ProviderRequest): object;
789
+ /** Decodes a framed record into a turn increment. */
790
+ abstract read(record: TRecord): ProviderIncrement;
791
+ /** Returns any records retained at end of input. */
792
+ abstract finish(parser: ProviderParserInterface<TRecord>): readonly TRecord[];
793
+ /**
794
+ * Generates a complete turn by draining the shared stream engine.
795
+ *
796
+ * @param messages - The conversation turns
797
+ * @param signal - The caller's cancellation bound
798
+ * @param tools - The advertised tool definitions
799
+ * @param options - The per-call generation configuration
800
+ * @returns The terminal stream result
801
+ */
802
+ generate(messages: readonly Message[], signal: AbortSignal, tools?: readonly ToolDefinition[], options?: ProviderStreamOptions): Promise<ProviderResult>;
803
+ /**
804
+ * Streams decoded deltas and returns the authoritative or assembled turn result.
805
+ *
806
+ * @param messages - The conversation turns
807
+ * @param signal - The caller's cancellation bound
808
+ * @param tools - The advertised tool definitions
809
+ * @param options - The per-call generation configuration
810
+ * @returns Content and native thinking deltas followed by the settled result
811
+ * @throws ProviderAbortError Thrown when the combined cancellation bound fires
812
+ * @throws ProviderError Thrown for an HTTP or protocol failure
813
+ */
814
+ stream(messages: readonly Message[], signal: AbortSignal, tools?: readonly ToolDefinition[], options?: ProviderStreamOptions): AsyncGenerator<ProviderDelta, ProviderResult>;
815
+ }
816
+
817
+ /**
818
+ * Configures the HTTP destination and stream assembly of a provider base.
819
+ *
820
+ * @remarks
821
+ * `path` appends to `url`. If `split` is true, separates in-content reasoning;
822
+ * if false, preserves content verbatim. Default: true.
823
+ * If `strict` is true, requires a settled result record; if false, assembles at end of input.
824
+ * Default: false.
825
+ */
826
+ export declare interface AgentProviderInput extends ProviderOptions {
827
+ readonly url: string;
828
+ readonly path?: string;
829
+ readonly split?: boolean;
830
+ readonly strict?: boolean;
831
+ }
832
+
833
+ /** Defines the wire-specific seams of the shared HTTP provider engine. */
834
+ export declare interface AgentProviderInterface<TRecord = Readonly<Record<string, unknown>>> extends ProviderInterface {
835
+ /** Creates fresh framing state for a call. */
836
+ frame(): ProviderParserInterface<TRecord>;
837
+ /** Projects a request to the concrete protocol's serializable body. */
838
+ body(request: ProviderRequest): object;
839
+ /** Decodes a framed record into its contribution to the turn. */
840
+ read(record: TRecord): ProviderIncrement;
841
+ /** Returns records retained at end of input before the parser is cleared. */
842
+ finish(parser: ProviderParserInterface<TRecord>): readonly TRecord[];
843
+ }
844
+
714
845
  /**
715
846
  * Configures `createAgentQueue` — the registry that rehydrates jobs, the partial-result
716
847
  * policy, and the substrate knobs threaded into the backing `createQueue`.
@@ -1211,6 +1342,21 @@ export declare interface AuthorityRule {
1211
1342
  readonly reason?: string;
1212
1343
  }
1213
1344
 
1345
+ /**
1346
+ * Assembles a provider result with only populated optional fields.
1347
+ *
1348
+ * @param content - The authoritative answer
1349
+ * @param thinking - The joined reasoning
1350
+ * @param tools - The accumulated calls
1351
+ * @param usage - The reported token usage
1352
+ * @returns The assembled result
1353
+ * @example
1354
+ * ```ts
1355
+ * buildProviderResult('ok', '', [], undefined) // { content: 'ok' }
1356
+ * ```
1357
+ */
1358
+ export declare function buildProviderResult(content: string, thinking: string, tools: readonly ToolCall[], usage: TokenUsage | undefined): ProviderResult;
1359
+
1214
1360
  /**
1215
1361
  * Builds the framed recap message for one compacted section — the same role and stable `id` as
1216
1362
  * {@link buildSummaryMessage}, with the content prefixed by {@link
@@ -2459,8 +2605,8 @@ export declare function createChannel<T>(): ChannelInterface<T>;
2459
2605
  *
2460
2606
  * @example Conversations & compaction
2461
2607
  * ```ts
2462
- * import { createConversation } from '@orkestrel/agent'
2463
2608
  * import type { ProviderInterface } from '@orkestrel/agent'
2609
+ * import { createConversation } from '@orkestrel/agent'
2464
2610
  *
2465
2611
  * declare const provider: ProviderInterface // any concrete implementation supplied by the host app
2466
2612
  * // The summarizer seam — built from the provider by the runtime; core stays provider-agnostic.
@@ -2651,6 +2797,77 @@ export declare function createInstructionManager(options?: InstructionManagerOpt
2651
2797
  */
2652
2798
  export declare function createMemoryConversationStore(): ConversationStoreInterface;
2653
2799
 
2800
+ /**
2801
+ * Creates an authorized relay handler that validates a bounded JSON request before streaming.
2802
+ *
2803
+ * @remarks
2804
+ * Answers with the `401` status when authorization refuses or throws, the `400`
2805
+ * status when the body is missing, unreadable, or invalid, the `413` status when
2806
+ * the body fills its byte budget or the inbound read is aborted, and the `502`
2807
+ * status when the upstream provider call cannot be constructed. Refusals carry no body.
2808
+ *
2809
+ * @param options - The upstream provider, authorization decision, and optional byte budget
2810
+ * @returns A fetch-standard handler suitable for a router
2811
+ * @example Mounting the relay on your server
2812
+ * ```ts
2813
+ * import type { ProviderInterface } from '@orkestrel/agent'
2814
+ * import { createRelay } from '@orkestrel/agent'
2815
+ * import { createDispatcher } from '@orkestrel/router'
2816
+ * import { createServer } from '@orkestrel/server'
2817
+ *
2818
+ * declare const upstream: ProviderInterface // the server-side provider holding the credential
2819
+ * declare const bearer: string
2820
+ *
2821
+ * const handler = createRelay({
2822
+ * provider: upstream,
2823
+ * authorize: (request) => request.headers.get('authorization') === `Bearer ${bearer}`,
2824
+ * })
2825
+ * const dispatcher = createDispatcher({
2826
+ * routes: [{ method: 'POST', path: '/relay', handler }],
2827
+ * })
2828
+ *
2829
+ * export function serve(request: Request): Promise<Response> {
2830
+ * return dispatcher.handle(request, undefined)
2831
+ * }
2832
+ *
2833
+ * const server = createServer({ dispatcher, state: () => undefined })
2834
+ * await server.start()
2835
+ * process.on('SIGTERM', () => server.stop()) // signal cancellation, drain, then close the listener
2836
+ * ```
2837
+ */
2838
+ export declare function createRelay(options: RelayOptions): RelayHandler;
2839
+
2840
+ /**
2841
+ * Creates a provider that carries calls through a relay endpoint.
2842
+ *
2843
+ * @remarks
2844
+ * This is the browser end alone. {@link createRelay} mounts the server end, and its example
2845
+ * is the server half this one pairs with.
2846
+ *
2847
+ * @param options - The endpoint, parser factory, and HTTP call configuration
2848
+ * @returns The concrete relay provider
2849
+ * @example Reaching the relay from the browser
2850
+ * ```ts
2851
+ * import type { ProviderInterface } from '@orkestrel/agent'
2852
+ * import { createRelayProvider } from '@orkestrel/agent'
2853
+ * import { createAbort } from '@orkestrel/abort'
2854
+ * // The browser application supplies this parser dependency.
2855
+ * import { createNDJSONParser } from '@orkestrel/ndjson'
2856
+ *
2857
+ * declare const bearer: string
2858
+ * const abort = createAbort()
2859
+ * const messages = [{ id: '1', role: 'user', content: 'Say hello.' }] as const
2860
+ *
2861
+ * const browser: ProviderInterface = createRelayProvider({
2862
+ * url: 'https://app.example/relay',
2863
+ * parser: createNDJSONParser,
2864
+ * headers: () => ({ authorization: `Bearer ${bearer}` }),
2865
+ * })
2866
+ * const result = await browser.generate(messages, abort.signal) // a ProviderResult like a local provider's
2867
+ * ```
2868
+ */
2869
+ export declare function createRelayProvider(options: RelayProviderOptions): RelayProvider;
2870
+
2654
2871
  /**
2655
2872
  * Creates a named scope — an immutable {@link ScopeInterface} from its `name` and its
2656
2873
  * per-category allow-lists, the `id` minted at construction.
@@ -2826,6 +3043,19 @@ export declare const DEFAULT_AUTHORITY_ZONE = "default";
2826
3043
  */
2827
3044
  export declare const DEFAULT_CONVERSATION_KEEP = 0;
2828
3045
 
3046
+ /**
3047
+ * Holds the default provider deadline in milliseconds — `120_000`, the wall-clock bound a call
3048
+ * runs under when `AgentProviderInput.timeout` is omitted, folded with the caller's signal so
3049
+ * whichever trips first cancels the call.
3050
+ */
3051
+ export declare const DEFAULT_PROVIDER_TIMEOUT = 120000;
3052
+
3053
+ /**
3054
+ * Holds the default relay request limit in bytes — `1_048_576`, the byte budget a relay applies
3055
+ * to an inbound body when `RelayOptions.limit` is omitted, refusing a body that reaches it.
3056
+ */
3057
+ export declare const DEFAULT_RELAY_LIMIT = 1048576;
3058
+
2829
3059
  /**
2830
3060
  * Synthesizes the denial {@link ToolResult} an authority-blocked call is fed back with — the
2831
3061
  * call's `id` / `name` keyed back, carrying a denial `error` instead of a value.
@@ -3223,6 +3453,13 @@ export declare interface InstructionManagerOptions {
3223
3453
  */
3224
3454
  export declare function intersectKeys(parent: readonly string[] | undefined, child: readonly string[] | undefined): readonly string[] | undefined;
3225
3455
 
3456
+ /**
3457
+ * Names the status a relay answers for a body that is missing, unreadable, or rejected by
3458
+ * `providerRequestContract` — `400`, carried with no body and reaching the browser as a
3459
+ * `ProviderError` with the `HTTP` code.
3460
+ */
3461
+ export declare const INVALID_RELAY_STATUS = 400;
3462
+
3226
3463
  /**
3227
3464
  * Narrows an unknown caught value to an {@link AgentError} through `instanceof`, so a `catch`
3228
3465
  * can branch on its `code`.
@@ -3312,34 +3549,20 @@ export declare function isConversationError(value: unknown): value is Conversati
3312
3549
  export declare function isConversationSnapshot(value: unknown): value is ConversationSnapshot;
3313
3550
 
3314
3551
  /**
3315
- * Checks whether an `unknown` is structurally a {@link Message} record — the per-message step of
3316
- * the {@link isConversationSnapshot} and {@link isSection} read-boundary narrows, where a present
3317
- * `calls` must be an array of valid {@link import('@orkestrel/tool').ToolCall}s. Total, never
3318
- * throwing, and never an assertion; the conversation analogue of
3319
- * {@link import('@orkestrel/workspace').isFile}.
3552
+ * Checks whether a value satisfies the domain conversation-message contract.
3320
3553
  *
3321
3554
  * @remarks
3322
- * A total guard (it never throws — adversarial input returns `false`). It checks the message's
3323
- * shape: a record with a `string` `id`, a `string` `role`, a `string` `content`, and — when present
3324
- * — a `calls` array every element of which is a valid
3325
- * {@link import('@orkestrel/tool').ToolCall} ({@link isToolCall} — the
3326
- * fail-closed deepening: a tampered `calls` element rejects the message, so the snapshot
3327
- * reads back as absent rather than replaying a malformed call) and an `images` that is an array
3328
- * (an absent optional passes). The `role` is left as a broad `string` here (an open
3329
- * {@link import('./types.js').MessageRole}, so any storage-read role string is accepted
3330
- * defensively rather than rejected against the current literal set). Enough to safely impose the
3331
- * {@link Message} type at
3332
- * a storage boundary without a cast.
3333
- *
3334
- * @param value - The value to test (one element of a snapshot's `messages` / a section's `messages`)
3335
- * @returns True if `value` has the structural shape of a {@link Message}; false otherwise
3555
+ * Roles belong to MessageRole and image elements are strings. Tool arguments may
3556
+ * carry non-JSON values, as the domain type permits; the message wire contract is
3557
+ * narrower. Unreadable fields and hostile inputs return false.
3336
3558
  *
3559
+ * @param value - The unknown message candidate
3560
+ * @returns True if the domain message fields are valid; false otherwise
3337
3561
  * @example
3338
3562
  * ```ts
3339
3563
  * isMessage({ id: '1', role: 'user', content: 'hi' }) // true
3340
- * isMessage({ id: '1', role: 'assistant', content: '', calls: [] }) // true
3341
- * isMessage({ id: '1', role: 'user' }) // false (missing content)
3342
- * isMessage({ id: '1', role: 'assistant', content: '', calls: [null] }) // false (malformed call)
3564
+ * isMessage({ id: '1', role: 'other', content: '' }) // false
3565
+ * isMessage({ id: '1', role: 'user', content: '', images: [1] }) // false
3343
3566
  * ```
3344
3567
  */
3345
3568
  export declare function isMessage(value: unknown): value is Message;
@@ -3362,6 +3585,18 @@ export declare function isMessage(value: unknown): value is Message;
3362
3585
  */
3363
3586
  export declare function isProviderAbortError(value: unknown): value is ProviderAbortError;
3364
3587
 
3588
+ /**
3589
+ * Narrows a caught value to the provider failure class through instanceof.
3590
+ *
3591
+ * @param value - The caught value
3592
+ * @returns True if the value is a provider failure; false otherwise
3593
+ * @example
3594
+ * ```ts
3595
+ * isProviderError(new ProviderError('HTTP', 'unavailable', { status: 503 })) // true
3596
+ * ```
3597
+ */
3598
+ export declare function isProviderError(value: unknown): value is ProviderError;
3599
+
3365
3600
  /**
3366
3601
  * Checks whether an `unknown` is structurally a {@link Section} record — a `string` `id` and
3367
3602
  * `summary` beside a `messages` array of valid {@link Message}s, the per-section step of the
@@ -3403,11 +3638,19 @@ export declare function isSection(value: unknown): value is Section;
3403
3638
  * @example
3404
3639
  * ```ts
3405
3640
  * joinThinking(undefined, 'first') // 'first'
3641
+ * joinThinking('', 'x') // 'x'
3406
3642
  * joinThinking('first', 'second') // 'first\n\nsecond'
3407
3643
  * ```
3408
3644
  */
3409
3645
  export declare function joinThinking(running: string | undefined, next: string): string;
3410
3646
 
3647
+ /**
3648
+ * Bounds the decoded error excerpt's input in bytes — `2048`, the leading bytes of a non-OK
3649
+ * response body handed to the decoder before the read cancels the remainder, so a `ProviderError`
3650
+ * message never carries a longer excerpt.
3651
+ */
3652
+ export declare const MAX_ERROR_BODY_LENGTH = 2048;
3653
+
3411
3654
  /**
3412
3655
  * Implements the {@link ConversationStoreInterface} in memory — a process-lifetime `Map` of
3413
3656
  * {@link ConversationSnapshot}s keyed by conversation id, the default store
@@ -3506,6 +3749,22 @@ export declare interface Message {
3506
3749
  */
3507
3750
  export declare const MESSAGE_TOKEN_OVERHEAD = 4;
3508
3751
 
3752
+ /** Validates and projects conversation messages at a JSON wire boundary. */
3753
+ export declare const messageContract: ContractInterface<Readonly<{
3754
+ id: string;
3755
+ role: "system" | "user" | "assistant" | "tool";
3756
+ content: string;
3757
+ } & {
3758
+ calls?: readonly Readonly<{
3759
+ id: string;
3760
+ name: string;
3761
+ arguments: {
3762
+ readonly [k: string]: JSONValue;
3763
+ };
3764
+ } & {}>[];
3765
+ images?: readonly string[];
3766
+ }>>;
3767
+
3509
3768
  /**
3510
3769
  * Carries the minimal data needed to author a {@link Message} — the `id` is
3511
3770
  * assigned by the layer that stores it, so a caller supplies only role / content
@@ -3562,6 +3821,31 @@ export declare interface MessageManagerInterface {
3562
3821
  /** Names the role a {@link Message} plays in a conversation turn. */
3563
3822
  export declare type MessageRole = 'system' | 'user' | 'assistant' | 'tool';
3564
3823
 
3824
+ /**
3825
+ * Describes a conversation message's JSON wire projection.
3826
+ *
3827
+ * @remarks
3828
+ * The wire is strictly narrower than Message: non-JSON call arguments are refused,
3829
+ * and caller context is refused by the guard or dropped by the parser.
3830
+ */
3831
+ export declare const messageShape: ObjectShape< {
3832
+ id: StringShape;
3833
+ role: LiteralShape<readonly ["system", "user", "assistant", "tool"]>;
3834
+ content: StringShape;
3835
+ calls: OptionalShape<ArrayShape<ObjectShape< {
3836
+ id: StringShape;
3837
+ name: StringShape;
3838
+ arguments: ObjectShape<Record<never, never>, JSONShape>;
3839
+ }, boolean | ContractShape>>>;
3840
+ images: OptionalShape<ArrayShape<StringShape>>;
3841
+ }, boolean | ContractShape>;
3842
+
3843
+ /**
3844
+ * Names the status a relay answers for a request body at or above its byte budget — `413`,
3845
+ * carried with no body and answered for an aborted inbound read as well.
3846
+ */
3847
+ export declare const OVERSIZED_RELAY_STATUS = 413;
3848
+
3565
3849
  /**
3566
3850
  * Reports a provider stream cancelled mid-flight by its bound signal — thrown by a
3567
3851
  * {@link ProviderInterface}'s `stream`, carrying the {@link ProviderResult} assembled from
@@ -3571,13 +3855,15 @@ export declare type MessageRole = 'system' | 'user' | 'assistant' | 'tool';
3571
3855
  * Lets a caller recover the partial content (and any tool calls / usage seen so far)
3572
3856
  * on cancellation: `catch` the throw, narrow with {@link isProviderAbortError}, and
3573
3857
  * read `partial`. `code` is the machine-readable condition (`'ABORT'` — the only one this
3574
- * error reports), so a `catch` branches on it rather than on the message string.
3858
+ * error reports), so a `catch` branches on it rather than on the message string. `cause`
3859
+ * holds the failure the cancel superseded when a throw raced the abort — the wire decoder's
3860
+ * {@link ProviderError}, say — and is undefined when the cancel was the only failure.
3575
3861
  */
3576
3862
  export declare class ProviderAbortError extends Error {
3577
3863
  /** Names the machine-readable condition — `'ABORT'`: a stream cancelled mid-flight. */
3578
3864
  readonly code: "ABORT";
3579
3865
  readonly partial: ProviderResult;
3580
- constructor(partial: ProviderResult);
3866
+ constructor(partial: ProviderResult, options?: ErrorOptions);
3581
3867
  }
3582
3868
 
3583
3869
  /**
@@ -3603,6 +3889,47 @@ export declare type ProviderDelta = {
3603
3889
  readonly text: string;
3604
3890
  };
3605
3891
 
3892
+ /**
3893
+ * Reports a coded provider failure with its HTTP status and underlying cause when available.
3894
+ *
3895
+ * @remarks
3896
+ * The provider base throws this error for a non-OK HTTP response, a missing response
3897
+ * body, or a missing settled result when strict assembly is enabled. Concrete wire
3898
+ * decoders also use it for malformed records and relayed provider failures.
3899
+ * `status` is present only for an `HTTP` failure; other codes leave it undefined.
3900
+ */
3901
+ export declare class ProviderError extends Error {
3902
+ /** Names the machine-readable condition — `'HTTP'`: a non-OK response, including a relay refusing an oversized request with 413; `'PROTOCOL'`: a missing response body, a malformed wire record, or a strict stream with no settled result; `'PROVIDER'`: an upstream failure carried by a relay error record. */
3903
+ readonly code: ProviderErrorCode;
3904
+ /** Holds the response status for an HTTP failure, or undefined for other codes. */
3905
+ readonly status: number | undefined;
3906
+ constructor(code: ProviderErrorCode, message: string, options?: ProviderErrorOptions);
3907
+ }
3908
+
3909
+ /** Names the machine-readable provider failure conditions. */
3910
+ export declare type ProviderErrorCode =
3911
+ /** Reports a non-OK HTTP response, including a relay request rejected with status 413. */
3912
+ 'HTTP'
3913
+ /** Reports a missing body, malformed wire record, or missing required settled result. */
3914
+ | 'PROTOCOL'
3915
+ /** Reports an upstream provider failure carried by a relay error record. */
3916
+ | 'PROVIDER';
3917
+
3918
+ /** Carries a provider failure's HTTP status and underlying cause. */
3919
+ export declare interface ProviderErrorOptions {
3920
+ readonly status?: number;
3921
+ readonly cause?: unknown;
3922
+ }
3923
+
3924
+ /** Holds the decoded contribution of a wire record to a provider turn. */
3925
+ export declare interface ProviderIncrement {
3926
+ readonly content: string;
3927
+ readonly thinking: string;
3928
+ readonly tools: readonly ToolCall[];
3929
+ readonly usage?: TokenUsage;
3930
+ readonly result?: ProviderResult;
3931
+ }
3932
+
3606
3933
  /**
3607
3934
  * Defines the pluggable LLM inference boundary — the one contract every agent chunk depends on. A
3608
3935
  * provider turns a conversation (plus optional tools) into either a single assembled {@link
@@ -3659,6 +3986,101 @@ export declare interface ProviderInterface {
3659
3986
  stream(messages: readonly Message[], signal: AbortSignal, tools?: readonly ToolDefinition[], options?: ProviderStreamOptions): AsyncGenerator<ProviderDelta, ProviderResult>;
3660
3987
  }
3661
3988
 
3989
+ /**
3990
+ * Configures a provider's deadline, transport, headers, and context framing.
3991
+ *
3992
+ * @remarks
3993
+ * `timeout` is an integer duration in milliseconds. Default: 120_000.
3994
+ * `fetch` defaults to the global transport bound to its global receiver.
3995
+ * `headers` runs for each request inside its deadline and receives the combined caller
3996
+ * and deadline signal so token requests can share that bound. It overrides the JSON
3997
+ * content type only when it returns that header. `format` is exposed to context assembly.
3998
+ */
3999
+ export declare interface ProviderOptions {
4000
+ readonly timeout?: number;
4001
+ readonly fetch?: typeof globalThis.fetch;
4002
+ readonly headers?: (signal: AbortSignal) => Readonly<Record<string, string>> | Promise<Readonly<Record<string, string>>>;
4003
+ readonly format?: ContextFormat;
4004
+ }
4005
+
4006
+ /** Defines the structural framing seam supplied by a concrete provider. */
4007
+ export declare interface ProviderParserInterface<TRecord = Readonly<Record<string, unknown>>> {
4008
+ /** Parses a decoded chunk into complete records. */
4009
+ parse(chunk: string): readonly TRecord[];
4010
+ /** Clears retained framing state. */
4011
+ clear(): void;
4012
+ }
4013
+
4014
+ /** Carries the conversation and per-call configuration sent to a provider. */
4015
+ export declare interface ProviderRequest {
4016
+ readonly messages: readonly Message[];
4017
+ readonly tools?: readonly ToolDefinition[];
4018
+ readonly options?: ProviderStreamOptions;
4019
+ }
4020
+
4021
+ /** Validates and projects provider requests at a JSON wire boundary. */
4022
+ export declare const providerRequestContract: ContractInterface<Readonly<{
4023
+ messages: readonly Readonly<{
4024
+ id: string;
4025
+ role: "system" | "user" | "assistant" | "tool";
4026
+ content: string;
4027
+ } & {
4028
+ calls?: readonly Readonly<{
4029
+ id: string;
4030
+ name: string;
4031
+ arguments: {
4032
+ readonly [k: string]: JSONValue;
4033
+ };
4034
+ } & {}>[];
4035
+ images?: readonly string[];
4036
+ }>[];
4037
+ } & {
4038
+ tools?: readonly Readonly<{
4039
+ name: string;
4040
+ } & {
4041
+ description?: string;
4042
+ parameters?: {
4043
+ readonly [k: string]: JSONValue;
4044
+ };
4045
+ }>[];
4046
+ options?: Readonly<{} & {
4047
+ think?: boolean;
4048
+ schema?: {
4049
+ readonly [k: string]: JSONValue;
4050
+ };
4051
+ }>;
4052
+ }>>;
4053
+
4054
+ /**
4055
+ * Describes a provider request's JSON wire projection.
4056
+ *
4057
+ * @remarks
4058
+ * The wire is strictly narrower than ProviderRequest: non-JSON arguments, parameters,
4059
+ * or schema members are refused, and caller context is refused or dropped.
4060
+ */
4061
+ export declare const providerRequestShape: ObjectShape< {
4062
+ messages: ArrayShape<ObjectShape< {
4063
+ id: StringShape;
4064
+ role: LiteralShape<readonly ["system", "user", "assistant", "tool"]>;
4065
+ content: StringShape;
4066
+ calls: OptionalShape<ArrayShape<ObjectShape< {
4067
+ id: StringShape;
4068
+ name: StringShape;
4069
+ arguments: ObjectShape<Record<never, never>, JSONShape>;
4070
+ }, boolean | ContractShape>>>;
4071
+ images: OptionalShape<ArrayShape<StringShape>>;
4072
+ }, boolean | ContractShape>>;
4073
+ tools: OptionalShape<ArrayShape<ObjectShape< {
4074
+ name: StringShape;
4075
+ description: OptionalShape<StringShape>;
4076
+ parameters: OptionalShape<ObjectShape<Record<never, never>, JSONShape>>;
4077
+ }, boolean | ContractShape>>>;
4078
+ options: OptionalShape<ObjectShape< {
4079
+ think: OptionalShape<BooleanShape>;
4080
+ schema: OptionalShape<ObjectShape<Record<never, never>, JSONShape>>;
4081
+ }, boolean | ContractShape>>;
4082
+ }, boolean | ContractShape>;
4083
+
3662
4084
  /**
3663
4085
  * Holds a single inference turn's structured outcome — the assembled assistant content,
3664
4086
  * any reasoning the provider separated from it, any tool calls the model requested,
@@ -3684,6 +4106,47 @@ export declare interface ProviderResult {
3684
4106
  readonly usage?: TokenUsage;
3685
4107
  }
3686
4108
 
4109
+ /** Validates and projects provider results at a JSON wire boundary. */
4110
+ export declare const providerResultContract: ContractInterface<Readonly<{
4111
+ content: string;
4112
+ } & {
4113
+ thinking?: string;
4114
+ tools?: readonly Readonly<{
4115
+ id: string;
4116
+ name: string;
4117
+ arguments: {
4118
+ readonly [k: string]: JSONValue;
4119
+ };
4120
+ } & {}>[];
4121
+ usage?: Readonly<{
4122
+ prompt: number;
4123
+ completion: number;
4124
+ total: number;
4125
+ } & {}>;
4126
+ }>>;
4127
+
4128
+ /**
4129
+ * Describes a provider result's JSON wire projection.
4130
+ *
4131
+ * @remarks
4132
+ * The wire is strictly narrower than ProviderResult: non-JSON call arguments are
4133
+ * refused, and caller context is refused or dropped.
4134
+ */
4135
+ export declare const providerResultShape: ObjectShape< {
4136
+ content: StringShape;
4137
+ thinking: OptionalShape<StringShape>;
4138
+ tools: OptionalShape<ArrayShape<ObjectShape< {
4139
+ id: StringShape;
4140
+ name: StringShape;
4141
+ arguments: ObjectShape<Record<never, never>, JSONShape>;
4142
+ }, boolean | ContractShape>>>;
4143
+ usage: OptionalShape<ObjectShape< {
4144
+ prompt: NumberShape;
4145
+ completion: NumberShape;
4146
+ total: NumberShape;
4147
+ }, boolean | ContractShape>>;
4148
+ }, boolean | ContractShape>;
4149
+
3687
4150
  /**
3688
4151
  * Carries the per-call options threaded into a {@link ProviderInterface}'s `generate` / `stream` —
3689
4152
  * the bag a caller passes to influence one inference call without reconfiguring the provider
@@ -3707,6 +4170,299 @@ export declare interface ProviderStreamOptions {
3707
4170
  readonly schema?: Readonly<Record<string, unknown>>;
3708
4171
  }
3709
4172
 
4173
+ /**
4174
+ * Decodes UTF-8 chunks with a final flush and releases the stream on every exit.
4175
+ *
4176
+ * @param body - The readable byte stream
4177
+ * @param signal - The optional cancellation bound; abort ends iteration without further chunks
4178
+ * @returns Decoded text chunks, including a held decoder tail
4179
+ * @example
4180
+ * ```ts
4181
+ * const body = new Response('answer').body
4182
+ * if (body !== null) for await (const chunk of readChunks(body)) render(chunk)
4183
+ * ```
4184
+ */
4185
+ export declare function readChunks(body: ReadableStream<Uint8Array>, signal?: AbortSignal): AsyncGenerator<string>;
4186
+
4187
+ /**
4188
+ * Reads a UTF-8 prefix of a byte stream and cancels its remainder.
4189
+ *
4190
+ * @remarks
4191
+ * The `limit` parameter bounds bytes passed to the decoder, including a partial final
4192
+ * character. An omitted limit reads to completion. A source may deliver a chunk larger
4193
+ * than the remaining limit; its unused bytes are discarded without decoding.
4194
+ * The read can overshoot by one source chunk. An abort leaves completion false.
4195
+ *
4196
+ * @param body - The readable byte stream
4197
+ * @param limit - The maximum byte prefix, or undefined for the complete stream
4198
+ * @param signal - The optional cancellation bound; abort returns the decoded prefix
4199
+ * @returns The decoded prefix and whether EOF occurred within the byte budget
4200
+ * @example
4201
+ * ```ts
4202
+ * import { readText } from '@orkestrel/agent'
4203
+ *
4204
+ * const body = new Response('answer').body
4205
+ * if (body !== null) await readText(body, 3) // { text: 'ans', complete: false }
4206
+ * ```
4207
+ */
4208
+ export declare function readText(body: ReadableStream<Uint8Array>, limit?: number, signal?: AbortSignal): Promise<TextRead>;
4209
+
4210
+ /**
4211
+ * Names the relay's newline-delimited JSON content type — `'application/x-ndjson; charset=utf-8'`,
4212
+ * the header a relay response carries beside `cache-control: no-store`.
4213
+ */
4214
+ export declare const RELAY_CONTENT_TYPE = "application/x-ndjson; charset=utf-8";
4215
+
4216
+ /**
4217
+ * Names the public message for an unexpected upstream relay failure — `'relay provider failed'`,
4218
+ * the fixed text every `error` frame carries, so an upstream failure's own message never reaches
4219
+ * the browser.
4220
+ */
4221
+ export declare const RELAY_PROVIDER_MESSAGE = "relay provider failed";
4222
+
4223
+ /** Carries a relay delta, settled result, remote abort, or remote failure. */
4224
+ export declare type RelayFrame = ProviderDelta | {
4225
+ readonly channel: 'result';
4226
+ readonly result: ProviderResult;
4227
+ } | {
4228
+ readonly channel: 'abort';
4229
+ readonly partial: ProviderResult;
4230
+ } | {
4231
+ readonly channel: 'error';
4232
+ readonly message: string;
4233
+ };
4234
+
4235
+ /** Validates and projects channel-discriminated relay frames at a JSON wire boundary. */
4236
+ export declare const relayFrameContract: ContractInterface<Readonly<{
4237
+ channel: "content" | "thinking";
4238
+ text: string;
4239
+ } & {}> | Readonly<{
4240
+ channel: "result";
4241
+ result: Readonly<{
4242
+ content: string;
4243
+ } & {
4244
+ thinking?: string;
4245
+ tools?: readonly Readonly<{
4246
+ id: string;
4247
+ name: string;
4248
+ arguments: {
4249
+ readonly [k: string]: JSONValue;
4250
+ };
4251
+ } & {}>[];
4252
+ usage?: Readonly<{
4253
+ prompt: number;
4254
+ completion: number;
4255
+ total: number;
4256
+ } & {}>;
4257
+ }>;
4258
+ } & {}> | Readonly<{
4259
+ channel: "abort";
4260
+ partial: Readonly<{
4261
+ content: string;
4262
+ } & {
4263
+ thinking?: string;
4264
+ tools?: readonly Readonly<{
4265
+ id: string;
4266
+ name: string;
4267
+ arguments: {
4268
+ readonly [k: string]: JSONValue;
4269
+ };
4270
+ } & {}>[];
4271
+ usage?: Readonly<{
4272
+ prompt: number;
4273
+ completion: number;
4274
+ total: number;
4275
+ } & {}>;
4276
+ }>;
4277
+ } & {}> | Readonly<{
4278
+ channel: "error";
4279
+ message: string;
4280
+ } & {}>>;
4281
+
4282
+ /**
4283
+ * Describes the channel-discriminated JSON relay wire projection.
4284
+ *
4285
+ * @remarks
4286
+ * The wire is strictly narrower than RelayFrame through its result and partial
4287
+ * fields: non-JSON arguments are refused, and caller context is refused or dropped.
4288
+ */
4289
+ export declare const relayFrameShape: UnionShape<readonly [ObjectShape< {
4290
+ channel: LiteralShape<readonly ["content", "thinking"]>;
4291
+ text: StringShape;
4292
+ }, boolean | ContractShape>, ObjectShape< {
4293
+ channel: LiteralShape<readonly ["result"]>;
4294
+ result: ObjectShape< {
4295
+ content: StringShape;
4296
+ thinking: OptionalShape<StringShape>;
4297
+ tools: OptionalShape<ArrayShape<ObjectShape< {
4298
+ id: StringShape;
4299
+ name: StringShape;
4300
+ arguments: ObjectShape<Record<never, never>, JSONShape>;
4301
+ }, boolean | ContractShape>>>;
4302
+ usage: OptionalShape<ObjectShape< {
4303
+ prompt: NumberShape;
4304
+ completion: NumberShape;
4305
+ total: NumberShape;
4306
+ }, boolean | ContractShape>>;
4307
+ }, boolean | ContractShape>;
4308
+ }, boolean | ContractShape>, ObjectShape< {
4309
+ channel: LiteralShape<readonly ["abort"]>;
4310
+ partial: ObjectShape< {
4311
+ content: StringShape;
4312
+ thinking: OptionalShape<StringShape>;
4313
+ tools: OptionalShape<ArrayShape<ObjectShape< {
4314
+ id: StringShape;
4315
+ name: StringShape;
4316
+ arguments: ObjectShape<Record<never, never>, JSONShape>;
4317
+ }, boolean | ContractShape>>>;
4318
+ usage: OptionalShape<ObjectShape< {
4319
+ prompt: NumberShape;
4320
+ completion: NumberShape;
4321
+ total: NumberShape;
4322
+ }, boolean | ContractShape>>;
4323
+ }, boolean | ContractShape>;
4324
+ }, boolean | ContractShape>, ObjectShape< {
4325
+ channel: LiteralShape<readonly ["error"]>;
4326
+ message: StringShape;
4327
+ }, boolean | ContractShape>]>;
4328
+
4329
+ /** Defines a host-independent relay request handler. */
4330
+ export declare type RelayHandler = (request: Request) => Promise<Response>;
4331
+
4332
+ /** Configures the upstream provider, mandatory authorization, and request byte limit. */
4333
+ export declare interface RelayOptions {
4334
+ readonly provider: ProviderInterface;
4335
+ /**
4336
+ * Authorizes the request before its body is read.
4337
+ *
4338
+ * @remarks
4339
+ * The hook must not consume the request body; a body-reading hook locks the stream
4340
+ * and the handler answers with the `400` status. The relay performs no origin or
4341
+ * method check. An application trusting an ambient credential such as a cookie
4342
+ * must compose origin and CSRF middleware before the handler to prevent cross-site calls.
4343
+ */
4344
+ readonly authorize: (request: Request) => boolean | Promise<boolean>;
4345
+ /**
4346
+ * Bounds the request body in bytes; the handler answers with the `413` status
4347
+ * for a body at or above the limit.
4348
+ */
4349
+ readonly limit?: number;
4350
+ }
4351
+
4352
+ /**
4353
+ * Carries provider calls over an authenticated NDJSON relay endpoint.
4354
+ *
4355
+ * @remarks
4356
+ * The `ToolCall.caller` member never crosses the hop. The wire body is an owned snapshot of
4357
+ * the projection read through property descriptors, so a serializer reachable only through a
4358
+ * `get` trap or a prototype is never consulted; an own function-valued property such as a
4359
+ * `toJSON` method is a value outside JSON and is refused before fetching, with the clone's
4360
+ * failure as the refusal's `cause`. A remote abort reconstructs a `ProviderAbortError` instance
4361
+ * without aborting the
4362
+ * local signal; the `Agent` runtime treats that instance as an error unless its own bound
4363
+ * signal is aborted.
4364
+ * Content is preserved verbatim, including literal thinking tags.
4365
+ * A refusal reaches the browser as a `ProviderError` instance with the `HTTP` code and status.
4366
+ * This is the browser end alone; {@link createRelay} mounts the server end, and
4367
+ * {@link createRelayProvider}'s example is the browser half of that pair.
4368
+ *
4369
+ * @example
4370
+ * ```ts
4371
+ * import type { ProviderResult } from '@orkestrel/agent'
4372
+ * import { RelayProvider } from '@orkestrel/agent'
4373
+ * // The browser application supplies this parser dependency.
4374
+ * import { createNDJSONParser } from '@orkestrel/ndjson'
4375
+ *
4376
+ * export function ask(bearer: string, signal: AbortSignal): Promise<ProviderResult> {
4377
+ * const browser = new RelayProvider({
4378
+ * url: 'https://relay.example/relay',
4379
+ * parser: createNDJSONParser,
4380
+ * headers: () => ({ authorization: `Bearer ${bearer}` }),
4381
+ * })
4382
+ * return browser.generate([{ id: 'ask', role: 'user', content: 'ping' }], signal)
4383
+ * }
4384
+ * ```
4385
+ */
4386
+ export declare class RelayProvider extends AgentProvider {
4387
+ #private;
4388
+ constructor(options: RelayProviderOptions);
4389
+ /** Identifies the relay backend. */
4390
+ readonly name = "relay";
4391
+ /** Creates fresh framing state for each response. */
4392
+ frame(): ProviderParserInterface;
4393
+ /**
4394
+ * Projects declared request fields and refuses values the JSON wire cannot carry.
4395
+ *
4396
+ * @remarks
4397
+ * The snapshot is taken from property descriptors, so a custom serializer a projected
4398
+ * value carries is ignored rather than consulted and cannot reach the wire.
4399
+ *
4400
+ * @param request - The domain conversation and call configuration
4401
+ * @returns The validated wire request with caller context omitted
4402
+ * @throws {ProviderError} Thrown when the snapshot cannot be taken — a hostile read or a
4403
+ * value outside JSON — carrying that failure as its `cause`, and when the snapshot the
4404
+ * projection produced is not a valid wire request
4405
+ */
4406
+ body(request: ProviderRequest): object;
4407
+ /**
4408
+ * Validates a relay frame and translates its channel into the shared stream engine.
4409
+ *
4410
+ * @param record - The framed wire record
4411
+ * @returns A delta contribution or authoritative result
4412
+ * @throws {ProviderAbortError} Thrown for a remote abort carrying its partial
4413
+ * @throws {ProviderError} Thrown for a malformed frame or remote provider failure
4414
+ */
4415
+ read(record: Readonly<Record<string, unknown>>): ProviderIncrement;
4416
+ /**
4417
+ * Recovers an unterminated final frame by completing its NDJSON line.
4418
+ *
4419
+ * @param parser - The call's retained framing state
4420
+ * @returns Records completed by the final newline
4421
+ */
4422
+ finish(parser: ProviderParserInterface): ReadonlyArray<Readonly<Record<string, unknown>>>;
4423
+ }
4424
+
4425
+ /** Configures a relay destination and its fresh structural parser factory. */
4426
+ export declare interface RelayProviderOptions extends ProviderOptions {
4427
+ readonly url: string;
4428
+ /** Creates a fresh parser for each relay response stream. */
4429
+ readonly parser: () => ProviderParserInterface;
4430
+ }
4431
+
4432
+ /**
4433
+ * Streams a provider call as validated NDJSON frames under response backpressure.
4434
+ *
4435
+ * @remarks
4436
+ * Cancellation aborts upstream before returning its iterator. Request listeners are
4437
+ * released on settlement. Unexpected provider failures carry a fixed public message.
4438
+ * An inbound abort leaves the response body neither closed nor errored — a server runtime
4439
+ * cancels that body when the client disconnects — so a consumer that aborts the inbound
4440
+ * signal itself must cancel the body rather than keep reading it.
4441
+ *
4442
+ * @example
4443
+ * ```ts
4444
+ * import type { ProviderInterface } from '@orkestrel/agent'
4445
+ * import { RelayStream } from '@orkestrel/agent'
4446
+ *
4447
+ * export function respond(provider: ProviderInterface, signal: AbortSignal): Response {
4448
+ * return new RelayStream({ provider, request: { messages: [] }, signal }).response
4449
+ * }
4450
+ * ```
4451
+ */
4452
+ export declare class RelayStream {
4453
+ #private;
4454
+ constructor(options: RelayStreamOptions);
4455
+ /** Exposes the pull-driven response for the provider call. */
4456
+ get response(): Response;
4457
+ }
4458
+
4459
+ /** Carries the upstream call and cancellation bound of a relay response stream. */
4460
+ export declare interface RelayStreamOptions {
4461
+ readonly provider: ProviderInterface;
4462
+ readonly request: ProviderRequest;
4463
+ readonly signal: AbortSignal;
4464
+ }
4465
+
3710
4466
  /**
3711
4467
  * Renders a path-addressed text body as a fenced reference block — a `File: <path>` label line
3712
4468
  * over a language-tagged fence, the framing an
@@ -4182,6 +4938,16 @@ export declare interface StreamInterface<T, R> {
4182
4938
  */
4183
4939
  export declare function sumUsage(running: TokenUsage | undefined, next: TokenUsage): TokenUsage;
4184
4940
 
4941
+ /** Carries a decoded stream prefix and whether the stream ended within its byte budget. */
4942
+ export declare interface TextRead {
4943
+ readonly text: string;
4944
+ /**
4945
+ * Reports true only when a read observes the `done` flag before exhausting the
4946
+ * byte budget; an abort reports false.
4947
+ */
4948
+ readonly complete: boolean;
4949
+ }
4950
+
4185
4951
  /**
4186
4952
  * Names the closing tag that ends a {@link THINK_OPEN} reasoning span — `'</think>'`. A span the
4187
4953
  * stream never closes (the model was cut off mid-reasoning) is treated as thinking to its end,
@@ -4294,6 +5060,33 @@ export declare interface ThinkSplitterInterface {
4294
5060
  flush(): string;
4295
5061
  }
4296
5062
 
5063
+ /**
5064
+ * Describes a tool call's JSON wire projection.
5065
+ *
5066
+ * @remarks
5067
+ * The wire is strictly narrower than the domain: non-JSON arguments are refused.
5068
+ * ToolCall.caller is not in this shape and never crosses a wire. The guard refuses
5069
+ * that extra member; the contract parser drops it.
5070
+ */
5071
+ export declare const toolCallShape: ObjectShape< {
5072
+ id: StringShape;
5073
+ name: StringShape;
5074
+ arguments: ObjectShape<Record<never, never>, JSONShape>;
5075
+ }, boolean | ContractShape>;
5076
+
5077
+ /**
5078
+ * Names the status a relay answers when the `authorize` callback returns anything but `true` or throws —
5079
+ * `401`, carried with no body and reaching the browser as a `ProviderError` with the `HTTP` code.
5080
+ */
5081
+ export declare const UNAUTHORIZED_RELAY_STATUS = 401;
5082
+
5083
+ /**
5084
+ * Names the status a relay answers when the upstream provider call cannot be constructed — `502`,
5085
+ * carried with no body after `provider.stream` was entered and threw before returning its
5086
+ * iterator.
5087
+ */
5088
+ export declare const UPSTREAM_RELAY_STATUS = 502;
5089
+
4297
5090
  /**
4298
5091
  * Names the section header {@link import('./AgentContext.js').AgentContext}'s `build()` renders the
4299
5092
  * active workspace's text files under — `'## Workspace'`, the leading line of the dedicated