dsh-opencode-go 0.1.19 → 0.1.21

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.
@@ -25,7 +25,9 @@ import { LlmAdapter } from '@deepseek-ai/dsh-llm';
25
25
  import type { GenerateOptions, ImageAttachmentAccess, LlmModelInfo, LlmResolvedModelInfo, StreamChunk } from '@deepseek-ai/dsh-llm';
26
26
  import type { AttachmentStore, ImageAttachmentRef } from '@deepseek-ai/dsh-attachment';
27
27
  import { OpencodeGoCatalog } from './catalog.ts';
28
+ import { ProxyTransport } from './proxy.ts';
28
29
  import type { OpencodeGoConfig } from './config.ts';
30
+ import { type GoAccountSwitch } from './accounts.ts';
29
31
  /**
30
32
  * The attachment-service bridges one image request reads. Construction-time
31
33
  * (context-dependent); the config-dependent policy numbers are merged per
@@ -39,6 +41,8 @@ export interface OpencodeGoImageAccess {
39
41
  }
40
42
  /** Constructor inputs for {@link OpencodeGoAdapter}. */
41
43
  export interface OpencodeGoAdapterOptions {
44
+ /** Shared with Host usage reads for this plugin mount. */
45
+ transport?: ProxyTransport;
42
46
  /**
43
47
  * The current configuration, re-read at every operation: a settings write
44
48
  * reaches the next request without a restart, and one operation never mixes
@@ -64,6 +68,7 @@ export interface OpencodeGoAdapterOptions {
64
68
  onReplayDegrade?: (reason: string) => void;
65
69
  /** Re-read picker models after a background catalog refresh commits. */
66
70
  onCatalogRefresh?: () => void;
71
+ onAccountSwitch?: (notice: GoAccountSwitch | undefined, config: OpencodeGoConfig) => void;
67
72
  }
68
73
  /**
69
74
  * The single route's adapter. The catalog snapshot freezes at each operation,
@@ -79,7 +84,11 @@ export declare class OpencodeGoAdapter extends LlmAdapter {
79
84
  * for the whole refresh interval.
80
85
  */
81
86
  private catalogCache;
87
+ private readonly transport;
88
+ /** Per-reference rejection deadlines, isolated by the gateway that rejected it. */
89
+ private readonly rejectedKeys;
82
90
  constructor(options: OpencodeGoAdapterOptions);
91
+ dispose(): Promise<void>;
83
92
  /**
84
93
  * The catalog resolver for one configuration, rebuilding on the facts it
85
94
  * owns. Public for the plugin's discovery registration, which resolves the
@@ -107,4 +116,9 @@ export declare class OpencodeGoAdapter extends LlmAdapter {
107
116
  private resolveReasoningLevel;
108
117
  stream(options: GenerateOptions): AsyncIterable<StreamChunk>;
109
118
  private streamWithSnapshot;
119
+ private rememberRejectedKey;
120
+ /** A stored change to a reference outranks the gateway's last rejection of it. */
121
+ forgetRejectedKey(ref: string): void;
122
+ /** One account, one SDK attempt; host recovery still owns failures after output. */
123
+ private streamAttempt;
110
124
  }
@@ -30,6 +30,7 @@ export declare class OpencodeGoCatalog {
30
30
  /** Kept for API compatibility; now reports unconfigured ids rather than hiding them. */
31
31
  private readonly onOmitted;
32
32
  private readonly onRefresh;
33
+ private readonly fetcher?;
33
34
  private served;
34
35
  private pending;
35
36
  /** A cold runtime read can use disk metadata while the shared online refresh runs. */
@@ -48,7 +49,7 @@ export declare class OpencodeGoCatalog {
48
49
  kept: number;
49
50
  }) => void,
50
51
  /** Kept for API compatibility; now reports unconfigured ids rather than hiding them. */
51
- onOmitted: (ids: readonly string[]) => void, onRefresh?: () => void);
52
+ onOmitted: (ids: readonly string[]) => void, onRefresh?: () => void, fetcher?: typeof globalThis.fetch | undefined);
52
53
  snapshot(force?: boolean, signal?: AbortSignal): Promise<CatalogSnapshot>;
53
54
  private restoreMetadata;
54
55
  private readSnapshot;
