Skip to content

Commit 9156ded

Browse files
Manage native background processes with durable logs and owned cleanup
1 parent 676d569 commit 9156ded

19 files changed

Lines changed: 1556 additions & 59 deletions

‎CHANGELOG.md‎

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,10 @@
1616
task overrides, and recorded selection/fallback notices. Model registration
1717
distinguishes identical names on different endpoints and preserves saved
1818
credential references and context limits during discovery.
19+
- Native background processes run development servers and watchers alongside
20+
tasks, retain bounded live logs and durable history, honor project permissions,
21+
and stop managed child processes when the application closes. Legacy history
22+
is imported without signalling stored PIDs or replaying old commands.
1923
- Native window automation covers actual tool execution, approvals, reload,
2024
cancellation, goal progression/pause, accessibility, and subprocess cleanup.
2125
- Native AppImage and Debian build scripts preserve per-format executable

‎README.md‎

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,8 @@ context, tools, permissions, checkpoints, plans, and verification.
1414
desktop window with the interface embedded in the executable. It needs no Python
1515
runtime or browser launcher. See the [native development guide](docs/NATIVE_DESKTOP.md)
1616
and the [goals](docs/NATIVE_GOALS.md) and [model routing](docs/NATIVE_ROUTING.md)
17-
workflows. Development AppImage and Debian
17+
workflows, plus [managed background processes](docs/NATIVE_BACKGROUND.md).
18+
Development AppImage and Debian
1819
packages include [dependency inventories and notices](licenses/native/README.md).
1920
Integrations and release checks are
2021
still in progress under the [migration gates](docs/NATIVE_MIGRATION.md);

‎docs/NATIVE_BACKGROUND.md‎

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
# Background processes in the native desktop
2+
3+
Open **Background processes** in the sidebar, or the **Background** drawer tab.
4+
Give the process a name, enter its command, and choose **Start process**. This is
5+
useful for a development server or watcher that should continue while you work
6+
on other tasks in the same project. Commands run in the selected project folder.
7+
8+
The panel shows process status, PID, start time, exit code, and live output.
9+
**Stop** waits for cleanup and retains the cancelled result. Stopping an already
10+
finished entry preserves its original completed or failed status. Duplicate
11+
active names are rejected within the same project.
12+
13+
## Output and history
14+
15+
The runner drains stdout and stderr continuously, including output without a
16+
newline. It preserves UTF-8 characters split across reads and keeps the most
17+
recent 64 KB of combined output in memory and SQLite. When that limit is reached,
18+
the panel indicates that older output was omitted. This is a log tail, not a
19+
complete terminal recording or interactive shell; stdin is closed.
20+
21+
The process list sends a 4 KB preview per entry so a large history does not
22+
repeatedly transfer all retained logs. **Read retained output** opens a snapshot
23+
of the stored tail and full command; **Refresh retained output** updates that
24+
snapshot. **Return to live output** returns to the automatically refreshed preview.
25+
26+
The panel shows the latest 100 entries for the current project, plus every active
27+
process even if it started before that history window. Older entries remain in
28+
SQLite. History and the retained log survive application restarts. The native
29+
migration imports legacy `background.db` history once without changing the
30+
original database; legacy active entries become interrupted history.
31+
32+
## Permissions and lifecycle
33+
34+
Starting a process is an explicit user command, like the Terminal Run button.
35+
The project must be trusted, read-only mode denies execution, and configured
36+
command restrictions still apply. The manager permits up to four active
37+
processes per project and sixteen per application profile. Background commands
38+
deliberately run alongside coding tasks; their shell side effects are not file
39+
tool checkpoints and are not undone by task rewind.
40+
41+
Processes continue between tasks and while you navigate to another project.
42+
Return to their original project to view or stop them. They do not inherit the
43+
foreground terminal timeout. On Stop or normal application shutdown, ShadowCode
44+
sends SIGTERM, allows up to two seconds for the parent process to exit, and then
45+
kills remaining members of the managed process group. Shutdown waits for output
46+
draining and persisted status. A subprocess that deliberately detaches into a
47+
different session is outside that process group; this runner is not an OS sandbox.
48+
49+
After an abrupt crash or forced termination, previously active records are marked
50+
**INTERRUPTED**. ShadowCode does not restart commands automatically or signal a
51+
persisted PID, which could now belong to an unrelated process. An interrupted
52+
record does not prove that an independently detached process has exited.
53+
54+
The desktop uses Rust IPC routes `GET/POST /api/background`,
55+
`GET /api/background/<id>`, and `POST /api/background/<id>/stop`. The full native
56+
CLI and agent-facing background tools remain part of the broader integration
57+
work; this feature supplies the manager and user-operated desktop controls.
58+
59+
See [verification](NATIVE_VERIFICATION.md) and the remaining
60+
[release gates](NATIVE_MIGRATION.md).

