refactor(process): split the process manager out of the bash executor
New process/ capability family: @deepseek-ai/dsh-process owns ctx.processes — abstract ProcessManager.spawn(spec) over a fully-explicit ProcessSpawnSpec — plus the shared DSH_* managed-environment and CollectedOutput vocabulary; @deepseek-ai/dsh-process-local carries the former bash-local run.ts plumbing (detached groups, tail-keep spill-backed output, credential scrub, kill escalation, kill-and-join disposal) with no config of its own. dsh-bash-local becomes a consumer: it keeps command defaulting, the fused deadline timedOut/aborted classification, the model-friendly terminal env (now merged through the ordinary env channel), and the [stderr]-marked background read merge, and spawns through ctx.processes. Background-process lifetime moves to the manager, so an executor reload no longer kills live background work; a background spawn failure is injected once into the read path instead of being buffered as fake stderr. dsh-bash re-exports the moved vocabulary so bash consumers keep one import root; dsh-bash-sandbox only redeclares the inherited inject. Every composition loading a bash executor now loads dsh-process-local (CLI, examples, python bundled runtime, create-sdk bash feature, inline test configs).
This commit is contained in:
@@ -82,10 +82,13 @@ flowchart LR
|
||||
pkg_agent_spine_demo["agent-spine-demo"]
|
||||
pkg_goal["goal"]
|
||||
svc_goals["ctx.goals<br/>Same-session goal domain"]
|
||||
pkg_bash["bash"]
|
||||
svc_bash["ctx.bash<br/>Bash executor seam"]
|
||||
pkg_process["process"]
|
||||
svc_processes["ctx.processes<br/>Process manager seam"]
|
||||
pkg_process_local["process-local"]
|
||||
pkg_bash_local["bash-local"]
|
||||
pkg_bash_sandbox["bash-sandbox"]
|
||||
pkg_bash["bash"]
|
||||
svc_bash["ctx.bash<br/>Bash executor seam"]
|
||||
svc_bashEnv["ctx.bashEnv<br/>Managed bash environment registry"]
|
||||
pkg_pty["pty"]
|
||||
svc_pty["ctx.pty<br/>Persistent PTY session registry"]
|
||||
@@ -164,6 +167,8 @@ flowchart LR
|
||||
pkg_modules --> svc_clientModuleHost
|
||||
pkg_permission --> svc_permission
|
||||
pkg_plan_mode --> svc_planMode
|
||||
pkg_process --> svc_processes
|
||||
pkg_process_local --> svc_processes
|
||||
pkg_pty --> svc_pty
|
||||
pkg_pty_local --> svc_pty
|
||||
pkg_sandbox --> svc_sandbox
|
||||
@@ -234,6 +239,8 @@ flowchart LR
|
||||
svc_invariants --> pkg_session
|
||||
svc_llm --> pkg_agent_loop
|
||||
svc_llm --> pkg_compact_basic
|
||||
svc_processes --> pkg_bash_local
|
||||
svc_processes --> pkg_bash_sandbox
|
||||
svc_pty --> pkg_tool_pty
|
||||
svc_sandbox --> pkg_bash_sandbox
|
||||
svc_sandbox --> pkg_pty_local
|
||||
@@ -317,6 +324,7 @@ flowchart LR
|
||||
| `ctx.agents` | `core` | [`agent`](../packages/core/agent) | - | [`agent-loop`](../packages/core/agent-loop), [`acp`](../packages/acp/acp), [`cli-demo`](../packages/examples/cli-demo), [`subagent-inprocess`](../packages/subagent/subagent-inprocess), [`tui-demo`](../packages/examples/tui-demo) | - | Owns live Agent handles, the create/resume factory seam, and process-local initiator propagation. |
|
||||
| `ctx.agentLoop` | `bundle` | [`agent-loop`](../packages/core/agent-loop) | - | [`agent-spine-demo`](../packages/examples/agent-spine-demo) | - | The one concrete loop plugin; extension packages depend on dsh-agent events and services, not on this package. |
|
||||
| `ctx.goals` | `core` | [`goal`](../packages/goal/goal) | - | - | - | Folds revisioned objective state from the session log and keeps live continuation activation process-local. |
|
||||
| `ctx.processes` | `seam` | [`process`](../packages/process/process) | [`process-local`](../packages/process/process-local) | [`bash-local`](../packages/bash/bash-local), [`bash-sandbox`](../packages/bash/bash-sandbox) | - | The bash executors spawn their process groups through ctx.processes; the manager owns group lifetime, bounded spill-backed output, and kill escalation. |
|
||||
| `ctx.bash` | `seam` | [`bash`](../packages/bash/bash) | [`bash-local`](../packages/bash/bash-local), [`bash-sandbox`](../packages/bash/bash-sandbox) | [`tool-bash`](../packages/bash/tool-bash), [`hooks-claude`](../packages/hooks/hooks-claude), [`hooks-codex`](../packages/hooks/hooks-codex) | - | The model-facing bash tools and hook bridges consume this seam; sandboxed or remote executors replace bash-local without touching them. |
|
||||
| `ctx.bashEnv` | `core` | [`tool-bash`](../packages/bash/tool-bash) | - | - | - | Plugins declare effect-scoped DSH_* facts; tool-bash collects one trusted snapshot per execution and the executor rebuilds the namespace. |
|
||||
| `ctx.pty` | `seam` | [`pty`](../packages/pty/pty) | [`pty-local`](../packages/pty/pty-local) | [`tool-pty`](../packages/pty/tool-pty) | - | The registry owns exact-Agent session identity and cleanup; backends own terminal mechanics, while tool-pty exposes the owner-scoped model surface. |
|
||||
|
||||
@@ -192,6 +192,8 @@ Source: [`packages/examples/agent-spine-demo/src/index.ts:87`](../packages/examp
|
||||
|
||||
## `@deepseek-ai/dsh-bash-local`
|
||||
|
||||
Requires: `processes`
|
||||
|
||||
```ts config-catalog
|
||||
/** Plugin config (all optional — `static Config` supplies the defaults). */
|
||||
export interface Config {
|
||||
@@ -210,11 +212,11 @@ export interface Config {
|
||||
}
|
||||
```
|
||||
|
||||
Source: [`packages/bash/bash-local/src/index.ts:17`](../packages/bash/bash-local/src/index.ts)
|
||||
Source: [`packages/bash/bash-local/src/index.ts:39`](../packages/bash/bash-local/src/index.ts)
|
||||
|
||||
## `@deepseek-ai/dsh-bash-sandbox`
|
||||
|
||||
Requires: `sandbox` · `sandboxPolicy`
|
||||
Requires: `processes` · `sandbox` · `sandboxPolicy`
|
||||
|
||||
```ts config-catalog
|
||||
/**
|
||||
@@ -2053,6 +2055,7 @@ These load from a `cordis.yml` entry with no `config:` block; they declare no co
|
||||
- `@deepseek-ai/dsh-goal-session` — requires `agents` · `goals` · `sessions` ([`packages/goal/goal-session/src/index.ts`](../packages/goal/goal-session/src/index.ts))
|
||||
- `@deepseek-ai/dsh-llm` ([`packages/llm/llm/src/index.ts`](../packages/llm/llm/src/index.ts))
|
||||
- `@deepseek-ai/dsh-lsp` ([`packages/lsp/lsp/src/index.ts`](../packages/lsp/lsp/src/index.ts))
|
||||
- `@deepseek-ai/dsh-process-local` ([`packages/process/process-local/src/index.ts`](../packages/process/process-local/src/index.ts))
|
||||
- `@deepseek-ai/dsh-pty` ([`packages/pty/pty/src/index.ts`](../packages/pty/pty/src/index.ts))
|
||||
- `@deepseek-ai/dsh-session` ([`packages/core/session/src/index.ts`](../packages/core/session/src/index.ts))
|
||||
- `@deepseek-ai/dsh-session-checkpoint-policy` — requires `llm` · `sessionPersistence` · `sessions` · `tools` ([`packages/session-persistence/session-checkpoint-policy/src/index.ts`](../packages/session-persistence/session-checkpoint-policy/src/index.ts))
|
||||
@@ -2073,6 +2076,7 @@ Abstract service classes — a deployment loads a concrete implementation packag
|
||||
- `@deepseek-ai/dsh-code-runtime` — abstract `CodeRuntime` ([`packages/code-runtime/code-runtime/src/index.ts`](../packages/code-runtime/code-runtime/src/index.ts))
|
||||
- `@deepseek-ai/dsh-compact` — abstract `CompactService` ([`packages/compact/compact/src/index.ts`](../packages/compact/compact/src/index.ts))
|
||||
- `@deepseek-ai/dsh-fs` — abstract `FileSystem` ([`packages/fs/fs/src/index.ts`](../packages/fs/fs/src/index.ts))
|
||||
- `@deepseek-ai/dsh-process` — abstract `ProcessManager` ([`packages/process/process/src/index.ts`](../packages/process/process/src/index.ts))
|
||||
- `@deepseek-ai/dsh-sandbox` — abstract `SandboxProvider` ([`packages/sandbox/sandbox/src/index.ts`](../packages/sandbox/sandbox/src/index.ts))
|
||||
- `@deepseek-ai/dsh-session-persistence` — abstract `SessionPersistence` ([`packages/session-persistence/session-persistence/src/index.ts`](../packages/session-persistence/session-persistence/src/index.ts))
|
||||
- `@deepseek-ai/dsh-session-query` — abstract `SessionQueryService` ([`packages/session-query/session-query/src/index.ts`](../packages/session-query/session-query/src/index.ts))
|
||||
|
||||
@@ -315,7 +315,7 @@ collect(execution: ToolExecution): DshEnvironment
|
||||
list(): BashEnvVariableInfo[]
|
||||
```
|
||||
|
||||
Types: [DshEnvironment](../core-data-structures/bash.md) · [ToolExecution](../core-data-structures/tools.md)
|
||||
Types: [DshEnvironment](../core-data-structures/process.md) · [ToolExecution](../core-data-structures/tools.md)
|
||||
|
||||
Source: [`packages/bash/tool-bash/src/index.ts:104`](../../packages/bash/tool-bash/src/index.ts)
|
||||
|
||||
@@ -829,6 +829,31 @@ Types: [Agent](../core-data-structures/core.md)
|
||||
|
||||
Source: [`packages/plan/plan-mode/src/index.ts:141`](../../packages/plan/plan-mode/src/index.ts)
|
||||
|
||||
## `ctx.processes` — `ProcessManager` (abstract seam)
|
||||
|
||||
Abstract process manager. Subclass, implement spawn, and load the subclass as a plugin — it registers as `ctx.processes` (one implementation per context; loading a second throws, which is cordis' standard duplicate-service behavior).
|
||||
|
||||
Implementations must honor these semantics:
|
||||
|
||||
- spawn returns immediately with a live handle; `done` resolves at process close and rejects only for spawn-level failures.
|
||||
- Output readers are offset-based and non-consuming, so independent readers never consume one another's output; lossy reads report truncation and the spill file holding the complete stream when one exists.
|
||||
- ProcessHandle.kill and the spec's abort signal escalate SIGTERM→grace→SIGKILL across the whole process group.
|
||||
- Disposal kills all still-running managed processes and awaits their exit.
|
||||
|
||||
```ts cordis-catalog
|
||||
/**
|
||||
* Start one managed child process from a fully-specified spec; this seam
|
||||
* applies no defaults.
|
||||
* @param spec - argv, directory, limits, grace, cancellation, and environment.
|
||||
* @returns the live process handle (readers, kill, outcome promise).
|
||||
*/
|
||||
abstract spawn(spec: ProcessSpawnSpec): ProcessHandle
|
||||
```
|
||||
|
||||
Types: [ProcessHandle](../core-data-structures/process.md) · [ProcessSpawnSpec](../core-data-structures/process.md)
|
||||
|
||||
Source: [`packages/process/process/src/index.ts:48`](../../packages/process/process/src/index.ts)
|
||||
|
||||
## `ctx.pty` — `PtyService`
|
||||
|
||||
In-process registry for replaceable PTY backends and exact-Agent sessions.
|
||||
|
||||
@@ -2,23 +2,13 @@
|
||||
|
||||
English | [中文](bash.zh.md)
|
||||
|
||||
The bash execution seam is split across interface ([dsh-bash](../../packages/bash/bash), `ctx.bash`), implementations ([dsh-bash-local](../../packages/bash/bash-local) and [dsh-bash-sandbox](../../packages/bash/bash-sandbox)), and consumer ([dsh-tool-bash](../../packages/bash/tool-bash), the `bash` schema). Generic background-task ids, ownership, and controls live in [tasks.md](tasks.md); this seam returns a task-free process handle.
|
||||
The bash execution seam is split across interface ([dsh-bash](../../packages/bash/bash), `ctx.bash`), implementations ([dsh-bash-local](../../packages/bash/bash-local) and [dsh-bash-sandbox](../../packages/bash/bash-sandbox)), and consumer ([dsh-tool-bash](../../packages/bash/tool-bash), the `bash` schema). Generic background-task ids, ownership, and controls live in [tasks.md](tasks.md); this seam returns a task-free process handle. Raw process-group mechanics live behind the [process-manager seam](process.md).
|
||||
|
||||
Source: [`packages/bash/bash/src/types.ts`](../../packages/bash/bash/src/types.ts)
|
||||
|
||||
## Managed shell environment namespace
|
||||
|
||||
`DSH_*` variables are Harness-owned child-process facts. The model-facing bash tool collects them through `ctx.bashEnv` and passes them through `BashExecRequest.dshEnv`; executors remove inherited `DSH_*` names before merging the current snapshot.
|
||||
|
||||
```ts type-equiv
|
||||
/** One environment key inside the managed {@link DSH_ENV_PREFIX} namespace. */
|
||||
type DshEnvironmentKey = `${typeof DSH_ENV_PREFIX}${string}`
|
||||
```
|
||||
|
||||
```ts type-equiv
|
||||
/** Trusted DeepSeek Harness variables for one bash execution. */
|
||||
type DshEnvironment = Readonly<Record<DshEnvironmentKey, string>>
|
||||
```
|
||||
`DSH_*` variables are Harness-owned child-process facts. The model-facing bash tool collects them through `ctx.bashEnv` and passes them through `BashExecRequest.dshEnv`; the process manager removes inherited `DSH_*` names before merging the current snapshot. The `DshEnvironmentKey`/`DshEnvironment` vocabulary is owned by the [process-manager seam](process.md) and re-exported by `dsh-bash`.
|
||||
|
||||
## Request vs. spec: the `resolve()` split
|
||||
|
||||
@@ -145,19 +135,7 @@ interface BashRunResult {
|
||||
}
|
||||
```
|
||||
|
||||
Each stream is a `CollectedOutput` — the (possibly truncated) text plus recovery info. When truncated, `text` is the **tail** and the complete stream spills to a private file:
|
||||
|
||||
```ts type-equiv
|
||||
/** One captured stream: the (possibly truncated) text plus recovery info. */
|
||||
interface CollectedOutput {
|
||||
/** Collected text — the TAIL of the stream when truncated. */
|
||||
text: string
|
||||
/** True when bytes were dropped from `text`. */
|
||||
truncated: boolean
|
||||
/** Path to a file holding the COMPLETE stream, when truncated and available. */
|
||||
spillPath?: string
|
||||
}
|
||||
```
|
||||
Each stream is a `CollectedOutput` — the (possibly truncated) text plus recovery info; when truncated, `text` is the **tail** and the complete stream spills to a private file. The shape is owned by the [process-manager seam](process.md) and re-exported by `dsh-bash`.
|
||||
|
||||
## File sandbox: `BashSandboxInfo`
|
||||
|
||||
|
||||
@@ -2,23 +2,13 @@
|
||||
|
||||
[English](bash.md) | 中文
|
||||
|
||||
bash 执行 seam 分为接口([dsh-bash](../../packages/bash/bash),`ctx.bash`)、实现([dsh-bash-local](../../packages/bash/bash-local) 与 [dsh-bash-sandbox](../../packages/bash/bash-sandbox))和消费方([dsh-tool-bash](../../packages/bash/tool-bash),即 `bash` schema)。通用后台任务的 id、所有权与控制位于 [tasks.md](tasks.md);本 seam 返回一个不含任务概念的进程句柄。
|
||||
bash 执行 seam 分为接口([dsh-bash](../../packages/bash/bash),`ctx.bash`)、实现([dsh-bash-local](../../packages/bash/bash-local) 与 [dsh-bash-sandbox](../../packages/bash/bash-sandbox))和消费方([dsh-tool-bash](../../packages/bash/tool-bash),即 `bash` schema)。通用后台任务的 id、所有权与控制位于 [tasks.md](tasks.md);本 seam 返回一个不含任务概念的进程句柄。原始进程组机制位于[进程管理器 seam](process.md)之后。
|
||||
|
||||
源码:[`packages/bash/bash/src/types.ts`](../../packages/bash/bash/src/types.ts)
|
||||
|
||||
## 受管 shell 环境命名空间
|
||||
|
||||
`DSH_*` 变量是归 Harness 所有的子进程事实。面向模型的 bash 工具通过 `ctx.bashEnv` 收集它们,再经由 `BashExecRequest.dshEnv` 传递;执行器在合并当前快照之前会移除继承而来的 `DSH_*` 名称。
|
||||
|
||||
```ts type-equiv
|
||||
/** One environment key inside the managed {@link DSH_ENV_PREFIX} namespace. */
|
||||
type DshEnvironmentKey = `${typeof DSH_ENV_PREFIX}${string}`
|
||||
```
|
||||
|
||||
```ts type-equiv
|
||||
/** Trusted DeepSeek Harness variables for one bash execution. */
|
||||
type DshEnvironment = Readonly<Record<DshEnvironmentKey, string>>
|
||||
```
|
||||
`DSH_*` 变量是归 Harness 所有的子进程事实。面向模型的 bash 工具通过 `ctx.bashEnv` 收集它们,再经由 `BashExecRequest.dshEnv` 传递;进程管理器在合并当前快照之前会移除继承而来的 `DSH_*` 名称。`DshEnvironmentKey`/`DshEnvironment` 词汇归[进程管理器 seam](process.md)所有,由 `dsh-bash` 重导出。
|
||||
|
||||
## 请求与规格:`resolve()` 拆分
|
||||
|
||||
@@ -145,19 +135,7 @@ interface BashRunResult {
|
||||
}
|
||||
```
|
||||
|
||||
每个流是一个 `CollectedOutput`:(可能被截断的)文本加恢复信息。截断时,`text` 是**尾部**,完整流溢出到一个私有文件:
|
||||
|
||||
```ts type-equiv
|
||||
/** One captured stream: the (possibly truncated) text plus recovery info. */
|
||||
interface CollectedOutput {
|
||||
/** Collected text — the TAIL of the stream when truncated. */
|
||||
text: string
|
||||
/** True when bytes were dropped from `text`. */
|
||||
truncated: boolean
|
||||
/** Path to a file holding the COMPLETE stream, when truncated and available. */
|
||||
spillPath?: string
|
||||
}
|
||||
```
|
||||
每个流是一个 `CollectedOutput`:(可能被截断的)文本加恢复信息;截断时,`text` 是**尾部**,完整流溢出到一个私有文件。该形状归[进程管理器 seam](process.md)所有,由 `dsh-bash` 重导出。
|
||||
|
||||
## 文件沙箱:`BashSandboxInfo`
|
||||
|
||||
|
||||
133
docs/core-data-structures/process.md
Normal file
133
docs/core-data-structures/process.md
Normal file
@@ -0,0 +1,133 @@
|
||||
# Process Manager
|
||||
|
||||
The child-process manager seam is split across interface ([dsh-process](../../packages/process/process), `ctx.processes`) and implementation ([dsh-process-local](../../packages/process/process-local)); its consumers are other capability seams — today the [bash executor family](bash.md), which passes `['bash', '-c', command]` argv and owns every default. This seam owns the managed `DSH_*` environment namespace and the `CollectedOutput` shape; [dsh-bash](../../packages/bash/bash) re-exports them so bash consumers keep one import root.
|
||||
|
||||
Source: [`packages/process/process/src/types.ts`](../../packages/process/process/src/types.ts)
|
||||
|
||||
## The fully-explicit spawn spec
|
||||
|
||||
The seam applies no defaults: every limit and directory is explicit on the spec, so the caller's own config — not a hidden process-manager default — decides them. `argv` is never shell-interpreted.
|
||||
|
||||
```ts type-equiv
|
||||
/**
|
||||
* A fully-specified spawn request. This seam applies no defaults: every limit
|
||||
* and directory is explicit, so the caller's own config — not a hidden
|
||||
* process-manager default — decides them (the `dsh-bash` request/spec split
|
||||
* is the owning template).
|
||||
*/
|
||||
interface ProcessSpawnSpec {
|
||||
/** Executable and arguments; `argv[0]` is the program. Never shell-interpreted here. */
|
||||
argv: readonly string[]
|
||||
/** Working directory for the child. */
|
||||
cwd: string
|
||||
/** Stdout in-memory cap; overflow spills to disk (tail kept in memory). */
|
||||
stdoutMaxBytes: number
|
||||
/** Stderr in-memory cap; overflow spills to disk (tail kept in memory). */
|
||||
stderrMaxBytes: number
|
||||
/** Per-stream spill-file cap; larger streams retain only their in-memory tail. */
|
||||
maxSpillBytes: number
|
||||
/** Grace period for kill escalation and for inherited pipes after process exit. */
|
||||
graceMs: number
|
||||
/**
|
||||
* Abort signal — kills the process group when it fires. The caller owns
|
||||
* deadlines and cause classification; this seam only reacts to the abort.
|
||||
*/
|
||||
signal?: AbortSignal | undefined
|
||||
/**
|
||||
* Bytes to write to the child's stdin, then close it. Absent (or empty)
|
||||
* leaves stdin closed/empty.
|
||||
*/
|
||||
stdin?: string | undefined
|
||||
/**
|
||||
* Ordinary environment entries merged after the implementation's credential
|
||||
* scrub. `DSH_*` names are rejected and belong in {@link dshEnv}.
|
||||
*/
|
||||
env?: Record<string, string> | undefined
|
||||
/**
|
||||
* Harness-owned `DSH_*` variables for this execution. Implementations
|
||||
* discard ambient `DSH_*` entries before merging this snapshot, so an
|
||||
* unavailable current fact cannot inherit a stale value from the harness
|
||||
* process, and reject non-`DSH_*` names supplied through this channel.
|
||||
*/
|
||||
dshEnv?: DshEnvironment | undefined
|
||||
}
|
||||
```
|
||||
|
||||
## Handles and offset-based reads
|
||||
|
||||
A spawn returns a live handle immediately. Output readers take whole-stream byte offsets and never consume, so independent readers cannot steal one another's deltas; the consuming-cursor model the bash tool presents is consumer-owned state over these readers.
|
||||
|
||||
```ts type-equiv
|
||||
/**
|
||||
* A live child process. `kill()` starts the group SIGTERM→grace→SIGKILL
|
||||
* escalation; buffered output remains readable after exit.
|
||||
*/
|
||||
interface ProcessHandle {
|
||||
/** Process id (group leader); -1 when the spawn itself failed. */
|
||||
readonly pid: number
|
||||
/** Live stdout reader (also readable after exit). */
|
||||
readonly stdout: ProcessOutputReader
|
||||
/** Live stderr reader (also readable after exit). */
|
||||
readonly stderr: ProcessOutputReader
|
||||
/** Resolves when the process closes; rejects only for spawn-level failures. */
|
||||
readonly done: Promise<ProcessOutcome>
|
||||
/** Begin SIGTERM→grace→SIGKILL on the process group. Idempotent. */
|
||||
kill(): void
|
||||
}
|
||||
```
|
||||
|
||||
```ts type-equiv
|
||||
/**
|
||||
* Cursor-free incremental access to one live output stream. Offsets are
|
||||
* whole-stream byte coordinates owned by the caller, so independent readers
|
||||
* cannot consume one another's output.
|
||||
*/
|
||||
interface ProcessOutputReader {
|
||||
/**
|
||||
* Read everything captured since `fromByte`. When that offset has slid out
|
||||
* of the in-memory tail window the read is `lossy` — it returns the whole
|
||||
* retained tail and the gap is only recoverable from the spill file.
|
||||
* @param fromByte - whole-stream offset to resume from (a prior read's `nextOffset`; 0 for the first read).
|
||||
* @returns the delta text, the next offset, the `lossy` flag, and the spill path when one exists.
|
||||
*/
|
||||
readFrom(fromByte: number): ProcessOutputRead
|
||||
}
|
||||
```
|
||||
|
||||
```ts type-equiv
|
||||
/** One incremental {@link ProcessOutputReader.readFrom} read. */
|
||||
interface ProcessOutputRead {
|
||||
/** Stream text from the requested offset (the whole retained tail when lossy). */
|
||||
text: string
|
||||
/** Whole-stream offset to resume from on the next read. */
|
||||
nextOffset: number
|
||||
/** True when the requested offset slid out of the in-memory tail window. */
|
||||
lossy: boolean
|
||||
/** Path to the full-stream spill file, when one was created and remains intact. */
|
||||
spillPath?: string
|
||||
}
|
||||
```
|
||||
|
||||
## Outcomes carry no cause classification
|
||||
|
||||
`done` reports raw exit facts. The manager kills on abort but never decides why — the caller reads the deadline signal it owns to classify timeout versus cancellation (the bash executor's `timedOut`/`aborted` split).
|
||||
|
||||
```ts type-equiv
|
||||
/**
|
||||
* Raw outcome of one closed process. Deliberately carries NO timeout or
|
||||
* cancellation classification: the manager kills on abort but does not decide
|
||||
* why — the caller reads the signal it owns to classify causes.
|
||||
*/
|
||||
interface ProcessOutcome {
|
||||
/** Exit code; null when the process died from a signal. */
|
||||
exitCode: number | null
|
||||
/** Terminating signal (e.g. 'SIGTERM'); null on normal exit. */
|
||||
signal: NodeJS.Signals | null
|
||||
stdout: CollectedOutput
|
||||
stderr: CollectedOutput
|
||||
}
|
||||
```
|
||||
|
||||
## Service behavior
|
||||
|
||||
The abstract [`ProcessManager`](../../packages/process/process/src/index.ts) seam defines `spawn` only; [`LocalProcessManager`](../../packages/process/process-local/src/index.ts) is the local implementation (detached groups, tail-keep spill-backed collection, credential scrub, kill-and-join disposal). See [`dsh-process`](../../packages/process/process/README.md) for the seam contract and [`dsh-process-local`](../../packages/process/process-local/README.md) for the mechanics.
|
||||
@@ -184,6 +184,10 @@ flowchart TD
|
||||
subgraph group_mcp["packages/mcp"]
|
||||
pkg_mcp_client["mcp-client"]
|
||||
end
|
||||
subgraph group_process["packages/process"]
|
||||
pkg_process["process"]
|
||||
pkg_process_local["process-local"]
|
||||
end
|
||||
subgraph group_pty["packages/pty"]
|
||||
pkg_pty["pty"]
|
||||
pkg_pty_local["pty-local"]
|
||||
@@ -243,6 +247,7 @@ flowchart TD
|
||||
pkg_jsonrpc_demo --> pkg_invariants
|
||||
pkg_host_apiproxy --> pkg_invariants
|
||||
pkg_host_webserver --> pkg_invariants
|
||||
pkg_process --> pkg_invariants
|
||||
pkg_storage --> pkg_invariants
|
||||
pkg_llm --> pkg_brand
|
||||
pkg_llm --> pkg_invariants
|
||||
@@ -266,6 +271,8 @@ flowchart TD
|
||||
pkg_client_ui_workspace --> pkg_client_ui_primitives
|
||||
pkg_client_ui_workspace --> pkg_client_ui_slots
|
||||
pkg_client_ui_workspace --> pkg_invariants
|
||||
pkg_process_local --> pkg_invariants
|
||||
pkg_process_local --> pkg_process
|
||||
pkg_helper --> pkg_brand
|
||||
pkg_helper --> pkg_invariants
|
||||
pkg_telemetry --> pkg_brand
|
||||
@@ -307,6 +314,7 @@ flowchart TD
|
||||
pkg_agent --> pkg_session
|
||||
pkg_agent --> pkg_system_prompt
|
||||
pkg_bash --> pkg_invariants
|
||||
pkg_bash --> pkg_process
|
||||
pkg_bash --> pkg_sandbox
|
||||
pkg_fs --> pkg_brand
|
||||
pkg_fs --> pkg_invariants
|
||||
@@ -371,6 +379,7 @@ flowchart TD
|
||||
pkg_goal --> pkg_session
|
||||
pkg_bash_local --> pkg_bash
|
||||
pkg_bash_local --> pkg_invariants
|
||||
pkg_bash_local --> pkg_process
|
||||
pkg_bash_local --> pkg_timeout
|
||||
pkg_fs_local --> pkg_fs
|
||||
pkg_fs_local --> pkg_invariants
|
||||
@@ -828,6 +837,7 @@ flowchart TD
|
||||
| [`jsonrpc-demo`](../packages/examples/jsonrpc-demo) | `examples` | [`invariants`](../packages/support/invariants) |
|
||||
| [`host-apiproxy`](../packages/host/apiproxy) | `host` | [`invariants`](../packages/support/invariants) |
|
||||
| [`host-webserver`](../packages/host/webserver) | `host` | [`invariants`](../packages/support/invariants) |
|
||||
| [`process`](../packages/process/process) | `process` | [`invariants`](../packages/support/invariants) |
|
||||
| [`storage`](../packages/storage/storage) | `storage` | [`invariants`](../packages/support/invariants) |
|
||||
| [`llm`](../packages/llm/llm) | `llm` | [`brand`](../packages/util/brand), [`invariants`](../packages/support/invariants) |
|
||||
| [`client-connection`](../packages/client/connection) | `client` | [`host-webserver`](../packages/host/webserver), [`invariants`](../packages/support/invariants) |
|
||||
@@ -836,6 +846,7 @@ flowchart TD
|
||||
| [`client-ui-layout`](../packages/client/ui-layout) | `client` | [`client-runtime`](../packages/client/runtime), [`client-ui-slots`](../packages/client/ui-slots), [`invariants`](../packages/support/invariants) |
|
||||
| [`client-ui-sidebar`](../packages/client/ui-sidebar) | `client` | [`client-runtime`](../packages/client/runtime), [`client-ui-primitives`](../packages/client/ui-primitives), [`client-ui-slots`](../packages/client/ui-slots), [`invariants`](../packages/support/invariants) |
|
||||
| [`client-ui-workspace`](../packages/client/ui-workspace) | `client` | [`client-runtime`](../packages/client/runtime), [`client-ui-primitives`](../packages/client/ui-primitives), [`client-ui-slots`](../packages/client/ui-slots), [`invariants`](../packages/support/invariants) |
|
||||
| [`process-local`](../packages/process/process-local) | `process` | [`invariants`](../packages/support/invariants), [`process`](../packages/process/process) |
|
||||
| [`helper`](../packages/sdk/helper) | `sdk` | [`brand`](../packages/util/brand), [`invariants`](../packages/support/invariants) |
|
||||
| [`telemetry`](../packages/sdk/telemetry) | `sdk` | [`brand`](../packages/util/brand), [`invariants`](../packages/support/invariants), [`paths`](../packages/util/paths) |
|
||||
| [`storage-domain`](../packages/storage/storage-domain) | `storage` | [`invariants`](../packages/support/invariants), [`storage`](../packages/storage/storage) |
|
||||
@@ -850,7 +861,7 @@ flowchart TD
|
||||
| [`sandbox`](../packages/sandbox/sandbox) | `sandbox` | [`invariants`](../packages/support/invariants), [`llm`](../packages/llm/llm) |
|
||||
| [`token-meter`](../packages/llm/token-meter) | `llm` | [`invariants`](../packages/support/invariants), [`llm`](../packages/llm/llm), [`session`](../packages/core/session) |
|
||||
| [`agent`](../packages/core/agent) | `core` | [`brand`](../packages/util/brand), [`invariants`](../packages/support/invariants), [`llm`](../packages/llm/llm), [`scope`](../packages/core/scope), [`session`](../packages/core/session), [`system-prompt`](../packages/core/system-prompt) |
|
||||
| [`bash`](../packages/bash/bash) | `bash` | [`invariants`](../packages/support/invariants), [`sandbox`](../packages/sandbox/sandbox) |
|
||||
| [`bash`](../packages/bash/bash) | `bash` | [`invariants`](../packages/support/invariants), [`process`](../packages/process/process), [`sandbox`](../packages/sandbox/sandbox) |
|
||||
| [`fs`](../packages/fs/fs) | `fs` | [`brand`](../packages/util/brand), [`invariants`](../packages/support/invariants), [`llm`](../packages/llm/llm), [`sandbox`](../packages/sandbox/sandbox) |
|
||||
| [`compact`](../packages/compact/compact) | `compact` | [`invariants`](../packages/support/invariants), [`llm`](../packages/llm/llm), [`session`](../packages/core/session) |
|
||||
| [`compact-tool-result-prune`](../packages/compact/compact-tool-result-prune) | `compact` | [`invariants`](../packages/support/invariants), [`llm`](../packages/llm/llm), [`session`](../packages/core/session) |
|
||||
@@ -869,7 +880,7 @@ flowchart TD
|
||||
| [`sandbox-policy`](../packages/sandbox/sandbox-policy) | `sandbox` | [`invariants`](../packages/support/invariants), [`sandbox`](../packages/sandbox/sandbox), [`session`](../packages/core/session) |
|
||||
| [`llm-retry`](../packages/llm/llm-retry) | `llm` | [`agent`](../packages/core/agent), [`invariants`](../packages/support/invariants), [`llm`](../packages/llm/llm), [`session`](../packages/core/session), [`timeout`](../packages/util/timeout) |
|
||||
| [`goal`](../packages/goal/goal) | `goal` | [`agent`](../packages/core/agent), [`brand`](../packages/util/brand), [`invariants`](../packages/support/invariants), [`llm`](../packages/llm/llm), [`scope`](../packages/core/scope), [`session`](../packages/core/session) |
|
||||
| [`bash-local`](../packages/bash/bash-local) | `bash` | [`bash`](../packages/bash/bash), [`invariants`](../packages/support/invariants), [`timeout`](../packages/util/timeout) |
|
||||
| [`bash-local`](../packages/bash/bash-local) | `bash` | [`bash`](../packages/bash/bash), [`invariants`](../packages/support/invariants), [`process`](../packages/process/process), [`timeout`](../packages/util/timeout) |
|
||||
| [`fs-local`](../packages/fs/fs-local) | `fs` | [`fs`](../packages/fs/fs), [`invariants`](../packages/support/invariants) |
|
||||
| [`fs-policy`](../packages/fs/fs-policy) | `fs` | [`fs`](../packages/fs/fs), [`invariants`](../packages/support/invariants) |
|
||||
| [`skill-local`](../packages/skill/skill-local) | `skill` | [`fs`](../packages/fs/fs), [`invariants`](../packages/support/invariants), [`paths`](../packages/util/paths), [`skill`](../packages/skill/skill) |
|
||||
|
||||
Reference in New Issue
Block a user