Repository navigation
Releases: hackafterdark/phosphor
Release list
v0.7.1
Phosphor v0.7.1
A performance and stability release: provider prompt caches stay warm
across agent turns, Windows sandbox startups and shutdowns no longer
stall, and the security advisory backlog is cleared.
Performance
- Provider prompt caches stay warm across agent turns. Dynamic run
state (todo list, active goal, post-turn reminders) used to be
reassembled into the system prompt on every agent-loop iteration,
invalidating provider prefix caches on every todo update. It now rides
the run's user message once as a<run_context>block, so the wire
prefix stays byte-identical and providers keep serving from cache. - MCP server instructions are ordered deterministically, so tooling
around the prompt stops churning the cache for no reason. - A drifting model is re-anchored on its open todo via tool results,
keeping long runs on track without rewriting the system prompt.
Fixes
- Windows ACL crawls are bounded. Container ACE grants and revokes
no longer block process startup or exit for minutes on deep workspace
or toolchain-cache trees; they run behind explicit deadlines, a grant
overrun fails the launch closed, and any revoked ACEs left behind are
cleaned up at the next launch. - Second instance fails fast. Starting another Phosphor against the
same data directory now fails instantly with the owner's PID instead
of stalling for 30 seconds on SQLite busy timeouts. Short-lived
read-only commands can still inspect a database a TUI is using. - Confined git works again. Writable sandbox roots can now unlink
and rename files, sogit add/commit/statuswork inside the
sandbox again, while.gitmetadata stays fenced from direct agent
writes. - No more ghost text over the TUI. Confined children launch with
CREATE_NO_WINDOW, so a child failing early (e.g.ssh.exeinside
the sandbox) can no longer paint raw text onto the terminal screen. - Continuation and queued turns deliver their notes. Recovery
instructions ("continue where you left off") and the todo snapshot
are now delivered on the outbound prompt instead of sitting in the
queue and leaking into a later user turn. - Flaky Windows CI test fixed. Session title generation no longer
races the prompt-cache wire test, ending the spurious
TestWirePromptByteStableAcrossTodosUpdatefailure.
Security
golang.org/x/netupgraded to v0.62.0, fixing CVE-2026-97045
(html.Rendernamespace-transition bug) and CVE-2026-78661
(quadratic-complexity panic when coalescing text nodes).- Remaining code-scanning and Dependabot alerts were triaged and
dismissed with evidence where the vulnerable code path is unreachable
in this codebase (unusedx/crypto/openpgp, unused TIFF decoding in
disintegration/imaging).
v0.7.0
Phosphor v0.7.0
This release ships kernel-enforced OS-level sandboxing for agent-executed
commands across Linux, macOS, and Windows, along with a broad set of security
hardening and usability enhancements.
OS-level sandboxing
The bash tool and MCP stdio servers now run inside kernel-enforced sandboxes
instead of relying on tool-layer path checks alone:
- Linux: seccomp-based filtering of child processes, with a hardened
denylist and safely floored resource limits. - macOS: Seatbelt profiles with rlimit-based resource caps; DNS and TLS
trust Mach services are granted so toolchains keep working inside the
sandbox. - Windows: restricted-token + Job Object sandboxing, with an AppContainer
tier for confined children, capability probing, and container ACE grants
that are revoked on shutdown. - Kernel resource limits (CPU, memory, file size, and more) are applied to
sandboxed bash and MCP children on all platforms. - ProxyOnly network tier: egress through a proxy only, with denial
messages that point at the config needed to allow a host (the refused host
is logged, never the full URL). - Sandbox escalation UX: commands that legitimately need to leave the
sandbox prompt the user for a one-off pre-grant; escalation prompts cannot
be bypassed by YOLO mode, allowlists, or hook pre-approvals. YOLO pin and
escalation pre-grants are available for recurring workflows. - Escape-hatch gating: host binaries that could bypass the sandbox are
denied while it is active, and nested shells on degraded hosts are closed
off. - The sandbox mode and resource caps are floored against workspace overrides,
so project settings cannot silently weaken them.
Security hardening
- Agent commands are denied read access to well-known credential locations
(.env, SSH keys, service-account files, etc.). - MCP stdio servers no longer inherit ambient credentials from the parent
process. - Workspace config files and
.gitare read-only for the agent, and the
sandbox defaults to workspace mode. - URL credential checks were hardened; secret scans on URLs or network
hiccups no longer abort agent runs. - Dependency upgrades: echo v5.4.2 (clears a critical vulnerability gate),
plus routine dependency bumps.
Toolchain & developer experience
- Opt-in, cache-scoped trust for language toolchain caches (e.g.
GOMODCACHE)
shared by the sandbox and path guard, so module inspection and local docs
lookups work out of the box. - Agents are steered toward local toolchain documentation (
go doc,pydoc,
man, ...) instead of web fetches when the local toolchain can answer. - New
allow_commandspermission opt-in and an OTel endpoint probe.
Fixes
- Runs that end on a spoken but unexecuted next step now continue instead of
stalling. - Windows job resource limits are attached only when sandboxing is active.
- Shutdown waits on in-flight workspace runs are now bounded, terminal Kitty
graphics-protocol probes are gated, and rendered Mermaid diagram links follow
the active theme.
Documentation
- New ADR for in-binary OS sandboxing, sandbox escalation/limits/toolchain
trust in the config reference, and expanded security-hardening docs
(including vibe-coding guidance).
v0.6.0
New Features
- Memory graph viewer with offline reports and search (#49)
- Skills dialog for viewing and toggling agent skills, plus a skill details viewer (#42, 7ee1808)
- phosphor-cron-jobs skill with validation of job
session_modeat load (#41)
Security
Hardening pass closing all 10 findings from the 2026-10-20 security audit:
- Egress firewall now validates resolved IP addresses by default (DNS-rebinding defense), and bracketed IPv6 literals no longer bypass the raw-IP block (#50)
- Wire-level redaction extended to tool-call inputs and tool results;
Summarize/GenerateTitleroute through the same redaction path (#50) - Wrapper-aware bash command deny list (
env curl,xargs wget,find -exec, absolute paths,.exesuffixes no longer slip past) (#51) fetch,download,agentic_fetch, andweb_searchall share the secured egress client;allow_raw_ips/ip_allow_listconfig is honored by every network tool (#51, #52)write/appendnow run the write-path secret gate;web_fetchallow-list race fixed; per-agent redaction policy replaces process-global state (#51)- Residual findings:
csync.Mapcopylocks defect resolved, stale security-doc paths corrected (#52)
Fixes
- Coerce schema type mismatches in tool-call inputs before execution (#48)
- Refresh the sidebar git branch; stabilize client session test (#39)
- Clear message when pasting an image into a text-only model
- Surface cron job events; speed up cron tests (#37)
Chores
v0.5.6
v0.5.6
Fixes
- Chat scroll stays put while you read history: during an active agent turn, scrolling up to read earlier text could snap the view back to the newest message, so follow mode is now anchored to position instead of scroll direction. Auto-follow resumes only once the view actually reaches the bottom (including via one big scroll-down), and stays out of the way while you are scrolled up.
- Scheduled jobs fire again: scheduled jobs were listed correctly but never fired; the dispatch path is fixed and jobs run on schedule.
New
- Git branch in the sidebar: the current git branch is shown under the workspace path in the sidebar, so you always know which checkout the agent is working in.
Full diff: v0.5.5...v0.5.6
v0.5.5
v0.5.5
Security
- Closed a workspace sandbox escape: compound shell commands could previously sidestep the path guard with
cd <outside> && <command>, letting the agent read or write files outside the workspace — confirmed live against OS files and the user's SSH directory. The fix adds two independent confinement layers:cdtargets are bounds-checked statically before the shell starts, and the interpreter's actual working directory is verified at runtime before any command executes or file opens. Heredoc bodies and herestring operands are now masked as data during validation, so file content can neither fake its way past the guard nor get corrupted by path rewriting. Ships with regression tests pinning every red-team vector as refused and legitimate in-workspace operations as allowed.
Fixes
- Memory tool refusals now guide recovery: refusals for a missing entry id or an unknown op name previously offered no way forward, so agents would guess invalid ops and give up. The refusals now name
op=addand list the valid op menu, and the tool description states theop=adddefault and the retire-without-id contradiction path up front.
Full diff: v0.5.4...v0.5.5
v0.5.4
Patch Release: Stability, Performance & Observability
Agent loop stability
- Empty-turn recovery — When a step ends normally but produces nothing actionable (no tool call, no text), the agent now
automatically continues the turn with a small bounded budget, so dropped chains of thought no longer stall a response. - Truncated tool-call recovery — Incomplete JSON streamed for a tool call is now detected and retried automatically
within a bounded budget, fixing rare dropped tool calls from providers that cut off arguments.
Both recoveries are tracked as internal continuations, keeping per-turn dispatch accounting correct.
TUI performance
- Faster prompt input — Sidebar panel data (workspace-search progress, memory sources/tallies) is now fetched off the
render path via background ticks, so a slow store read no longer delays keystrokes. - Cached sidebar rendering — The logo block and section strings are memoized and reused across animation/spinner-only
frames, rebuilding only when state actually changes. - Markdown alignment in streamed replies — Mid-stream replies assembled from multiple fragment renders could produce
rows wider than the wrap width, causing the terminal to re-wrap lines and headings/bullets to appear randomly indented.
The final frame now drops the streaming cache and draws one coherent full render, with seam trimming that compares
visible glyphs so blocks keep a single blank line between them.
Misc edge-case fixes: nil-cursor guard on draw, immediate memory panel refresh on session switch.
New observability tools
- phosphor_trace — Reads Phosphor's in-process OpenTelemetry span ring and prints a compact per-turn trace tree (span
name, nesting, duration, status, key GenAI attributes: model, step index, finish reason, token usage, tool name). Great
for diagnosing which step stalled or where nesting broke.
Enable it with observability.memory_buffer in phosphor.json (number of recent spans kept in the ring; off when
unset).
Chores
- Cross-platform golden-file comparison now normalizes line endings, so tests pass identically on Windows and Unix
checkouts.
ஃ Generated with Phosphor
v0.5.3
Agent Reliability & Qwen/vLLM Hardening
Added
- Automatic continuation when a response is cut off by the token limit, instead of the turn silently ending. Configurable via
max_tokens_continuationsinphosphor.json(default: 2). - Request-size clamping to prevent hard context-window rejection errors from the provider — applied both before sending a request and re-checked at every step of a multi-step turn.
- Recovery for a tool-call block that the parser fails to recognize (seen with Qwen's
qwen3_xmltool-call format), instead of the turn silently dead-ending. - A lightweight "build incrementally" nudge in the coding system prompt, encouraging scaffold-first development on large or open-ended builds instead of fully designing everything before writing any code.
Fixed
- Turn termination caused by raw ChatML control tokens appearing in model output or reasoning — tokens are now defanged on the way in, and the system prompt no longer requires spelling out the literal token to discuss the issue.
- A deadlock where the agent's own internal continuation/retry logic was incorrectly treated as a competing request and blocked itself.
- Duplicate "thinking" output and an infinite loop that could occur while recovering from a cut-off response.
- Auto-summarization (context compaction) silently failing to run before a request — sessions could exceed their context budget without ever compacting, because the proactive check saw itself as a busy session and gave up.
Changed
- Updated the
fantasyprovider library (0.45.0 → 0.45.2), picking up an upstream fix for reasoning/content ordering when a provider batches the end of a reasoning block with the start of the next content in a single stream chunk.
Memory UX
Added
/memoryslash command family for inspecting and managing the memory vault from the TUI:/memory— status dialog (corpus counts, injected bytes vs. budget, vault path, tamper-seal status, active threads)/memory sources [query]— search the memory corpus, or view this session's provenance/memory review— list pending drafts and queued proposals;confirm/ignore/retireto resolve them/memory fsck— full rescan reconciling the index against the on-disk markdown/memory budget— injected byte usage, corpus and tag counts, breakdown by type/memory policy [rule]— list or add human-asserted policy entries/memory pin/unpin/demote/dispute/retire/cite— per-entry lifecycle management/memory key— tamper-seal key status, show, restore, rotate
- Memory Review dialog for confirming, ignoring, or retiring pending memory drafts and proposals.
- Memory entries added to the command menu: Memory Status, Review Memory, Memory Sources, Check Memory (fsck), Memory Budget, Memory Policy.
- Memory sidebar panel showing injected-byte budget usage and active/pending/recalled entry counts, with warnings surfaced for unsigned entries, a missing integrity key, or quarantined entries.
Fixed
- Various memory ID and stats accuracy issues; integrity/tamper-seal hardening around hand-edited entries.
v0.5.1
Custom provider management in the command menu
The command menu gains two new entries — Manage Custom Providers and Add Custom Provider — so providers can be set up
and tuned without hand-editing JSON.
Manage Custom Providers lists every provider defined in your config files and opens a full editing view:
• Edit provider settings in place: display name, base URL, API key, type, tool-call format, and more
• Manage the provider's models down to individual options — context window, max tokens, cost, reasoning levels,
temperature/top-p, provider options, and more
• Add and delete models; toggle booleans and cycle enum values with a single keypress
• Existing values load into the editor when you open a field, so you can backspace to clear, or use the arrow keys to
tweak in place
• Safe deletes with a confirmation step, including a heads-up when a provider still lives in a file the app won't write
to
Add Custom Provider is a four-step wizard (name → base URL → API key → model IDs) that validates as you go and writes
the result to the app's config.
v0.5.0
✨ Headline — first-party memory system
A durable memory vault so context, decisions, and preferences survive across sessions. Ships on by default and fully
configurable via the memory.* config block.
• Three agent tools — memory (record), memory_search (recall), memory_read (load a stored value by id).
• Structured entries — typed facts with closed-menu categories, plus thread , tags , and scope ; entries are
tombstoned, not deleted via supersede / retire , so history stays answerable.
• Controllable autonomy (dials, validated at load) — write approval ask / balanced / auto , proactive_recall off /
hint / on , cross_session isolated / related / transcript , and human_edits authoritative / advisory .
Consequential writes (e.g. decisions) can be held for confirmation by policy.
• Tamper-evident vault (HMAC integrity seal) — every entry sealed with a keyed digest so poisoned/tampered content is
refused; seal key managed via /memory key . On by default.
• Learned-secret memory — detected secrets are remembered by keyed hash and scrubbed on reappearance (on by default).
• Context safety — the always-injected block is hard byte-capped so memory can never crowd the window; a budget floor
skips model-spending memory work when you're low on quota.
• Subagent guard — only the primary agent may write memory; subagents run write-guarded so throwaway or cron-style
prompts can't contaminate the shared vault.
• Opt-in distillation, auto-reindex on vault changes, and contended-write replay for concurrent instances.
• TUI — a /memory slash command, a review dialog, and human-readable frontmatter titles.
• Evals & coverage — a retrieval eval harness plus tests for invariants, integrity, drift, concurrency, and gate
behavior.
✦ Agent & TUI output fixes
• Fixed agent responses rendering with thinking mixed into the final answer — reasoning and the final response now
display distinctly (rode along with the memory work).
• Various tool-call and agent-turn correctness fixes landed alongside the memory phases.
✦ Search, indexing & commands
• Fixed autocomplete tab selection, the workspace index, and the /compact command.
• Added doc types to the FTS5 index; assorted structural_search improvements.
v0.4.0
What's Changed
- Security/additional secrets protection by @tmaiaroto in #27
- Updated documentation
Bug Fixes
- File reference autocomplete list selection, the correct (highlighted) file is now selected
- Workspace index information widget on the right side panel displays correct index status
/compactslash command fixed
Full Changelog: v0.3.0...v0.4.0