‎docs/NATIVE_DESKTOP.md‎

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,9 @@ not require that tool. No global PATH change is needed.
9696
- [Model routing](NATIVE_ROUTING.md) selects a registered model for Plan, Build,
9797
Review, and Test. Provider-scoped IDs keep identical model names on different
9898
servers distinct; conversations retain the actual selection and fallback notices.
99+
- [Background processes](NATIVE_BACKGROUND.md) run project servers and watchers
100+
alongside coding tasks, with live bounded logs, retained history, stop controls,
101+
and process-group cleanup during application shutdown.
99102

100103
## Checks
101104

@@ -121,7 +124,8 @@ and `SHADOW_WEBKIT_DRIVER` select explicit executable paths. Logs, screenshots,
121124
and a machine-readable result are written to `artifacts/native/`. This test
122125
checks the real embedded window, Rust IPC, approval, file and terminal tools,
123126
reload, cancellation, compact layout, model routing/fallback notices, goals and
124-
their live transcript, pause, light/dark/compact/goals/routing accessibility,
127+
their live transcript, pause, managed background processes,
128+
light/dark/compact/goals/routing/background accessibility,
125129
and managed shutdown. It also verifies
126130
that the executable embeds the current compiled interface and does not load
127131
`libpython`.

‎docs/NATIVE_MIGRATION.md‎

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,10 @@ Implemented foundation:
7777
editable Plan/Build/Review/Test selections, preserved custom credentials and
7878
context limits, queued configuration snapshots, explicit per-task overrides,
7979
persisted model/fallback notices, and goal verification routed to Test.
80+
- [Managed background processes](NATIVE_BACKGROUND.md) for project servers and
81+
watchers, with permission checks, bounded live log tails, durable status and
82+
audit events, project-scoped controls, bounded concurrency, legacy history
83+
import, and cancellation/shutdown that waits for process-group cleanup.
8084
- A persisted native task loop, per-workspace FIFO follow-ups, four concurrent
8185
workspaces, scoped approvals, cancellation that waits for cleanup, restart
8286
recovery, and atomic completion/usage/event commits. Continuation and branching

‎docs/NATIVE_VERIFICATION.md‎

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ remain in [NATIVE_MIGRATION.md](NATIVE_MIGRATION.md).
66

77
## Automated checks
88

9-
`cargo fmt --all --check`, Clippy with warnings denied, and all **78 native
9+
`cargo fmt --all --check`, Clippy with warnings denied, and all **89 native
1010
integration tests** pass on the development machine. The suite covers:
1111

1212
- Config validation, private secrets, untrusted project overlays, profile locks,
@@ -42,6 +42,13 @@ integration tests** pass on the development machine. The suite covers:
4242
planning permissions, and goal verification through the Test model. A provider
4343
failure is checked to never send the task to the default endpoint; invalid
4444
settings are checked before writing secrets.
45+
- Background permission checks, logs without newlines, split UTF-8 output,
46+
output floods with a bounded live tail, graceful/forced cancellation, child
47+
cleanup, concurrent stop calls, per-project/global limits, project isolation,
48+
coexistence with agent tasks, and shutdown. Restart/import tests preserve the
49+
original legacy database and verify that an unrelated process with a stored PID
50+
is never signalled. Active processes remain visible past 100 newer history
51+
entries; failed audit storage prevents spawning an unrecorded command.
4552

4653
The host's distro `rustdoc` needs its LLVM library directory in the loader path
4754
for doc tests. The full suite was run with:
@@ -67,7 +74,7 @@ The first window run exposed a SQLite LIKE escape bug that appeared only after
6774
sessions existed. A regression now covers real session listing and literal
6875
search. Visual inspection also found a cancellation transcript race and an open
6976
sidebar obscuring a resized compact window; the window test checks both.
70-
Axe WCAG 2 A/AA and 2.1 AA checks pass in light, dark, compact, Goals, and Router workspace
77+
Axe WCAG 2 A/AA and 2.1 AA checks pass in light, dark, compact, Goals, Router, and Background workspace
7178
views. The compact check caught the Review button losing its accessible name
7279
when its text was hidden; the control now retains an explicit label.
7380
The native test also creates a goal through the drawer, completes all three
@@ -80,6 +87,10 @@ confirms the chosen model in actual requests and the conversation, reloads its
8087
notice without duplication, and checks a visible default-model fallback for a
8188
missing saved route. The Router screenshot is inspected alongside the existing
8289
workspace views.
90+
The window test starts a background process through the form, inspects live and
91+
retained output, performs a coding task while it runs, and stops it through the
92+
drawer. It then closes the application with another background process and
93+
terminal child running, checking that the app and both managed process groups exit.
8394
Fourteen interface unit tests cover ordered replay, pagination, stream finalization,
8495
listener cleanup, interruption, native tool cards, routing/fallback replay, and
8596
disambiguated model labels that omit URL credentials. The seven existing browser

0 commit comments

Comments
 (0)