dsh-ptc-plus 0.5.3 → 0.5.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.
Files changed (40) hide show
  1. package/README.en.md +1 -1
  2. package/README.md +1 -1
  3. package/client.cjs +3326 -2881
  4. package/compiler-core.cjs +127 -127
  5. package/compiler-core.cjs.map +2 -2
  6. package/docs/README.md +1 -0
  7. package/docs/capability-planning-components.md +6 -6
  8. package/docs/capability-projection.md +1 -1
  9. package/docs/capability-surface.md +133 -0
  10. package/docs/client-ui.md +17 -15
  11. package/docs/client-visual-contract.md +7 -7
  12. package/docs/installation.md +9 -2
  13. package/docs/panel-concept.md +171 -0
  14. package/docs/releases/v0.5.4.md +75 -0
  15. package/docs/runtime-reference.md +14 -0
  16. package/docs/verification.md +1 -1
  17. package/index.js +117 -30
  18. package/internal/binding-adoption.js +103 -11
  19. package/internal/capability-command-receipt.js +99 -15
  20. package/internal/capability-environment.js +1108 -348
  21. package/internal/capability-plan.js +18 -2
  22. package/internal/capability-policy.js +13 -0
  23. package/internal/capability-selection.js +330 -0
  24. package/internal/direct-surface-owner.js +17 -4
  25. package/internal/message-sources.js +21 -0
  26. package/internal/program-bindings.js +13 -4
  27. package/internal/runtime-bridge-owner.js +5 -1
  28. package/internal/runtime-config.js +10 -0
  29. package/internal/session-log-view.js +47 -5
  30. package/internal/settings-compat.js +6 -0
  31. package/internal/user-bindings-owner.js +20 -3
  32. package/package.json +45 -31
  33. package/src/client-authoring-view.js +7 -8
  34. package/src/client-capabilities-view.js +871 -948
  35. package/src/client-capability-sort.js +22 -9
  36. package/src/client-copy.js +116 -294
  37. package/src/client-settings-view.js +90 -33
  38. package/src/client-styles.js +67 -19
  39. package/src/client.js +46 -21
  40. package/internal/capability-delivery-proof.js +0 -70
@@ -2,11 +2,14 @@ import { PTC_MESSAGE_SOURCE_KIND } from './message-sources.js'
2
2
  import { sessionExecutionAvailable } from './host-tool-sdk.js'
3
3
  import { bindingToggleMessage } from './binding-toggle-receipt.js'
4
4
  import {
5
- bindingAdoptionMessage,
5
+ BINDING_ADOPTION_RECORD,
6
6
  clearedBindingAdoption,
7
7
  declinedBindingEntries,
8
8
  withBindingAdoption,
9
9
  } from './binding-adoption.js'
10
+ // Namespace import: the record writer is one public surface of the host, and the module
11
+ // load must not depend on a named export that a future release could rename.
12
+ import * as dshSession from '@deepseek-ai/dsh-session'
10
13
  import { RPC_CONTRACTS } from './rpc-contract.js'
11
14
  import { randomUUID } from 'node:crypto'
12
15
  import { dirname } from 'node:path'
