Merge branch 'master' into worktree/dsh-arg-parser
Integrate the Commander argument adapter and dsh-front-door work with master's config-tree `dsh web` (#601: AppCLIEntry + apps/cli/cordis.yml) and the packages/ui/acp → packages/acp/acp relocation. - web.ts: keep master's AppCLIEntry-based boot, but take the adapter's parsed (host, port, dev) instead of an internal parseArgs. The adapter's host/port defaults (127.0.0.1/3080) match cordis.yml, so always passing them is behavior-equivalent to master's "undefined keeps the yml default". - apps/cli/package.json: master's expanded config-tree dep set + commander. - retire-readline Agent Note: point the TUI refusal proof at apps/cli/tests/built-bin.e2e.ts (both languages), re-record the pair. - READMEs reconciled (demo-bin removal + master's ACP/channel rewording).
This commit is contained in:
@@ -139,10 +139,9 @@ export type TurnEndReason = TurnEndReasonMap[keyof TurnEndReasonMap]
|
||||
*
|
||||
* Deliberately minimal: a human-readable `content` line and a three-state
|
||||
* `status`. No id, priority, or `activeForm` — the list is replaced wholesale
|
||||
* on every write (last-write-wins), so entries need no stable identity, and the
|
||||
* status triple is exactly the ACP `PlanEntryStatus`, so a UI bridge can map a
|
||||
* todo list onto an ACP `plan` 1:1 (synthesizing the priority ACP additionally
|
||||
* requires).
|
||||
* on every write (last-write-wins), so entries need no stable identity. The
|
||||
* three statuses describe the complete portable lifecycle needed by model and
|
||||
* UI consumers.
|
||||
*/
|
||||
export interface TodoItem {
|
||||
/** What this task is — a short imperative line shown in the UI. */
|
||||
|
||||
@@ -363,7 +363,7 @@ export function createRunCodeTool(registry: ToolRegistry, requireRuntime: () =>
|
||||
exec.signal.removeEventListener('abort', onOuterAbort)
|
||||
}
|
||||
},
|
||||
// ACP execute cards use the program as their visible title.
|
||||
// The program is the call's always-visible UI label.
|
||||
presentCall: args => ({
|
||||
card: 'generic',
|
||||
title: args.code,
|
||||
|
||||
@@ -69,7 +69,7 @@ export { defineContentToolFixture, type ContentToolFixtureOptions } from './test
|
||||
|
||||
// The render-intent vocabulary a tool declares via `presentCall`/`presentResult`
|
||||
// lives in its own UI-facing module; re-export it so `@deepseek-ai/dsh-tools`
|
||||
// stays the single public surface for consumers (producers + the ACP bridge).
|
||||
// stays the single public surface for tool producers and UI adapters.
|
||||
export type {
|
||||
ToolCallKind,
|
||||
FileLocation,
|
||||
|
||||
@@ -8,19 +8,17 @@
|
||||
import type { ContentBlock } from '@deepseek-ai/dsh-llm'
|
||||
|
||||
/**
|
||||
* Category of a tool call, used by a UI to pick an icon / treatment. A neutral
|
||||
* vocabulary owned here (NOT an ACP type) so tools describe themselves without
|
||||
* depending on any client protocol; a UI bridge maps it to its own enum. The
|
||||
* member set mirrors the common ACP `ToolKind` values; `other` is the default.
|
||||
* Category of a tool call, used by a UI to pick an icon or treatment. The
|
||||
* provider-neutral vocabulary lets tools describe themselves without depending
|
||||
* on a particular client; `other` is the default.
|
||||
*/
|
||||
export type ToolCallKind = 'read' | 'edit' | 'delete' | 'move' | 'search' | 'execute' | 'fetch' | 'other'
|
||||
|
||||
/**
|
||||
* A file location a tool reads or modifies, so a capable UI can "follow along" —
|
||||
* highlight or jump to the file (and line) as the tool runs. Provider-neutral;
|
||||
* a UI bridge maps it to its own affordance (the ACP bridge forwards it as
|
||||
* `tool_call.locations`). `path` is what the tool operated on (the model-facing
|
||||
* path); `line` is an optional 1-based line to focus (e.g. a read's offset).
|
||||
* highlight or jump to the file (and line) as the tool runs. `path` is what the
|
||||
* tool operated on (the model-facing path); `line` is an optional 1-based line
|
||||
* to focus (e.g. a read's offset).
|
||||
*/
|
||||
export interface FileLocation {
|
||||
path: string
|
||||
@@ -29,10 +27,9 @@ export interface FileLocation {
|
||||
|
||||
/**
|
||||
* A single-file change a tool is about to make, for a UI that renders inline
|
||||
* diffs (an editor's diff card). Provider-neutral; the ACP bridge forwards it as
|
||||
* a `{ type: 'diff' }` tool-call content block. `oldText` is `null` for a
|
||||
* new-file create (nothing to diff against); an overwrite also uses `null`,
|
||||
* because a call-time presenter has no access to the file's prior content.
|
||||
* diffs. `oldText` is `null` for a new-file create (nothing to diff against);
|
||||
* an overwrite also uses `null`, because a call-time presenter has no access to
|
||||
* the file's prior content.
|
||||
*/
|
||||
export interface FileDiff {
|
||||
path: string
|
||||
|
||||
@@ -696,10 +696,8 @@ describe('the run_code dispatch bridge', () => {
|
||||
it('presents the program as the execute-card title', async () => {
|
||||
const { ctx } = await setup({ mode: 'code' })
|
||||
const tool = ctx.tools.get(RUN_CODE_NAME)!
|
||||
// The program IS the title, mirroring how command tools title their cards
|
||||
// with the command: an ACP client's execute-card header is the only
|
||||
// always-visible slot (Zed renders no body content and no raw input for
|
||||
// execute-kind cards without a real terminal).
|
||||
// The program is the title, mirroring how command tools label their cards
|
||||
// with the command while retaining the same value in the expanded input.
|
||||
expect(tool.presentCall?.({ code: 'return 1' })).toEqual({
|
||||
card: 'generic',
|
||||
title: 'return 1',
|
||||
|
||||
Reference in New Issue
Block a user