@@ -0,0 +1,19 @@
1
+ import type { GoAccountsActions, GoAccountsState } from './accounts-controller.ts';
2
+ import type { en } from './locales.ts';
3
+ type Translate = (key: keyof typeof en, params?: Record<string, unknown>) => string;
4
+ /**
5
+ * The account card: a folded header that summarizes the set, and one row per
6
+ * account inside. Rows keep the identity, key state, rolling quota and its reset
7
+ * countdown; everything else opens under the row. The handle is the drag source —
8
+ * dragging it, or the arrow keys on it, reorders the list, and the first row is
9
+ * the preferred account. Every row is read in the same pass, so the one refresh
10
+ * stamp belongs to the card and sits in its header.
11
+ */
12
+ export declare function AccountsCard({ state, actions, writable, t, locale }: {
13
+ state: GoAccountsState;
14
+ actions: GoAccountsActions;
15
+ writable: boolean;
16
+ t: Translate;
17
+ locale?: string;
18
+ }): import("react").JSX.Element;
19
+ export {};
@@ -1,10 +1,7 @@
1
1
  /**
2
- * The OpenCode Go settings page. Three cards carry the page's whole order — the
3
- * connection (the switch that routes the provider plus the API key it
4
- * authenticates with), the models the gateway currently serves and their
5
- * capacities, and the adapter tuning fields behind a collapsed disclosure at the
6
- * foot. The credential reference, the endpoint, and the tuning knobs all live in
7
- * the `llm-opencode-go` namespace, so every card writes the same document.
2
+ * The OpenCode Go settings page: provider activation, accounts and credentials,
3
+ * available models and capacities, then advanced tuning. Account operations
4
+ * apply immediately; tuning fields use the page's save/discard actions.
8
5
  */
9
6
  import type { InjectFace } from '@deepseek-ai/dsh-client-ui-slots';
10
7
  import type { OpencodeGoSectionFace } from './section-controller.ts';
@@ -1,6 +1,6 @@
1
1
  import type { SnapshotStore } from '@deepseek-ai/dsh-client-store';
2
2
  import type { ModelDirectoryState } from '@deepseek-ai/dsh-client-ui-model-selection/client';
3
- import type { GoUsage } from '../usage-contract.ts';
3
+ import { type GoUsage } from '../usage-contract.ts';
4
4
  import type { SettingsScope } from './settings.ts';
5
5
  import type { OpencodeGoSettings } from './section-controller.ts';