@@ -232,6 +235,11 @@ export function createUserBindingsOwner(ctx, options = {}) {
232
235
  let disposed = false
233
236
  const codeConsole = new UserBindingConsole(currentOptions)
234
237
  const commandRegistrations = new Map()
238
+ // The host's writer for a fact that belongs in the log but not on the model-visible
239
+ // surface. Every supported release publishes it, so an adoption decision is taken when
240
+ // it is made instead of waiting for a step to carry a message.
241
+ const appendRecord = typeof options.appendRecord === 'function' ? options.appendRecord
242
+ : typeof dshSession.appendPluginRecord === 'function' ? dshSession.appendPluginRecord : undefined
235
243
  const sessionAgents = new Map()
236
244
  const sessionGenerations = new Map()
237
245
  const agentLifecycles = new WeakMap()
@@ -331,8 +339,17 @@ export function createUserBindingsOwner(ctx, options = {}) {
331
339
  if (session === undefined || typeof session.append !== 'function') {
332
340
  throw new Error('binding adoption requires a live session')
333
341
  }
334
- if (session.append('user/message', bindingAdoptionMessage(adoption), { surfaceOp: 'append' }) === undefined) {
335
- throw new Error('the session did not record the binding adoption decision')
342
+ if (appendRecord === undefined) {
343
+ throw new Error('ptc-plus: this DSH release publishes no plugin-record writer, so a binding adoption decision cannot be recorded')
344
+ }
345
+ // Adoption is this session's own statement and the catalog the model reads already
346
+ // reflects it, so it is taken the moment the control is used: durable through the log,
347
+ // outside the model-visible surface, and requiring no prior step. A session that cannot
348
+ // take the record reports that instead of a decision nothing stored.
349
+ try {
350
+ appendRecord(session, BINDING_ADOPTION_RECORD, adoption)
351
+ } catch (error) {
352
+ throw new Error(`the session did not record the binding adoption decision: ${error?.message ?? String(error)}`)
336
353
  }
337
354
  return { kind: 'success', text: adoptionReceipt(adoption) }
338
355
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "dsh-ptc-plus",
3
- "version": "0.5.3",
3
+ "version": "0.5.4",
4
4
  "icon": "assets/ptc-plus-icon.svg",
5
5
  "description": "A session-bound agent-native REPL for DeepSeek Harness PTC mode.",
6
6
  "type": "module",
@@ -43,7 +43,7 @@
43
43
  ],
44
44
  "engines": {
45
45
  "node": "^22.19.0 || >=24.0.0",
46
- "dsh": "*"
46
+ "dsh": ">=0.2.1-0 <0.2.3"
47
47
  },
48
48
  "allowScripts": {
49
49
  "esbuild": false
@@ -51,8 +51,8 @@
51
51
  "dependencies": {
52
52
  "@babel/code-frame": "^7.29.7",
53
53
  "@babel/parser": "^7.29.0",
54
- "@deepseek-ai/dsh-util-values": "^0.2.0-rc.2 || ^0.2.1-alpha.1",
55
- "@deepseek-ai/schemastery": "^3.18.3",
54
+ "@deepseek-ai/dsh-util-values": "^0.2.2-alpha.2",
55
+ "@deepseek-ai/schemastery": "~3.18.6-alpha.1",
56
56
  "@jridgewell/trace-mapping": "^0.3.31",
57
57
  "acorn": "^8.15.0"
58
58
  },
@@ -174,36 +174,50 @@
174
174
  "@codemirror/language": "^6.12.4",
175
175
  "@codemirror/state": "^6.7.4",
176
176
  "@codemirror/view": "^6.43.11",
177
- "@deepseek-ai/dsh": "next",
178
- "@deepseek-ai/dsh-agent-loop": "next",
179
- "@deepseek-ai/dsh-api-gateway": "next",
180
- "@deepseek-ai/dsh-api-remotes": "next",
181
- "@deepseek-ai/dsh-atomic-write": "next",
182
- "@deepseek-ai/dsh-client-locale": "next",
183
- "@deepseek-ai/dsh-client-store": "next",
184
- "@deepseek-ai/dsh-client-test-runtime": "next",
185
- "@deepseek-ai/dsh-client-ui-conversation": "next",
186
- "@deepseek-ai/dsh-client-ui-primitives": "next",
187
- "@deepseek-ai/dsh-client-ui-renderer": "next",
188
- "@deepseek-ai/dsh-client-ui-session": "next",
189
- "@deepseek-ai/dsh-client-ui-slots": "next",
190
- "@deepseek-ai/dsh-commands": "next",
191
- "@deepseek-ai/dsh-compaction-image-offload": "next",
192
- "@deepseek-ai/dsh-home-paths": "next",
193
- "@deepseek-ai/dsh-llm": "next",
194
- "@deepseek-ai/dsh-session-format-catalog": "next",
195
- "@deepseek-ai/dsh-session-format-v0-to-v1": "next",
196
- "@deepseek-ai/dsh-session-persistence-jsonl": "next",
197
- "@deepseek-ai/dsh-settings": "next",
198
- "@deepseek-ai/dsh-skill-filesystem": "next",
199
- "@deepseek-ai/dsh-tool-cordis": "next",
200
- "@deepseek-ai/dsh-tools": "next",
201
- "@deepseek-ai/dsh-typert-protocol": "next",
202
- "@deepseek-ai/dsh-typert-registry": "next",
203
- "@deepseek-ai/dsh-util-workspace-path": "next",
177
+ "@deepseek-ai/cordis": "4.0.6-alpha.1",
178
+ "@deepseek-ai/cordis-plugin-group": "1.0.6-alpha.1",
179
+ "@deepseek-ai/cordis-plugin-include": "1.0.11-alpha.1",
180
+ "@deepseek-ai/cordis-plugin-loader": "1.0.7-alpha.1",
181
+ "@deepseek-ai/cordis-plugin-timer": "1.1.8-alpha.1",
182
+ "@deepseek-ai/cosmokit": "1.8.7-alpha.1",
183
+ "@deepseek-ai/dsh": "alpha",
184
+ "@deepseek-ai/dsh-agent-loop": "alpha",
185
+ "@deepseek-ai/dsh-agent-loop-testkit": "alpha",
186
+ "@deepseek-ai/dsh-api-gateway": "alpha",
187
+ "@deepseek-ai/dsh-api-remotes": "alpha",
188
+ "@deepseek-ai/dsh-atomic-write": "alpha",
189
+ "@deepseek-ai/dsh-client-locale": "alpha",
190
+ "@deepseek-ai/dsh-client-store": "alpha",
191
+ "@deepseek-ai/dsh-client-test-runtime": "alpha",
192
+ "@deepseek-ai/dsh-client-ui-conversation": "alpha",
193
+ "@deepseek-ai/dsh-client-ui-primitives": "alpha",
194
+ "@deepseek-ai/dsh-client-ui-renderer": "alpha",
195
+ "@deepseek-ai/dsh-client-ui-session": "alpha",
196
+ "@deepseek-ai/dsh-client-ui-slots": "alpha",
197
+ "@deepseek-ai/dsh-commands": "alpha",
198
+ "@deepseek-ai/dsh-compaction-image-offload": "alpha",
199
+ "@deepseek-ai/dsh-home-paths": "alpha",
200
+ "@deepseek-ai/dsh-llm": "alpha",
201
+ "@deepseek-ai/dsh-scope": "alpha",
202
+ "@deepseek-ai/dsh-session": "alpha",
203
+ "@deepseek-ai/dsh-session-format-catalog": "alpha",
204
+ "@deepseek-ai/dsh-session-format-v0-to-v1": "alpha",
205
+ "@deepseek-ai/dsh-session-persistence-jsonl": "alpha",
206
+ "@deepseek-ai/dsh-settings": "alpha",
207
+ "@deepseek-ai/dsh-skill": "alpha",
208
+ "@deepseek-ai/dsh-skill-filesystem": "alpha",
209
+ "@deepseek-ai/dsh-spill-policy": "alpha",
210
+ "@deepseek-ai/dsh-tool-cordis": "alpha",
211
+ "@deepseek-ai/dsh-tool-executor-native": "alpha",
212
+ "@deepseek-ai/dsh-tool-executor-ptc": "alpha",
213
+ "@deepseek-ai/dsh-tools": "alpha",
214
+ "@deepseek-ai/dsh-typert-protocol": "alpha",
215
+ "@deepseek-ai/dsh-typert-registry": "alpha",
216
+ "@deepseek-ai/dsh-util-workspace-path": "alpha",
204
217
  "@lezer/highlight": "^1.2.3",
205
218
  "@radix-ui/react-select": "^2.2.6",
206
219
  "@shikijs/langs": "^4.3.1",
220
+ "@tanstack/react-virtual": "^3.14.24",
207
221
  "@testing-library/react": "^16.3.3",
208
222
  "amaro": "1.1.11",
209
223
  "anser": "^2.3.5",
@@ -69,7 +69,11 @@ export function createAuthoringView(React, deps) {
69
69
  }) {
70
70
  const input = useInput?.(snapshot => snapshot)
71
71
  const available = useBindingCommand(snapshot => snapshot)
72
- const capabilityAvailable = useCapabilityCommand?.(snapshot => snapshot) === true
72
+ // The capability command source publishes nothing until a session observes it, and
73
+ // this entry is the surface that keeps it observed while mounted. Its value decides
74
+ // no branch here: whether `/capabilities` is listed is the command's own answer when
75
+ // it runs, so the refresh shortcut stays usable and the refusal carries its reason.
76
+ useCapabilityCommand?.(() => undefined)
73
77
  const settings = usePtcSettings(snapshot => snapshot)
74
78
  const [review, view] = useBindingReview(sessionId)
75
79
  const anchorRef = React.useRef(null)
@@ -113,8 +117,7 @@ export function createAuthoringView(React, deps) {
113
117
  const pluginEnabled = featureEnabled(settings, 'plugin') && (hasDraft || featureEnabled(settings, 'ptcMenu'))
114
118
  const canPrefill = typeof useInput === 'function' && typeof inputActions?.setDraft === 'function'
115
119
  const canAuthor = quickAccess && available && canPrefill
116
- const canRefresh = pluginEnabled && settings.status === 'ready' && settings.writable === true
117
- && capabilityAvailable && canPrefill
120
+ const canRefresh = pluginEnabled && settings.status === 'ready' && settings.writable === true && canPrefill
118
121
  const menuOpen = pluginEnabled && view.reachable && !managing && !capabilitiesOpen && !settingsOpen
119
122
  && menu !== null && menu.key === view.candidateKey
120
123
  // The dialog owns the management session; losing the input surface only
@@ -411,8 +414,7 @@ export function createAuthoringView(React, deps) {
411
414
  const actionButton = (id, copy) => h('button', {
412
415
  type: 'button', role: 'menuitem', className: 'ptcPlusMenuButton',
413
416
  disabled: id === 'refresh' && !canRefresh,
414
- title: id === 'refresh' && !capabilityAvailable ? t('capabilities.refreshUnavailable')
415
- : id === 'settings' ? settingsPath(t) : t(copy),
417
+ title: id === 'settings' ? settingsPath(t) : t(copy),
416
418
  onClick: () => selectMenuItem(id),
417
419
  }, actionCopy(id, copy))
418
420
  const actionSections = [
@@ -496,7 +498,6 @@ export function createAuthoringView(React, deps) {
496
498
  }) : null,
497
499
  SessionCapabilityControls && capabilitiesOpen && view.reachable
498
500
  ? h(SessionCapabilityControls, { sessionId, open: true, t,
499
- enabled: pluginEnabled && settings.status === 'ready' && settings.writable === true,
500
501
  onClose: () => {
501
502
  setCapabilitiesOpen(false)
502
503
  queueMicrotask(() => anchorRef.current?.querySelector('.ptcPlusAuthorButton')
@@ -747,8 +748,6 @@ export function createAuthoringView(React, deps) {
747
748
  node.outcome?.kind !== 'error' ? null : h('p', { className: 'ptcPlusMessage ptcPlusDanger' },
748
749
  node.outcome.text ?? t('bindings.commandFailed')),
749
750
  canOpen ? h(ActionButton, { onClick: () => openBindingReview(review) }, t('bindings.reviewOpen')) : null,
750
- !current.mounted && (candidate !== null || matches && projection.phase === 'ready')
751
- ? h('p', { className: 'ptcPlusMessage' }, t('bindings.reviewUnavailable')) : null,
752
751
  candidate === null ? null : h('details', { className: 'ptcPlusBindingSourceDetails' },
753
752
  h('summary', null, t('tool.source')), h(BindingCandidateContent, { candidate, t })))
754
753
  }