Commit Graph

8588 Commits

Author SHA1 Message Date
kingwl
583d532bc3 merge compact duration display
# Conflicts:
#	.agents/notes/implemented/feature/2026-07-27-web-subagent-conversations.i18n.yaml
#	.agents/notes/implemented/feature/2026-07-27-web-subagent-conversations.md
#	.agents/notes/implemented/feature/2026-07-27-web-subagent-conversations.zh.md
#	apps/web/tests/snapshots/subagent-conversation/tree.expected.md
#	packages/client/ui-subagent/README.i18n.yaml
#	packages/client/ui-subagent/README.md
#	packages/client/ui-subagent/README.zh.md
#	packages/client/ui-subagent/src/client/SubagentCatalogAction.tsx
#	packages/client/ui-subagent/tests/conversation-ui.spec.tsx
2026-08-03 13:31:19 +08:00
kingwl
255cd90c6e compact long subagent durations 2026-08-03 13:23:40 +08:00
kingwl
309a7202f2 merge duration review comment placement 2026-08-03 12:05:20 +08:00
kingwl
c183fae6f9 clarify timing projection schema cast 2026-08-03 12:04:44 +08:00
kingwl
24ff409f62 merge refreshed duration base 2026-08-03 12:03:59 +08:00
kingwl
ad42057586 merge latest master into subagent duration fix 2026-08-03 12:02:47 +08:00
kingwl
e97b47092e merge subagent timing review fixes
# Conflicts:
#	.agents/notes/implemented/feature/2026-07-27-web-subagent-conversations.i18n.yaml
#	.agents/notes/implemented/feature/2026-07-27-web-subagent-conversations.md
#	.agents/notes/implemented/feature/2026-07-27-web-subagent-conversations.zh.md
#	packages/client/ui-subagent/README.i18n.yaml
#	packages/client/ui-subagent/README.md
#	packages/client/ui-subagent/README.zh.md
2026-08-03 11:51:24 +08:00
kingwl
fdf83f2c3e document projection-cut duration bound 2026-08-03 11:44:11 +08:00
CreatixChu
4d6bf76326 Merge pull request #1168 from deepseek-harness/worktree/archive-icon
fix(ui-workspace): draw Archive session with the archive-box glyph
2026-08-03 11:41:45 +08:00
kingwl
0b0de64769 bound inactive subagent timing to projection cut 2026-08-03 11:40:33 +08:00
creatixchu
3f34a72b66 review(ui-primitives): stop the size doc from enumerating native sizes
The parenthetical listed 14/16 and this branch added 20, but the set never
held to it: IconRightUpOutline14 defaults to 8, IconTreeCorner8x10 to 10,
and IconWarningOutline16 to 14. Drop the list rather than maintain one that
drifts, and retitle the icons test that carried the same generalization.
2026-08-03 10:42:34 +08:00
creatixchu
b85c0a1851 fix(ui-workspace): draw Archive session with the archive-box glyph
The session row menu's Archive action carried ic_ds_download_outline_16, a
download tray that reads as "save to disk" rather than "put away". Swap it
for the design's archive glyph — a lidded box with a label slot — added to
the ic_ds_* set as IconArchiveOutline20.