6
6
  export interface UsagePillProps {
@@ -9,6 +9,8 @@ export interface UsagePillProps {
9
9
  readUsage: () => Promise<GoUsage>;
10
10
  t: (key: string) => string;
11
11
  getLocale?: () => string;
12
+ credentialChanges?: SnapshotStore<number>;
13
+ selectAccount?: (ref: string) => Promise<boolean>;
12
14
  }
13
15
  /** Only a visible, enabled pill mounts the usage poller. */
14
- export declare function UsagePill({ directory, settings, ...props }: UsagePillProps): import("react").JSX.Element | null;
16
+ export declare function UsagePill({ directory, settings, credentialChanges, ...props }: UsagePillProps): import("react").JSX.Element | null;
@@ -0,0 +1,80 @@
1
+ import type { Context } from '@deepseek-ai/cordis';
2
+ import { type AccountSettings, type GoAccount } from '../accounts.ts';
3
+ import type { GoUsage } from '../usage-contract.ts';
4
+ import type { SettingsScope } from './settings.ts';
5
+ export interface GoAccountView extends GoAccount {
6
+ configured?: boolean;
7
+ writable?: boolean;
8
+ usage?: GoUsage;
9
+ updatedAt?: number;
10
+ stale?: boolean;
11
+ loading?: boolean;
12
+ failed?: boolean;
13
+ /** Why the last quota read failed, safe to show: it carries no credential value. */
14
+ problem?: string;
15
+ }
16
+ export interface GoAccountsState {
17
+ entries: readonly GoAccountView[];
18
+ activeRef: string;
19
+ autoSwitch: boolean;
20
+ busy: boolean;
21
+ blocked: boolean;
22
+ refreshing: boolean;
23
+ failure?: 'write' | 'cleanup' | 'remove' | 'read';
24
+ }
25
+ export interface GoAccountsActions {
26
+ loadAccounts: () => void;
27
+ addAccount: (name: string, key: string) => Promise<boolean>;
28
+ renameAccount: (ref: string, name: string) => Promise<boolean>;
29
+ removeAccount: (ref: string) => Promise<boolean>;
30
+ selectAccount: (ref: string) => Promise<boolean>;
31
+ setAutoSwitch: (next: boolean) => Promise<boolean>;
32
+ replaceAccountKey: (ref: string, key: string) => Promise<boolean>;
33
+ /** Move one account to a new position; the first row becomes the preferred account. */
34
+ moveAccount: (ref: string, toIndex: number) => Promise<boolean>;
35
+ }
36
+ /** Immediate account operations, separate from the page's staged tuning form. */
37
+ export declare class GoAccountsController {
38
+ private readonly scope;
39
+ private readonly ctx;
40
+ private readonly readUsage;
41
+ private readonly publish;
42
+ private readonly blocked;
43
+ private rows;
44
+ private busy;
45
+ private refreshing;
46
+ private failure;
47
+ private epoch;
48
+ private identity;
49
+ private loaded;
50
+ private disposed;
51
+ constructor(scope: SettingsScope<AccountSettings & {
52
+ baseURL?: string;
53
+ proxyURL?: string;
54
+ }>, ctx: Context, readUsage: (ref: string) => Promise<GoUsage>, publish: () => void, blocked: () => boolean);
55
+ snapshot(): GoAccountsState;
56
+ sync(): void;
57
+ dispose(): void;
58
+ invalidate(ref: string): void;
59
+ refresh(): Promise<void>;
60
+ /** Mark every account row as unreadable with the Host's own diagnostic. */
61
+ private markUnreadable;
62
+ actions(): GoAccountsActions;
63
+ /**
64
+ * Reorder the visible accounts and keep the preferred reference on the first row.
65
+ * The adapter tries the preferred reference first and the rest in array order, so
66
+ * one write is what makes top-to-bottom the real call order. A placeholder row the
67
+ * settings never stored is materialized here, which its `legacy:` id admits.
68
+ */
69
+ private move;
70
+ private account;
71
+ private mutate;
72
+ private add;
73
+ /** Loaded rows answer from cache; anything they do not know is described on
74
+ * the spot, so a placeholder decision never races the page's first describe. */
75
+ private configuredOf;
76
+ private rename;
77
+ private select;
78
+ private remove;
79
+ private run;
80
+ }
@@ -1,8 +1,49 @@
1
1
  /** Copy dictionaries for the OpenCode Go settings page. English is the key-set source of truth. */
2
2
  export declare const en: {
3
+ accountsTitle: string;
4
+ accountsRefresh: string;
5
+ accountsBlocked: string;
6
+ accountsEmpty: string;
7
+ accountsWriteFailed: string;
8
+ accountsReadFailed: string;
9
+ accountsCleanupFailed: string;
10
+ accountsRemoveKeyFailed: string;
11
+ accountsStatusUnknown: string;
12
+ accountDefault: string;
13
+ accountAdd: string;
14
+ accountRename: string;
15
+ accountReplaceKey: string;
16
+ accountRemove: string;
17
+ accountRemoveHint: string;
18
+ accountName: string;
19
+ accountKeyHint: string;
20
+ accountConfirm: string;
21
+ accountCancel: string;
22
+ accountAutoSwitch: string;
23
+ accountAutoSwitchHint: string;
24
+ accountPreferredTag: string;
25
+ accountSwitchAction: string;
26
+ accountSwitchTitle: string;
27
+ accountSwitchBack: string;
28
+ accountSwitchHint: string;
29
+ accountSwitchFailed: string;
30
+ accountFallbackQuota: string;
31
+ accountFallbackCredential: string;
32
+ accountsSummary: string;
33
+ accountsSummaryEmpty: string;
34
+ accountsAvailability: string;
35
+ accountsAvailabilityFailed: string;
36
+ accountsDetails: string;
37
+ accountsDetailsHide: string;
38
+ accountDragHandle: string;
39
+ accountConfigureHint: string;
40
+ usageResetMinutes: string;
41
+ usageResetHours: string;
42
+ usageResetDays: string;
43
+ usageResetDue: string;
44
+ usageResetUnknown: string;
3
45
  usageTitle: string;
4
46
  usageRollingShort: string;
5
- usageHint: string;
6
47
  usageWeekShort: string;
7
48
  usage_rolling: string;
8
49
  usage_weekly: string;
@@ -12,6 +53,7 @@ export declare const en: {
12
53
  usageLoading: string;
13
54
  usageUnavailable: string;
14
55
  usageStaleShort: string;
56
+ usageFallbackShort: string;
15
57
  usageStaleHint: string;
16
58
  usageRefreshFailed: string;
17
59
  usageLastUpdated: string;
@@ -101,6 +143,9 @@ export declare const en: {
101
143
  apiKeyEnvHint: string;
102
144
  baseURLLabel: string;
103
145
  baseURLHint: string;
146
+ proxyURLLabel: string;
147
+ proxyURLHint: string;
148
+ proxyURLInvalid: string;
104
149
  refreshMinutesLabel: string;
105
150
  refreshMinutesHint: string;
106
151
  streamIdleTimeoutMsLabel: string;
@@ -14,6 +14,8 @@ import type { GoModel, GoModelCatalog } from '../models-contract.ts';
14
14
  import { type UsageDisplayMode } from '../usage-display.ts';
15
15
  import type { SnapshotStore } from '@deepseek-ai/dsh-client-store';
16
16
  import type { SettingsScope } from './settings.ts';
17
+ import type { GoAccount } from '../accounts.ts';
18
+ import { type GoAccountsState, type GoAccountsActions } from './accounts-controller.ts';
17
19
  import { type FieldState, type FormActions, type FormShell } from './staged-form.ts';
18
20
  /** Namespace of the OpenCode Go adapter. Spelled here rather than imported: a client package must not depend on a Host package. */
19
21
  export declare const OPENCODE_GO_NS = "llm-opencode-go";
@@ -27,8 +29,12 @@ export interface OpencodeGoSettings {
27
29
  modelVisibility?: Record<string, boolean>;
28
30
  /** Credential reference naming the environment key. */
29
31
  apiKeyEnv?: string;
32
+ accounts?: GoAccount[] | null;
33
+ autoSwitch?: boolean;
30
34
  /** The gateway endpoint; also the live listing base. */
31
35
  baseURL?: string;
36
+ /** Optional network proxy used by the Host. */
37
+ proxyURL?: string;
32
38
  /** Live catalog re-resolution interval, in minutes. */
33
39
  refreshMinutes?: number;
34
40
  /** Largest idle gap between stream events, in milliseconds. */
@@ -82,6 +88,7 @@ export type OpencodeGoModels =
82
88
  };
83
89
  /** What the settings page renders. */
84
90
  export interface OpencodeGoSectionState extends FormShell {
91
+ accounts?: GoAccountsState;
85
92
  /**
86
93
  * Whether the adapter currently serves its route. Resolved from the section
87
94
  * rather than staged: the switch writes on the click that flips it, because
@@ -96,6 +103,7 @@ export interface OpencodeGoSectionState extends FormShell {
96
103
  apiKeyEnv: FieldState;
97
104
  /** The gateway endpoint. */
98
105
  baseURL: FieldState;
106
+ proxyURL: FieldState;
99
107
  /** Live catalog re-resolution interval, in minutes. */
100
108
  refreshMinutes: FieldState;
101
109
  /** Largest idle gap between stream events, in milliseconds. */
@@ -122,7 +130,7 @@ export interface OpencodeGoSectionState extends FormShell {
122
130
  modelLimitDraft: OpencodeGoModelLimits;
123
131
  }
124
132
  /** The registration-side face the page's slot entry injects. */
125
- export interface OpencodeGoSectionFace extends FormActions {
133
+ export interface OpencodeGoSectionFace extends FormActions, GoAccountsActions {
126
134
  hooks: {
127
135
  /** Page snapshot bound by the UI renderer as useOpencodeGo. */
128
136
  opencodeGo: SnapshotStore<OpencodeGoSectionState>;
@@ -150,12 +158,15 @@ export declare class OpencodeGoSectionController {
150
158
  private pickerFailed;
151
159
  private face;
152
160
  private readonly unsubscribe;
161
+ private accounts;
162
+ private credentialRequest;
163
+ private keyDraftRef;
153
164
  /**
154
165
  * @param scope - the bound settings scope for the `llm-opencode-go` namespace.
155
166
  * @param ctx - the page plugin's context, whose `remote.credentials` namespace
156
167
  * answers for the credential the section references.
157
168
  */
158
- constructor(scope: SettingsScope<OpencodeGoSettings>, ctx: ClientContext, readModels?: () => Promise<RemoteResult<GoModelCatalog>>);
169
+ constructor(scope: SettingsScope<OpencodeGoSettings>, ctx: ClientContext, readModels?: () => Promise<RemoteResult<GoModelCatalog>>, readUsage?: (ref: string) => Promise<import('../usage-contract.ts').GoUsage>);
159
170
  /** Release subscriptions without disposing the host's shared form. */
160
171
  dispose(): void;
161
172
  private projection;
@@ -191,5 +191,13 @@ export declare class StagedForm {
191
191
  private baseValue;
192
192
  private userLayer;
193
193
  private stored;
194
+ /**
195
+ * Whether a draft already equals the field's effective value, so a save would
196
+ * write nothing. The save plan and the override badge both answer for it.
197
+ * @param field - field name inside the namespace section.
198
+ * @param staged - the staged edit to test.
199
+ * @returns true when the draft is a no-op; a clear is never one.
200
+ */
201
+ private unchangedDraft;
194
202
  private publish;
195
203
  }
@@ -10,6 +10,7 @@
10
10
  */
11
11
  import z from '@deepseek-ai/schemastery';
12
12
  import { type UsageDisplayMode } from './usage-display.ts';
13
+ import { type GoAccount } from './accounts.ts';
13
14
  /** Environment variable resolving the OpenCode API key. */
14
15
  export declare const DEFAULT_API_KEY_ENV = "OPENCODE_API_KEY";
15
16
  /** Successful refresh lifetime; failed refreshes retry sooner and explicit discovery revalidates immediately. */
@@ -45,8 +46,13 @@ export interface OpencodeGoConfig {
45
46
  modelVisibility?: Record<string, boolean>;
46
47
  /** Credential reference: the environment variable the key resolves from. */
47
48
  apiKeyEnv: string;
49
+ accounts?: GoAccount[] | null;
50
+ /** Try other saved accounts on quota/credential rejection before any content is emitted. */
51
+ autoSwitch?: boolean;
48
52
  /** The gateway endpoint; also the base of the live model listing. */
49
53
  baseURL: string;
54
+ /** Optional HTTP(S) or SOCKS5 proxy; blank uses the default network transport. */
55
+ proxyURL: string;
50
56
  /** Request/picker cache lifetime in minutes; explicit discovery bypasses it. */
51
57
  refreshMinutes: number;
52
58
  /** Largest idle gap between stream events before the request fails. */
@@ -41,6 +41,7 @@ export { OpencodeGoAdapter } from './adapter.ts';
41
41
  export type { OpencodeGoAdapterOptions, OpencodeGoImageAccess } from './adapter.ts';
42
42
  export { DEFAULT_BASE_URL, DISPLAY_NAME, PROVIDER_ID, OpencodeGoCatalog, discoverCatalogModels, readLiveModelIds, } from './catalog.ts';
43
43
  export { Config, PlainConfig, assertBaseURL } from './config.ts';
44
+ export { assertProxyURL } from './proxy-url.ts';
44
45
  export type { OpencodeGoConfig } from './config.ts';
45
46
  export declare const name = "llm-opencode-go";
46
47
  export declare const inject: string[];
@@ -3,7 +3,7 @@ export declare function transportFailure(error: unknown): string;
3
3
  /** Keep the endpoint useful in diagnostics without user information or query secrets. */
4
4
  export declare function diagnosticURL(raw: string): string;
5
5
  /** The caller's signal covers both attempts, the retry delay, and all response reads. */
6
- export declare function fetchJsonResponse(url: string, init: RequestInit, maxBytes: number, encoding?: 'identity' | 'gzip'): Promise<{
6
+ export declare function fetchJsonResponse(url: string, init: RequestInit, maxBytes: number, encoding?: 'identity' | 'gzip', fetcher?: typeof globalThis.fetch): Promise<{
7
7
  response: Response;
8
8
  body: unknown;
9
9
  }>;
@@ -0,0 +1,2 @@
1
+ /** Shared by Host validation and the browser form; never echo proxy credentials. */
2
+ export declare function assertProxyURL(raw: string | undefined): string;
@@ -0,0 +1,11 @@
1
+ /** Per-mount transport. Fetch closures retain their address across settings changes. */
2
+ export declare class ProxyTransport {
3
+ private current;
4
+ private readonly retired;
5
+ private disposed;
6
+ forProxy(raw?: string): typeof globalThis.fetch | undefined;
7
+ /** Close replaced pools after their in-flight response bodies have finished. */
8
+ private retire;
9
+ /** Unloading the mount cancels remaining requests and releases every pool. */
10
+ dispose(): Promise<void>;
11
+ }
@@ -1,4 +1,5 @@
1
1
  import type { RemoteResult, TypertRemoteContribution } from '@deepseek-ai/dsh-typert-protocol';
2
+ import type { GoAccountSwitch } from './accounts.ts';
2
3
  export interface UsageWindow {
3
4
  status: 'ok' | 'rate-limited';
4
5
  percent: number;
@@ -7,10 +8,12 @@ export interface UsageWindow {
7
8
  export interface GoUsage {
8
9
  /** Opaque Host identity for this endpoint/account; never a credential or its hash. */
9
10
  source?: string;
11
+ lastSwitch?: GoAccountSwitch;
10
12
  rolling: UsageWindow;
11
13
  weekly: UsageWindow;
12
14
  monthly: UsageWindow;
13
15
  }
16
+ export declare function parseAccountSwitch(value: unknown): GoAccountSwitch;
14
17
  /** Reject missing statistics rather than turning unavailable data into zero. */
15
18
  export declare function parseGoUsage(value: unknown): GoUsage;
16
19
  declare module '@deepseek-ai/dsh-typert-protocol' {
@@ -19,11 +22,13 @@ declare module '@deepseek-ai/dsh-typert-protocol' {
19
22
  readonly retryable: boolean;
20
23
  readonly retainPrevious: boolean;
21
24
  readonly source?: string;
25
+ readonly lastSwitch?: GoAccountSwitch;
22
26
  };
23
27
  }
24
28
  interface TypertRemoteNamespaceMap {
25
29
  opencodeGoUsage: {
26
30
  read(): Promise<RemoteResult<GoUsage>>;
31
+ readAccount(ref: string): Promise<RemoteResult<GoUsage>>;
27
32
  };
28
33
  }
29
34
  }
@@ -1,15 +1,27 @@
1
1
  import type { Context } from '@deepseek-ai/cordis';
2
2
  import { TypertRemoteService } from '@deepseek-ai/dsh-typert-protocol';
3
3
  import { type GoUsage } from './usage-contract.ts';
4
+ import type { GoAccountSwitch } from './accounts.ts';
5
+ import { ProxyTransport } from './proxy.ts';
4
6
  interface UsageOptions {
5
7
  baseURL: () => string;
6
- resolveApiKey: () => Promise<string | undefined>;
8
+ proxyURL?: () => string;
9
+ transport?: ProxyTransport;
10
+ resolveApiKey: (ref?: string) => Promise<string | undefined>;
11
+ activeRef?: () => string;
12
+ accountRefs?: () => readonly string[];
13
+ lastSwitch?: () => GoAccountSwitch | undefined;
7
14
  }
8
15
  /** Account statistics are fetched on the Host; credentials never enter the browser. */
9
16
  export declare class GoUsageService extends TypertRemoteService {
10
17
  private readonly options;
11
- private identity?;
18
+ private readonly identities;
19
+ private readonly pending;
20
+ private readonly transport;
12
21
  constructor(ctx: Context, options: UsageOptions);
13
22
  read(): Promise<GoUsage>;
23
+ readAccount(ref: string): Promise<GoUsage>;
24
+ private readRef;
25
+ private fetchUsage;
14
26
  }
15
27
  export {};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "dsh-opencode-go",
3
- "version": "0.1.19",
3
+ "version": "0.1.21",
4
4
  "description": "OpenCode Go model provider and settings UI for DeepSeek Harness",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -34,6 +34,7 @@
34
34
  "cordis.patch.yml",
35
35
  "THIRD_PARTY_NOTICES.md",
36
36
  "docs",
37
+ "!docs/multi-account-review-plan.md",
37
38
  "examples"
38
39
  ],
39
40
  "dsh": {
@@ -89,7 +90,8 @@
89
90
  "dependencies": {
90
91
  "@deepseek-ai/dsh-brand": "0.1.6-alpha.1",
91
92
  "@deepseek-ai/schemastery": "3.18.3",
92
- "opencode-go-pi-ai": "npm:@earendil-works/pi-ai@0.87.1"
93
+ "opencode-go-pi-ai": "npm:@earendil-works/pi-ai@0.87.1",
94
+ "undici": "7.30.0"
93
95
  },
94
96
  "devDependencies": {
95
97
  "@deepseek-ai/cordis": "4.0.2",