@addozhang/dsh-discord 0.6.4 → 0.6.5-rc.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -36,17 +36,19 @@ No extra process: the adapter is a DSH plugin that mounts straight onto your `ds
36
36
 
37
37
  ## Versions
38
38
 
39
- Two channels ship in parallel, each pinned to the dsh host surface it was verified against. Pick the adapter and the dsh CLI from the same row:
39
+ Two channels ship in parallel, each following the dsh host surface it was verified against. Pick the adapter and the dsh CLI from the same row:
40
40
 
41
41
  | Channel | Adapter | dsh CLI | Install |
42
42
  |---|---|---|---|
43
- | **stable (0.2.1 line)** | `0.6.4` — npm `latest` | `0.2.1-rc.3`+ — npm `latest`/`next` | `dsh plugin --profile web add @addozhang/dsh-discord` |
44
- | **next (0.2.1 line)** | `>=0.6.1-rc.1` — npm `next` | `0.2.1-rc.3`+ — npm `latest`/`next` | `dsh plugin --profile web add @addozhang/dsh-discord@next` |
43
+ | **stable (0.2.1 line)** | `0.6.5` — npm `latest` | `0.2.1-rc.3`+ — npm `latest`/`next` | `dsh plugin --profile web add @addozhang/dsh-discord` |
44
+ | **next (0.2.1 line)** | `>=0.6.5-rc.1` — npm `next` | `0.2.1-rc.3`+ — npm `latest`/`next` | `dsh plugin --profile web add @addozhang/dsh-discord@next` |
45
45
  | Legacy (0.1.7 line) | `0.5.0` — exact version | `0.1.7-rc.1` — exact version | `dsh plugin --profile web add @addozhang/dsh-discord@0.5.0` |
46
46
 
47
- - **The rows do not mix.** Adapter `0.6.1+` carries runtime dependencies (`dsh-storage-domain`/`dsh-credentials`) pinned to the dsh `0.2.1` line — on any other host line the exact-version compatibility gate disables them (the storageDomain service never arrives and the plugin stays inactive); adapter `0.6.0-rc.1` is the `0.2.0-rc.2` pairing (both sides are exact-version installs now that the dist-tags moved to 0.2.1), and adapter `0.5.0` pins the `0.1.7` line symmetrically. Adapter `>=0.5.0-rc.4` (including `0.5.0`) speaks the 0.1.7 profile-backed settings forms and controller services and will not load on older hosts (the startup probe refuses with one actionable diagnostic); `0.5.0-rc.1`–`rc.3` target dsh `0.1.6-alpha`; adapter `0.4.x` talks to the former `apiProxy` surface, which `0.1.6-alpha` removed — it remains the pairing for the dsh `0.1.5` stable line, reachable by exact version (e.g. `@addozhang/dsh-discord@0.4.0`). A mismatched pair fails at startup.
48
- - To switch the dsh CLI line: `npm install -g @deepseek-ai/dsh@latest` (0.2.1-rc.x, pairs with adapter 0.6.1+) or `npm install -g @deepseek-ai/dsh@0.1.7-rc.1` (pairs with adapter 0.5.0).
49
- - Right after a `next` release, the `@next` spec can resolve to a stale cached version. If the installed copy looks old, install by exact version instead (e.g. `@addozhang/dsh-discord@0.5.0-rc.4`) and verify the `version` field inside the profile's `node_modules`.
47
+ - **Adapter `0.6.5+` ships no dsh-internal packages.** The `dsh-storage-domain` declaration helpers (`defineDomain`/`domainTable`) are mirrored inside the plugin, and the host's `storageDomain` service is consumed through a structural contract. Upgrading the dsh CLI or Desktop within the 0.2.1 line (including the exact-version plugin gate introduced in `0.2.1-rc.5`) therefore no longer disables this plugin. The host API surface is still guarded by the startup probe — a host lacking a required service surface refuses activation with one actionable diagnostic.
48
+ - **Existing installs of adapter `0.6.1`–`0.6.4`:** those versions carried `dsh-storage-domain@0.2.1-rc.3` as a runtime dependency. Since dsh `0.2.1-rc.5` the host disables any profile-tree plugin row whose version does not exactly match the runtime — the carried copy shadows the host's own, the `storageDomain` service vanishes, and the plugin stays pending (no workspaces or sessions in the UI; data is untouched). Upgrade the adapter to `0.6.5+` to fix it. If you manually added a `@deepseek-ai/dsh-storage-domain` entry to the profile's `package.json` as a stopgap, remove it too — it will trip the same gate on the next host upgrade.
49
+ - Earlier pairings are unchanged: adapter `0.6.0-rc.1` ↔ dsh `0.2.0-rc.2` (both sides are exact-version installs now that the dist-tags moved to 0.2.1), and adapter `0.5.0` pins the `0.1.7-rc.1` line symmetrically. Adapter `>=0.5.0-rc.4` (including `0.5.0`) speaks the 0.1.7 profile-backed settings forms and controller services and will not load on older hosts (the startup probe refuses with one actionable diagnostic); `0.5.0-rc.1`–`rc.3` target dsh `0.1.6-alpha`; adapter `0.4.x` talks to the former `apiProxy` surface, which `0.1.6-alpha` removed — it remains the pairing for the dsh `0.1.5` stable line, reachable by exact version (e.g. `@addozhang/dsh-discord@0.4.0`).
50
+ - To switch the dsh CLI line: `npm install -g @deepseek-ai/dsh@latest` (0.2.1-rc.x, pairs with adapter 0.6.5+) or `npm install -g @deepseek-ai/dsh@0.1.7-rc.1` (pairs with adapter 0.5.0).
51
+ - Right after a `next` release, the `@next` spec can resolve to a stale cached version. If the installed copy looks old, install by exact version instead (e.g. `@addozhang/dsh-discord@0.6.5-rc.1`) and verify the `version` field inside the profile's `node_modules`.
50
52
 
51
53
  ## Install
52
54
 
package/README.zh.md CHANGED
@@ -36,17 +36,19 @@
36
36
 
37
37
  ## 版本支持
38
38
 
39
- 两条通道并行发布,各自钉在经过真机验证的 dsh 宿主面上。适配器与 dsh CLI 请取同一行:
39
+ 两条通道并行发布,各自跟随经过真机验证的 dsh 宿主面。适配器与 dsh CLI 请取同一行:
40
40
 
41
41
  | 通道 | 适配器 | dsh CLI | 安装命令 |
42
42
  |---|---|---|---|
43
- | **stable(0.2.1 线)** | `0.6.4` — npm `latest` | `0.2.1-rc.3`+ — npm `latest`/`next` | `dsh plugin --profile web add @addozhang/dsh-discord` |
44
- | **next(0.2.1 线)** | `>=0.6.1-rc.1` — npm `next` | `0.2.1-rc.3`+ — npm `latest`/`next` | `dsh plugin --profile web add @addozhang/dsh-discord@next` |
43
+ | **stable(0.2.1 线)** | `0.6.5` — npm `latest` | `0.2.1-rc.3`+ — npm `latest`/`next` | `dsh plugin --profile web add @addozhang/dsh-discord` |
44
+ | **next(0.2.1 线)** | `>=0.6.5-rc.1` — npm `next` | `0.2.1-rc.3`+ — npm `latest`/`next` | `dsh plugin --profile web add @addozhang/dsh-discord@next` |
45
45
  | 旧线(0.1.7) | `0.5.0` — 精确版本号 | `0.1.7-rc.1` — 精确版本号 | `dsh plugin --profile web add @addozhang/dsh-discord@0.5.0` |
46
46
 
47
- - **两行不可混搭。** 适配器 `0.6.1+` 携带的运行时依赖(`dsh-storage-domain`/`dsh-credentials`)钉在 dsh `0.2.1` 线——装到其它宿主线会被宿主的精确版本兼容门禁用(storageDomain 服务缺失,插件保持未激活);适配器 `0.6.0-rc.1` 是 `0.2.0-rc.2` 的配对(dist-tags 已移到 0.2.1,两侧都只能精确版本号安装),适配器 `0.5.0` 同理反向钉在 `0.1.7` 线。适配器 `>=0.5.0-rc.4`(含 `0.5.0`)使用 0.1.7 的 profile-backed settings forms 与控制器服务,在更旧的宿主上无法加载(startup 探针会给出一条可操作的诊断后拒绝激活);`0.5.0-rc.1`–`rc.3` 对应 dsh `0.1.6-alpha`;适配器 `0.4.x` 使用旧版 `apiProxy` 宿主面(该面已在 `0.1.6-alpha` 中移除)——它仍是 dsh `0.1.5` stable 线的配对,可用精确版本号安装(如 `@addozhang/dsh-discord@0.4.0`)。错配会在启动时失败。
48
- - 切换 dsh CLI 通道:`npm install -g @deepseek-ai/dsh@latest`(0.2.1-rc.x,配适配器 0.6.1+)或 `npm install -g @deepseek-ai/dsh@0.1.7-rc.1`(配适配器 0.5.0)。
49
- - `next` 刚发版后,`@next` 规格可能解析到过期的缓存版本。若装到的版本偏旧,请改用精确版本号安装(如 `@addozhang/dsh-discord@0.5.0-rc.4`),并核对 profile `node_modules` 中的 `version` 字段。
47
+ - **适配器 `0.6.5+` 不再随包携带任何 dsh 内部包**:`dsh-storage-domain` 的声明辅助(`defineDomain`/`domainTable`)已内联进插件,宿主的 `storageDomain` 服务按结构化契约消费。因此 dsh CLI / Desktop 在 0.2.1 线内升级(含 `0.2.1-rc.5` 起生效的插件精确版本兼容门)不会再禁用本插件。宿主 API 面仍由 startup 探针守护——宿主缺少所需服务面时拒绝激活并给出一条可操作诊断。
48
+ - **适配器 `0.6.1`–`0.6.4` 的存量安装注意:** 这些版本把 `dsh-storage-domain@0.2.1-rc.3` 作为运行时依赖随包携带。dsh `0.2.1-rc.5` 起宿主会禁用 profile 树中与运行时版本不精确匹配的插件行——被携带的副本盖住宿主副本后,`storageDomain` 服务随之消失,插件保持 pending(UI 里既无工作区也无会话,数据无损)。把适配器升级到 `0.6.5+` 即修复;若曾在 profile 的 `package.json` 里手工添加过 `@deepseek-ai/dsh-storage-domain` 条目(一种临时缓解),请一并移除——否则下一次宿主升级它会自己撞上同一道门禁。
49
+ - 更早的配对关系不变:适配器 `0.6.0-rc.1` ↔ dsh `0.2.0-rc.2`(dist-tags 已移到 0.2.1,两侧都只能精确版本号安装),适配器 `0.5.0` 同理反向钉在 `0.1.7-rc.1` 线;适配器 `>=0.5.0-rc.4`(含 `0.5.0`)使用 0.1.7 的 profile-backed settings forms 与控制器服务,在更旧的宿主上无法加载(startup 探针会给出一条可操作的诊断后拒绝激活);`0.5.0-rc.1`–`rc.3` 对应 dsh `0.1.6-alpha`;适配器 `0.4.x` 使用旧版 `apiProxy` 宿主面(该面已在 `0.1.6-alpha` 中移除)——它仍是 dsh `0.1.5` stable 线的配对,可用精确版本号安装(如 `@addozhang/dsh-discord@0.4.0`)。
50
+ - 切换 dsh CLI 通道:`npm install -g @deepseek-ai/dsh@latest`(0.2.1-rc.x,配适配器 0.6.5+)或 `npm install -g @deepseek-ai/dsh@0.1.7-rc.1`(配适配器 0.5.0)。
51
+ - `next` 刚发版后,`@next` 规格可能解析到过期的缓存版本。若装到的版本偏旧,请改用精确版本号安装(如 `@addozhang/dsh-discord@0.6.5-rc.1`),并核对 profile `node_modules` 中的 `version` 字段。
50
52
 
51
53
  ## 安装
52
54
 
@@ -5,7 +5,38 @@
5
5
  * scan space from parsed parts. The spec is declared once with
6
6
  * `defineDomain`, which fails loud at module load on any naming or version
7
7
  * misconfiguration.
8
+ *
9
+ * 16.106: `defineDomain`/`domainTable` are mirrored here instead of imported.
10
+ * Shipping `@deepseek-ai/dsh-storage-domain` as a plugin dependency made pnpm
11
+ * hoist a plugin-owned copy over the profile tree, and the host's
12
+ * exact-version compatibility gate (0.2.1-rc.5+) then disabled that row on
13
+ * every host patch release — cascading `storageDomain` away and pending the
14
+ * workspace/session graph. `dsh-base` already provides the row at the host's
15
+ * exact version, and the host's `open()` consumes a spec purely structurally
16
+ * (property reads plus `.parse`/`.safeParse` on the caller's own zod
17
+ * schemas), so an inlined spec is indistinguishable from a package-built one.
18
+ * The mirror is kept honest by `test/state-domain.test.ts`, which checks it
19
+ * against the real package (a devDependency) accept-for-accept and
20
+ * reject-for-reject. Types still come from the package — compile-time only.
8
21
  */
22
+ import type { DomainSpec, DomainTableSpec } from '@deepseek-ai/dsh-storage-domain';
23
+ import type { ZodType } from 'zod';
24
+ /**
25
+ * Declare one table. Mirrored from `@deepseek-ai/dsh-storage-domain`: the
26
+ * runtime value is the plain `{ valueSchema }` pair — the key type is a
27
+ * compile-time phantom that never exists at runtime.
28
+ */
29
+ export declare function domainTable<K extends string, V>(schema: ZodType<V>): DomainTableSpec<K, V>;
30
+ /**
31
+ * Identity helper that pins a spec's literal types and validates its fields.
32
+ * Mirrored from `@deepseek-ai/dsh-storage-domain` (0.2.1 line): misconfiguration
33
+ * fails loud at the owning package's module load, before any medium is
34
+ * touched — a domain or table name outside `UNIT_NAME_RE`, a version that is
35
+ * not a non-negative integer, or a global schema that accepts `null` all
36
+ * throw. Keep the checks and messages in sync with upstream;
37
+ * `test/state-domain.test.ts` drift-guards the equivalence.
38
+ */
39
+ export declare function defineDomain<S extends DomainSpec>(spec: S): S;
9
40
  /**
10
41
  * Storage-legal domain name (`UNIT_NAME_RE` allows only lowercase, digits,
11
42
  * and underscores) and the current format version; a medium stamped with a
@@ -42,13 +73,13 @@ export declare const discordDomainSpec: {
42
73
  name: string;
43
74
  version: number;
44
75
  tables: {
45
- channel_bindings: import("@deepseek-ai/dsh-storage-domain").DomainTableSpec<"channel", {
76
+ channel_bindings: DomainTableSpec<"channel", {
46
77
  workspaceId: string;
47
78
  revision: number;
48
79
  boundBy: string;
49
80
  boundAtMs: number;
50
81
  }>;
51
- thread_bindings: import("@deepseek-ai/dsh-storage-domain").DomainTableSpec<"thread", {
82
+ thread_bindings: DomainTableSpec<"thread", {
52
83
  sessionId: string;
53
84
  workspaceId: string;
54
85
  revision: number;
@@ -56,7 +87,7 @@ export declare const discordDomainSpec: {
56
87
  createdAtMs: number;
57
88
  renderedSeq?: number | undefined;
58
89
  }>;
59
- inbound_intents: import("@deepseek-ai/dsh-storage-domain").DomainTableSpec<"intent", {
90
+ inbound_intents: DomainTableSpec<"intent", {
60
91
  contentHash: string;
61
92
  state: "claimed" | "unknown" | "succeeded" | "failed";
62
93
  claimedAtMs: number;
@@ -5,9 +5,73 @@
5
5
  * scan space from parsed parts. The spec is declared once with
6
6
  * `defineDomain`, which fails loud at module load on any naming or version
7
7
  * misconfiguration.
8
+ *
9
+ * 16.106: `defineDomain`/`domainTable` are mirrored here instead of imported.
10
+ * Shipping `@deepseek-ai/dsh-storage-domain` as a plugin dependency made pnpm
11
+ * hoist a plugin-owned copy over the profile tree, and the host's
12
+ * exact-version compatibility gate (0.2.1-rc.5+) then disabled that row on
13
+ * every host patch release — cascading `storageDomain` away and pending the
14
+ * workspace/session graph. `dsh-base` already provides the row at the host's
15
+ * exact version, and the host's `open()` consumes a spec purely structurally
16
+ * (property reads plus `.parse`/`.safeParse` on the caller's own zod
17
+ * schemas), so an inlined spec is indistinguishable from a package-built one.
18
+ * The mirror is kept honest by `test/state-domain.test.ts`, which checks it
19
+ * against the real package (a devDependency) accept-for-accept and
20
+ * reject-for-reject. Types still come from the package — compile-time only.
8
21
  */
9
- import { defineDomain, domainTable } from '@deepseek-ai/dsh-storage-domain';
10
22
  import { ChannelBindingRecord, InboundIntentRecordSchema, ThreadBindingRecord } from './records.js';
23
+ /**
24
+ * Storage-legal unit name, mirrored from `@deepseek-ai/dsh-storage`
25
+ * (`UNIT_NAME_RE`): lowercase, digits, underscores, leading letter.
26
+ */
27
+ const UNIT_NAME_RE = /^[a-z][a-z0-9_]*$/;
28
+ /**
29
+ * Declare one table. Mirrored from `@deepseek-ai/dsh-storage-domain`: the
30
+ * runtime value is the plain `{ valueSchema }` pair — the key type is a
31
+ * compile-time phantom that never exists at runtime.
32
+ */
33
+ export function domainTable(schema) {
34
+ return { valueSchema: schema };
35
+ }
36
+ /**
37
+ * Identity helper that pins a spec's literal types and validates its fields.
38
+ * Mirrored from `@deepseek-ai/dsh-storage-domain` (0.2.1 line): misconfiguration
39
+ * fails loud at the owning package's module load, before any medium is
40
+ * touched — a domain or table name outside `UNIT_NAME_RE`, a version that is
41
+ * not a non-negative integer, or a global schema that accepts `null` all
42
+ * throw. Keep the checks and messages in sync with upstream;
43
+ * `test/state-domain.test.ts` drift-guards the equivalence.
44
+ */
45
+ export function defineDomain(spec) {
46
+ const candidate = spec;
47
+ if (!UNIT_NAME_RE.test(candidate.name))
48
+ throw new Error(`domain name '${candidate.name}' must match ${String(UNIT_NAME_RE)}`);
49
+ if (!Number.isInteger(candidate.version) || candidate.version < 0)
50
+ throw new Error(`domain '${candidate.name}' version must be a non-negative integer, got ${String(candidate.version)}`);
51
+ for (const compat of candidate.compatibleVersions ?? []) {
52
+ if (!Number.isInteger(compat) || compat < 0 || compat >= candidate.version) {
53
+ throw new Error(`domain '${candidate.name}' compatibleVersions entries must be non-negative integers below version ${String(candidate.version)}, got ${String(compat)}`);
54
+ }
55
+ }
56
+ if (candidate.layout !== undefined) {
57
+ const layout = candidate.layout;
58
+ if (layout !== 'single' && layout !== 'per-record')
59
+ throw new Error(`domain '${candidate.name}' layout must be 'single' or 'per-record', got ${layout}`);
60
+ }
61
+ if (candidate.invalidRecords !== undefined) {
62
+ const policy = candidate.invalidRecords;
63
+ if (policy !== 'backup-and-skip')
64
+ throw new Error(`domain '${candidate.name}' invalidRecords must be 'backup-and-skip' when present, got ${policy}`);
65
+ }
66
+ for (const table of Object.keys(candidate.tables)) {
67
+ if (!UNIT_NAME_RE.test(table))
68
+ throw new Error(`domain '${candidate.name}' table name '${table}' must match ${String(UNIT_NAME_RE)}`);
69
+ }
70
+ if (candidate.global !== undefined && candidate.global.schema.safeParse(null).success) {
71
+ throw new Error(`domain '${candidate.name}' global schema must not accept null: null is the medium's "never written" sentinel, so a stored null could not round-trip`);
72
+ }
73
+ return spec;
74
+ }
11
75
  /**
12
76
  * Storage-legal domain name (`UNIT_NAME_RE` allows only lowercase, digits,
13
77
  * and underscores) and the current format version; a medium stamped with a
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@addozhang/dsh-discord",
3
- "version": "0.6.4",
3
+ "version": "0.6.5-rc.1",
4
4
  "description": "Discord adapter for DeepSeek Harness · DeepSeek Harness 的 Discord 适配器",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -57,13 +57,13 @@
57
57
  },
58
58
  "devDependencies": {
59
59
  "@deepseek-ai/cordis": "4.0.5",
60
- "@deepseek-ai/dsh-client-store": "0.2.1-rc.2",
61
- "@deepseek-ai/dsh-client-ui-renderer": "0.2.1-rc.2",
62
- "@deepseek-ai/dsh-client-ui-settings": "0.2.1-rc.2",
63
- "@deepseek-ai/dsh-client-ui-slots": "0.2.1-rc.2",
64
- "@deepseek-ai/dsh-credentials": "0.2.1-rc.2",
65
- "@deepseek-ai/dsh-settings": "0.2.1-rc.2",
66
- "@deepseek-ai/dsh-storage-domain": "0.2.1-rc.2",
60
+ "@deepseek-ai/dsh-client-store": "0.2.1-rc.5",
61
+ "@deepseek-ai/dsh-client-ui-renderer": "0.2.1-rc.5",
62
+ "@deepseek-ai/dsh-client-ui-settings": "0.2.1-rc.5",
63
+ "@deepseek-ai/dsh-client-ui-slots": "0.2.1-rc.5",
64
+ "@deepseek-ai/dsh-credentials": "0.2.1-rc.5",
65
+ "@deepseek-ai/dsh-settings": "0.2.1-rc.5",
66
+ "@deepseek-ai/dsh-storage-domain": "0.2.1-rc.5",
67
67
  "@eslint/js": "9.39.1",
68
68
  "@types/node": "24.10.1",
69
69
  "@types/react": "18.3.1",
@@ -78,7 +78,6 @@
78
78
  "vitest": "4.1.11"
79
79
  },
80
80
  "dependencies": {
81
- "@deepseek-ai/dsh-storage-domain": "0.2.1-rc.3",
82
81
  "@deepseek-ai/schemastery": "3.18.5",
83
82
  "zod": "^4.4.3"
84
83
  },