The glyph is native 20, the first of that size in the set, so the menu's
16px icon slot asks for it explicitly. The figma export's 0.11px stroke ring
around the box contour is dropped: it restates the same contour in the same
ink, which currentColor already carries.
2026-08-03 10:30:32 +08:00
kingwl
57e2433f45 show subagent token metrics 2026-08-03 01:19:36 +08:00
kingwl
c831c99981 keep subagent duration fix focused 2026-08-03 01:08:32 +08:00
kingwl
3a920be9c5 stack subagent token and duration metrics 2026-08-03 00:22:01 +08:00
kingwl
6b6acbe0c5 Merge master into subagent usage branch
# Conflicts:
#	.agents/notes/implemented/feature/2026-07-27-web-subagent-conversations.i18n.yaml
#	.agents/notes/implemented/feature/2026-07-27-web-subagent-conversations.md
#	.agents/notes/implemented/feature/2026-07-27-web-subagent-conversations.zh.md
#	apps/web/tests/snapshots/subagent-conversation/tree.expected.md
#	apps/web/tests/subagent-conversation.e2e.ts
#	packages/client/ui-subagent/src/client/SubagentCatalogAction.tsx
2026-08-02 23:37:17 +08:00
kingwl
b30686d634 show subagent usage and active duration 2026-08-02 23:31:24 +08:00
Tianyi Cui
8bf606ba80 Merge pull request #1146 from deepseek-harness/fix/subagent-stack-end-result
fix(subagent/web/host/acp): end-result fixes for the continuable-subagent stack
2026-08-02 23:19:11 +08:00
Tianyi Cui
1ea72962eb Merge master into fix/subagent-stack-end-result 2026-08-02 23:13:00 +08:00
Ziya
45a59ffa26 Merge pull request #1156 from deepseek-harness/fix/goal-complete-wrapup
fix(tool-goal): deliver a user-facing wrap-up message after goal-round complete/blocked
2026-08-02 11:03:22 -04:00
ZiyaZhang
e72978ba98 fix(tool-goal): scope the wrap-up no-more-tools clause to the current run
The injected instruction persists as a durable user message, so an
unscoped 'Do not call any more tools.' stays in every later request's
history. Scope it: '...in this run; further work waits for the user's
next instruction.' A/B probes on deepseek-v4-pro show the scoped wording
is non-inferior in-turn (4/4 zero tool calls, closing quality unchanged)
and next-turn tool use is unaffected under both wordings; the scoped
form states the instruction's actual lifetime.
2026-08-02 07:29:18 -07:00
ZiyaZhang
820a5a97f1 review(tool-goal,llm-replay): address ds-review-bot round one
- fromRequest placeholder: the last two braces of a consecutive } run now
  terminate the placeholder, so patterns may end with a brace quantifier
  (bot warning; the truncated pattern could even silently mis-match since
  an unclosed { is literal in JS regexes)
- document that derived JSONL entries pass through the same resolution
- widen ToolRunContext/deferContext seam docs beyond composite-only usage
  (source JSDoc, README pair, core-data-structures type-equiv blocks)
- pin direct-human blocked as uninstructed, completing the
  goal-round/direct-human x complete/blocked test quadrant
2026-08-02 07:19:26 -07:00
Ziya
2ef9c6eb41 Merge pull request #1155 from deepseek-harness/feat/web-thinking-tail-scroll
feat(web): follow live reasoning tail while collapsed
2026-08-02 09:27:12 -04:00
Tianyi Cui
711a33ea8d fix(web): keep known subagent chooser visible 2026-08-02 21:22:39 +08:00
ZiyaZhang
8f77ab467f test(web): harden live thinking tail observation 2026-08-02 06:12:13 -07:00
ZiyaZhang
666ef95f81 fix(tool-goal): let the model deliver a wrap-up message after a goal-round complete/blocked
A goal round reporting complete or blocked used to conclude the turn at
the tool result, so the model never spoke after the call and sessions
ended on a bare update_goal card. The terminal update now defers one
plugin-sourced <goal_complete>/<goal_blocked> instruction onto its
result asking for a grounded closing message without further tool
calls; the turn then ends through the ordinary no-tool-calls stop.
Direct-human mutations stay uninstructed. Wording chosen by A/B
sampling on deepseek-v4-pro; one extra request per goal lifecycle.

New keyless ACP snapshot goal-wrapup drives the shipped app through
create -> round one -> autonomous complete and pins the injection, the
same-turn closing message, and the completed turn end.
2026-08-02 05:58:45 -07:00
ZiyaZhang
04d43e3b19 feat(llm-replay): resolve {{fromRequest:...}} placeholders against the live request
A scripted sidecar cannot know values minted at run time, so terminal
goal updates (which must echo the random goal id) were previously
un-scriptable. Placeholders in scripted entries now resolve against the
request corpus at stream time: last match wins, capture group 1 or the
whole match substitutes, and unmatched/invalid/unterminated patterns
fail loud.
2026-08-02 05:58:31 -07:00
Tianyi Cui
da80b0e5e6 chore(docs): refresh the descriptor catalog pointer
Correcting the cold-resume module contract added one JSDoc line above SubagentDescriptorData, but the generated persistence catalog still linked the durable subagent/descriptor event payload to descriptor.ts line 36. That left a dead source pointer and made the repository documentation gate fail even though the catalog content itself was otherwise current.

Regenerate docs/persistence-catalog.md so its source link follows the declaration to line 37. This is a generated-reference correction only: it does not change the durable event vocabulary, payload shape, or runtime behavior.

Validated with pnpm run verify-persistence-catalog and git diff --cached --check; the generator reports the catalog is up to date.
2026-08-02 20:34:43 +08:00
Tianyi Cui
a54eadf2f1 test(web): pin the subagent snapshot to English
The subagent conversation scenario asserts English role names and compares English accessibility goldens, but it opened a raw Playwright page while the rest of the English Web scenarios use the shared bootstrap that writes dsh.locale before client initialization. Once the subagent surface became localized, the raw page left those assertions dependent on ambient browser or persisted locale selection.

Create the page through newEnglishPage so the product sees an explicit English preference before boot, while preserving the standard 1680 by 1000 viewport. Chinese-surface scenarios continue to bypass this helper and advertise their own locale explicitly.

A fresh library build and production Vite build completed successfully. The focused assembled subagent-conversation Web suite then passed all 8 keyless replay tests against the updated singular-copy golden, and the staged diff passes formatting, lint, and whitespace hooks.
2026-08-02 20:30:01 +08:00
ZiyaZhang
975b57b54a feat(web): follow live reasoning tail while collapsed 2026-08-02 05:29:25 -07:00
Tianyi Cui
e4663cb10b test(web): share the subagent locale translator
The localized catalog spec introduced two package-local translation stubs: one manually looped over interpolation parameters and the other indexed the Chinese dictionary directly. That duplicates framework test plumbing and can drift from the shared lookup, fallback, and placeholder semantics used by the rest of the client suites.

Use makeTranslate from dsh-client-test-runtime as the single Chinese translator for both catalog and read-only composer assertions. Record the test-only workspace dependency in the ui-subagent manifest and lockfile; no production dependency or runtime bundle edge is added.

This removes twelve lines of local translation behavior while preserving the same Chinese assertions and exercising the shared interpolation path. Both ui-subagent test files pass with all 28 tests, the package TypeScript project checks cleanly, and the staged diff passes formatting, lint, and whitespace hooks.
2026-08-02 20:28:23 +08:00
Tianyi Cui
a24f9b06e7 refactor(subagent): drop speculative effect rollback
The PR moved child scope-effect registration into the contribution-installation try/catch solely to cover a hypothetical throw, while documenting that Context.effect cannot reject for the live unpublished scope passed to apply. The change therefore added control-flow and rollback implications for a failure mode the API does not expose, without changing observable behavior.

Keep the rollback boundary focused on contribution installers, which are the operations that can actually fail and leave recorded installations to unwind. Register the child-scope cleanup effect immediately after that boundary, as before; its disposer still converges with contribution removal through the registry idempotence rules.

This is a behavior-preserving removal of unnecessary code. The focused activation-setup-registry suite passes all 11 tests, the subagent TypeScript project checks cleanly, and the staged diff passes whitespace validation.
2026-08-02 20:25:39 +08:00
Tianyi Cui
ab4120ac96 docs(subagent): keep intent note current
The PR appended a superseded warning to one obsolete durability clause while leaving the same active decision record with mutually incompatible claims about Task-backed continuations, provider resume dispatch, and persistence guarantees. Because implemented Agent Notes are current authority rather than a review-history log, readers could still derive an API and ownership model that no longer exists.

Rewrite the affected decision, alternatives, and consequences in place around the activation-based implementation: ordinary starts remain holder-owned one-shot runs; continuable starts return durable child and accepted message identities; the manager owns materialization, follow-up/report routing, cold resume, and teardown; providers only contribute detached first-create data through prepareContinuable; and flush participation is observable but is not proof that a persistence backend stored state.

Keep the English and Chinese records equivalent, move the Chinese dispose glossary to its new first use, and refresh the pairing sidecar. This commit changes documentation authority only; it does not change runtime behavior.

Validated with the scoped translation-pairing writer and checker, verify-md-wrap, verify-agent-note-format, verify-agent-note-classification, and git diff --cached --check.
2026-08-02 20:25:20 +08:00
Tianyi Cui
f91b4b2cdc docs(subagent): correct cold-resume parent contract
The descriptor module claimed that no parent exists during cold resume, using that as the reason maxTokens cannot be inherited. Continuable follow-up actually requires and authorizes the exact live direct parent before it loads the descriptor and materializes the child, so the stated lifecycle fact was false.

Keep the real persistence decision explicit: per-activation budgets are not durable descriptor composition. Cold resume reconstructs child options only from the curated durable fields, so it deliberately neither restores the establishing budget nor inherits the live parent current transient budget; the resumed provider and model route defaults apply.

This is a contract-only correction with no runtime change. The exported JSDoc gate remains clean.
2026-08-02 20:18:31 +08:00
Tianyi Cui
3fc4142c04 fix(web): pluralize singular subagent counts
The localized catalog exposed one count.total and one count.running string for every cardinality. The English dictionary therefore rendered both the visible trigger and its accessibility label as 1 subagents, and the assembled Web golden had begun preserving that grammar error.

Split both count families into explicit one and other keys, following the existing client locale convention. SubagentCatalogAction selects the pair from the effective descendant count; English uses subagent for one and subagents otherwise, while Chinese keeps its unchanged classifier text under the same key domain.

Add a component regression proving a single running descendant selects both singular keys. Update the real Web E2E locator and keyless assembled aria golden from 1 subagents to 1 subagent. Both ui-subagent test files pass all 28 tests and the package TypeScript project builds cleanly.
2026-08-02 20:17:34 +08:00
Tianyi Cui
ac88b6e4c7 fix(acp): retain nested teardown diagnostics
ACP waits for every owned Agent disposal and throws one AggregateError when any Session teardown fails. The aggregate message embedded each rejected value with String(failure) because the connection-close logger itself renders only the outer error message. String preserves only an Error name and message, so causes and AggregateError members disappeared from the operational warning.

Render each per-session rejection with the existing errorChain diagnostic helper before joining it into the outer message. The original rejected values remain in AggregateError.errors for programmatic inspection, while the message now carries cause chains and nested aggregate members through the String-based logger.

Exercise a disposal failure containing both AggregateError members and a nested cause, while retaining the existing barrier that proves the second Session finishes disposal before any warning is emitted. All 10 ACP disposal tests pass and the ACP TypeScript project builds cleanly.
2026-08-02 20:14:46 +08:00
Tianyi Cui
7b40fd5419 perf(web): trail only membership-invalidated catalogs
refreshSubagents previously treated every overlapping caller as proof that the in-flight response was stale. Selection, menu opening, and reconnect paths can legitimately request the same catalog concurrently without any host mutation, so those reads were coalesced and then followed by an unnecessary second RPC.

Restore ordinary in-flight coalescing at the public refresh boundary. The debounced host/session-added path now owns the membership-specific stale mark: if its timer fires during an older pull, it queues one trailing request; otherwise it starts the refresh directly. Parent removal keeps its separate explicit invalidation and trailing-refresh path.

Add a regression proving two overlapping reads share one Promise and issue one RPC. Rework the membership test to start from a restored selected parent, so only the host membership frame can request the trailing pull instead of the test priming the stale bit with an unrelated duplicate read.

Validated with both focused catalog cases, all 40 SessionManager tests, and the client runtime TypeScript project build.
2026-08-02 20:13:28 +08:00
Tianyi Cui
069f2644ff fix(web): preserve removal across stale catalog pulls
The earlier removal fix invalidated parentAvailable immediately and queued a trailing subagent.list request, but it still applied the already in-flight success verbatim. That stale success reopened the composer and became the trailing request baseline. If the trailing request failed, its error snapshot preserved parentAvailable:true indefinitely.

Record a false-only parent availability override on the exact in-flight catalog request when the owner removal frame arrives. Successful and failed responses now replay that request-local invalidation before publishing a snapshot, and addressed child Sessions receive the same effective value. The trailing request therefore starts from a false baseline and a later transport or business failure cannot resurrect the removed parent.

Strengthen the regression to assert the catalog and selected child remain read-only immediately after a stale parentAvailable:true success, then fail the trailing pull and assert the error snapshot remains unavailable. The complete SessionManager test file passes all 39 tests, and the client runtime TypeScript project builds cleanly.
2026-08-02 20:11:34 +08:00
Tianyi Cui
b54381f3e7 fix(agent): commit mutable setup at publication
Agent setup may await while a mutable contribution registry changes. The previous subagent path validated and committed its provisioning batch inside the setup callback. A revocation queued after that callback returned therefore treated the installation as resident and released it, even though AgentLoop had not published the child yet. AgentLoop could then admit and announce a child whose required capability had already disappeared.

Introduce AgentSetupCommit as the optional synchronous result of create and resume setup. AgentLoop now awaits setup, invokes that commit with no intervening asynchronous boundary, and only then enters the Session and Agent registries. A commit failure follows the existing private-transaction rollback, so neither identity is published and the caller can reuse the id.

Keep continuable-subagent installations provisional until this publication commit. Contribution removal still releases every installation immediately, but now marks an unpublished batch invalid so its commit rejects with ACTIVATION_SETUP_REVOKED. Once the commit succeeds, later removal remains ordinary live revocation.

Cover create and resume ordering, resume commit rejection and identity reuse, and an assembled microtask revocation that leaves only the parent Agent and Session. Update the public JSDoc, architecture flow, package contracts, current Agent Notes, Chinese counterparts, pairing records, and generated Cordis API to describe the new boundary.

Validated with the four focused Agent/subagent test files (91 tests), the isolated assembled regression, targeted TypeScript project builds, generated Cordis API freshness, export JSDoc verification, scoped translation pairing, Markdown wrapping, and Mermaid parsing.
2026-08-02 20:09:05 +08:00
Tianyi Cui
baf133d134 Merge pull request #933 from deepseek-harness/codex/web-steer-support
feat(web): steer queued messages into active turns
2026-08-02 18:00:12 +08:00
imccyu
7d08e43720 fix(web): address steering review feedback 2026-08-02 17:53:07 +08:00
imccyu
cf918fa05d test(web): explain steering replay pace 2026-08-02 17:53:07 +08:00
imccyu
d59ab5596e docs(host): align queue mirror contract 2026-08-02 17:53:07 +08:00
imccyu
a31b3eb7b8 test(host): cover queue mirror event expiry 2026-08-02 17:53:07 +08:00
imccyu
53531b9af2 test(snapshot): refresh Cordis steering API fixture 2026-08-02 17:53:07 +08:00
imccyu
3a9f78c55e feat(web): restore actions after steering consumption 2026-08-02 17:53:07 +08:00
imccyu
dffe955ed2 feat(web): surface and configure composer steering 2026-08-02 17:53:07 +08:00
kingwl
5b17d3bab5 fix(web): match queue steer icon to design 2026-08-02 17:53:07 +08:00
kingwl
955a12cca4 feat(web): steer queued messages into active turns 2026-08-02 17:53:07 +08:00
Ziya
fff0172208 Merge pull request #1125 from deepseek-harness/agent/web-search-timeout-budget
fix(cli): give shipped web search a 60s budget
2026-08-02 05:42:41 -04:00