Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 42 additions & 0 deletions .context/DECISIONS.md
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,48 @@ For significant decisions:

-->

## [2026-09-05-195906] Pi extension deploys as a flat single file (.pi/extensions/ctx.ts) with no package.json

**Status**: Accepted

**Context**: Pi loads both flat .pi/extensions/*.ts and subdirectory .pi/extensions/<name>/index.ts extensions; only the subdirectory form can carry a package.json with runtime dependencies. Decided 2026-08-23.

**Decision**: Pi extension deploys as a flat single file (.pi/extensions/ctx.ts) with no package.json

**Rationale**: The shim needs only a type-only import of @earendil-works/pi-coding-agent plus node:child_process, so a flat file keeps exact symmetry with the OpenCode plugin deploy (one managed path, refresh in place, the same validate semantics) and no npm install step for users.

**Consequence**: ctx setup pi manages exactly one extension path. A future extension that needs runtime dependencies must move to the subdirectory form. node:child_process stays mandatory because the Pi exec helper has no stdin pipe for the hook envelope.

---

## [2026-09-05-195906] Pi re-injection predicate scans the live context instead of a flag or a custom compaction summary

**Status**: Accepted

**Context**: After Pi compaction the injected packet is either folded into the lossy LLM summary or survives in the kept tail. Alternatives were a boolean injected flag in extension memory and a custom session_before_compact summary owned by ctx. Decided 2026-08-23; shipped in 694f6d37.

**Decision**: Pi re-injection predicate scans the live context instead of a flag or a custom compaction summary

**Rationale**: sessionManager.buildContextEntries() (summary + kept tail + post-compaction entries) is the ground truth for what the model can still see, so scanning it for the ctx customType re-injects exactly when the packet is gone and never duplicates one that survived. A flag is lost on extension teardown (/new /resume /fork /reload), and a custom summary would replace the Pi summary with undocumented cross-extension precedence.

**Consequence**: No extension state decides injection; only the packet cache is in memory and is re-warmed on session_start. Known edge: an overflow compaction with willRetry skips before_agent_start, so re-injection waits for the next prompt.

---

## [2026-09-05-195906] Pi extension injects the ctx packet with display:true (visible in the TUI)

**Status**: Accepted

**Context**: Pi before_agent_start can inject a persistent custom_message with display true or false; the ctx packet could be hidden from the user like a system-prompt fragment. Decided 2026-08-23 during the Pi integration design (specs/pi-cli-integration.md, resolved open question 1).

**Decision**: Pi extension injects the ctx packet with display:true (visible in the TUI)

**Rationale**: Transparency: the user sees exactly what ctx put in front of the model, and an injection bug (duplicate, stale, missing) shows in the TUI instead of failing silently.

**Consequence**: The packet appears in the Pi transcript on the first prompt and after every re-injection; any future nudge-to-LLM change (PI.8 c) keeps the same visibility rule.

---

## [2026-08-23-120839] Codex memories are out of scope for the ctx memory bridge

**Status**: Accepted
Expand Down
30 changes: 30 additions & 0 deletions .context/LEARNINGS.md
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,36 @@ DO NOT UPDATE FOR:
-->


## [2026-09-05-195906] golangci-lint exits 7 with 0 issues when tools/typecheck/*/node_modules exists on this Windows machine

**Context**: After npm ci in tools/typecheck/pi (the CI typecheck gate run locally), golangci-lint run ./... printed 0 issues but exited 7 with: typechecking error: pattern ./...: open tools\typecheck\pi\node_modules\@earendil-works\pi-coding-agent\dist\extensions: The system cannot find the file specified. Deleting node_modules restored exit 0 with the tree otherwise unchanged.

**Lesson**: The golangci-lint package loader walks ./... into node_modules and fails on a directory it cannot open on Windows; the exit code, not the printed issue count, is the gate signal. Upstream CI is unaffected because lint and typecheck run in separate jobs.

**Application**: Run the local typecheck in tools/typecheck/<tool>, then delete its node_modules before golangci-lint (or lint first). Treat a non-zero golangci exit with 0 issues as an environment failure, not a clean run.

---

## [2026-08-23-204632] Windows git over HTTPS fails with SEC_E_NO_CREDENTIALS unless the openssl backend is pinned

**Context**: During the pi integration, every `git fetch`/`ls-remote` over an https remote on this Windows machine failed with `schannel: AcquireCredentialsHandle failed: SEC_E_NO_CREDENTIALS (0x8009030e)` - git's default TLS (schannel) has no usable credential state here. `gh` (own TLS stack) worked fine, and SSH keys were rejected, so the failure looked like a credentials/remote problem.

**Lesson**: git's schannel backend and the Windows credential manager can be broken independently of the remote; the fix is a per-invocation backend override, not key/credential surgery.

**Application**: On this machine, run every git https remote operation as `git -c http.sslBackend=openssl <cmd>` (git 2.51 supports it). Diagnose with `gh api` first to rule out remote-side auth before touching keys.

---

## [2026-08-23-204632] zensical site rebuilds are non-reproducible off the canonical toolchain (entity-escape drift)

**Context**: Rebuilding site/ locally with the pinned zensical 0.0.51 (fresh venv, Python 3.10) produced 120 files of pure escape drift (`&#39;` vs literal `'` inside highlighted code blocks) against the committed artifacts; pinning pygments older did not help.

**Lesson**: The zensical pin only pins the generator, not its transitive deps (markdown/pygments/jinja resolution drifts), so committed site/ output is not reproducible on arbitrary machines; the drift is user-invisible (entities render identically) but is pure diff churn that flips back on the next canonical build.

**Application**: After a local `zensical build`, run `git diff --ignore-cr-at-eol --numstat site/` and inspect representative hunks BEFORE committing; if the delta is escape drift rather than real content, revert site/ (`git checkout -- site/`, remove new untracked pages) and defer the rebuild to the canonical build machine; record the deferral in the task notes.

---

## [2026-08-23-170949] Hook commands must survive four shells and hostile cwds; hosts punish pre-ctx aborts

**Context**: Adversarial audit of every ctx hook surface (Claude/Codex/Copilot manifests, 16 Copilot wrapper scripts, OpenCode plugin, trace hook, plugin-reload) after the Codex non-repo-cwd anchor bug: 20 confirmed defects in 7 classes.
Expand Down
96 changes: 96 additions & 0 deletions .context/TASKS.md
Original file line number Diff line number Diff line change
Expand Up @@ -3102,3 +3102,99 @@ work is the delivery layer: plugin root, manifests, deployer, parser, docs.
- [x] [CX6] Verification gate: make lint, make test, make audit green; live ctx setup codex --write + codex exec hook run (SessionStart context injection, UserPromptSubmit nudges, SessionEnd journal import) recorded in the PR; DECISIONS entries for plugin-root placement, TOML append strategy, skill generation, memories non-goal. Spec: specs/codex-integration.md #priority:medium #session:581183bc #branch:feat/codex-integration #commit:ce5a8328 #added:2026-08-23-120739

- [ ] [CX7] Follow-up: Windows commandWindows overrides for the Codex hooks manifest (hooks currently require a POSIX shell with git on PATH). Spec: specs/codex-integration.md #priority:medium #session:581183bc #branch:feat/codex-integration #commit:ce5a8328 #added:2026-08-23-120739

## Phase PI — Pi CLI Integration

Spec: `specs/pi-cli-integration.md`
Branch: `feat/pi-cli-integration` (based on upstream main ce5a8328, 2026-08-23)

Pi (earendil-works/pi, pi.dev) is a self-extensible coding-agent CLI with a
TypeScript extension system, Agent Skills support, native AGENTS.md, and — by
design — no MCP. Integration follows the OpenCode blueprint: Go setup package +
embedded TS shim + bundled skills + shared AGENTS.md template.

- [ ] Read `specs/pi-cli-integration.md` before starting any PI task.
#added:2026-08-23-151000
- [x] PI.1: Embedded assets — `internal/assets/integrations/pi/extension/ctx.ts`
(thin shim: before_agent_start live-context-scan packet injection,
session_start warm-up cache, session_compact cache drop, tool_result
post-commit / check-task-completion with isError gating, agent_settled
check-persistence; hook-JSON envelope on piped stdin) and
`internal/assets/integrations/pi/skills/` (same 10-skill set as
OpenCode; embed.go directives added) #added:2026-08-23-151000
#completed:2026-08-23
- [x] PI.2: Accessors + constants — `internal/assets/read/agent/pi.go`
(PiExtension, PiSkills) and `internal/config/hook` pi path constants
(+ asset.go DirIntegrationsPi*) #added:2026-08-23-151000
#completed:2026-08-23
- [x] PI.3: `internal/cli/setup/core/pi/` package — pi.go, extension.go,
skill.go, validate.go + deploy_test.go/testmain_test.go modeled on the
opencode suite (all 4 tests green) #added:2026-08-23-151000
#completed:2026-08-23
- [x] PI.4: CLI wiring — `case cfgHook.ToolPi` branch in setup root.Run()
(run.go + doc.go); supporting text: hooks.yaml hook.pi + supported-tools line,
write.yaml write.hook-pi-*, config/embed/text DescKeys, write/setup InfoPi*
(TestDescKeyYAMLLinkage green; no new Use* constant, no new subcommand)
#added:2026-08-23-151000 #completed:2026-08-23
- [x] PI.5: Docs — pi entry in supported-tools reference (integrations.md +
setup.md + multi-tool-setup.md) + pi quickstart guide (docs/home/pi.md +
zensical nav). NOTE: site/ HTML rebuild deferred — this machine's zensical
0.0.51 venv renders entity-escape drift (120 files, &#39; vs ') vs the
committed artifacts (unpinned zensical transitive deps); rebuild on the
canonical build machine and stage site/ with a follow-up commit
#added:2026-08-23-151000 #completed:2026-08-23
- [x] PI.6: Validation — go build ./... + golangci-lint (0 issues) + targeted
go test green; full-suite delta vs clean main verified: zero new failures
(20 failing packages, all pre-existing Windows-environment: CRLF render
drift, .exe exec, audit path exemptions). Scratch project: init +
dry-run + --write + idempotent re-run + tamper-refresh (byte-identical to
embedded) + unknown-tool list all verified with a freshly built binary.
Live pi: extension loads clean (A/B run with/without .pi identical);
full LLM round-trip blocked by local pi provider config (gx10-spark/*
unreachable from this environment) — left for a working-provider machine
#added:2026-08-23-151000 #completed:2026-08-23
- [x] PI.7: CI type-check for the pi extension — tools/typecheck/pi/
(tsconfig + package.json + lockfile with @earendil-works/pi-coding-agent
0.84.2 types, tsc --noEmit PASSING locally) + typecheck-pi-extension job in
.github/workflows/ci.yml (mirrors tools/typecheck/opencode/). Decisions
locked 2026-08-23: display:true, CI typecheck in scope
#added:2026-08-23-151000 #completed:2026-08-23
- [ ] Bug (review finding, pre-existing): OpenCode plugin lifecycle legs lack
the hook-JSON stdin envelope — `ctx system post-commit` from
internal/assets/integrations/opencode/plugin/index.ts bails silently in
FullPreamble (no envelope fed via BunShell), so the post-commit nudge is
likely dead; check-task-completion/check-persistence run but key per-session
state to IDUnknown. Spec: specs/pi-cli-integration.md "Hook envelope
requirement" section documents the correct envelope shape; fix the opencode
plugin the same way (or add envelope flags on the Go side) #priority:medium
#added:2026-08-23-151000
- [ ] PI.8 (audit follow-ups, non-blocking): from the fable-5 effort-max
branch audit (2026-08-23, verdict ship-ready after MAJOR 1, which is
fixed on-branch): (a) post-compaction re-warm runs `ctx agent` inline on
the prompt path (up to 15s) — consider re-warming inside the
session_compact handler instead, and cache the fetch promise rather than
the packet so a first prompt that outruns the warm-up cannot spawn a
second `ctx agent` (review 2026-09-05); (b) embedded assets are not EOL-pinned
(no .gitattributes; Windows builds embed CRLF skills vs LF on CI —
cross-binary refresh flapping; add `internal/assets/** text eol=lf`
pin, repo-wide pre-existing hazard); (c) hook nudge stdout is discarded —
Pi's tool_result handlers can return {content} to append the nudge to the
tool result and reach the LLM (OpenCode parity chose .quiet(); design
decision, not a bug); (d) tools/typecheck/pi/tsconfig.json could mirror
the opencode twin's explicit `paths` mapping for @earendil-works/pi-coding-agent
(resolution works today via node_modules probing; hardening only);
(e) extract a shared deploy helper for the pi/opencode twins — skill.go
and validate.go differ only by package name and constants (review
round 2 suggestion, 2026-09-05)
#priority:low #added:2026-08-23-221600
- [x] PI.9: Review round 2 (maintainer nits on PR #161, 2026-09-05): docs
re-injection predicate reworded to the live-context scan (docs/home/pi.md,
docs/operations/integrations.md); spec latency claim softened (cache miss
runs the fetch on the prompt path, 15s bound); "plugin hook" -> "tool
integration" in ctx-agent SKILL.md (pi + opencode trees);
TestPiSkillsMirrorOpenCode byte-identity guard over the mirrored skill
trees; exact 0.84.2 pin in tools/typecheck/pi/package.json + lockfile
root. Preceded by the upstream main merge (9520e171): 7 shared-insertion
conflicts resolved, zero new test failures vs the main baseline (28
pre-existing Windows-environment packages on both). site/ rebuild still
deferred to the canonical build machine #added:2026-09-05-194204 #completed:2026-09-05
22 changes: 22 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,28 @@ jobs:
working-directory: tools/typecheck/opencode
run: npx tsc --noEmit

typecheck-pi-extension:
name: Typecheck Pi extension
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v7

- name: Set up Node
uses: actions/setup-node@v7
with:
node-version: '20'
cache: 'npm'
cache-dependency-path: tools/typecheck/pi/package-lock.json

- name: Install dependencies
working-directory: tools/typecheck/pi
run: npm ci

- name: Type-check embedded extension
working-directory: tools/typecheck/pi
run: npx tsc --noEmit

vscode-extension:
name: VS Code extension build + typecheck
runs-on: ubuntu-latest
Expand Down
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,7 @@ editors/vscode/*.vsix

# Type-check tooling for embedded plugins
tools/typecheck/opencode/node_modules/
tools/typecheck/pi/node_modules/

# Some ideas are best kept hidden.
ideas
Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -167,7 +167,7 @@ recipes are the right next stop.
| [Recipes](https://ctx.ist/recipes/) | Practical workflow guides |
| [CLI Reference](https://ctx.ist/cli/) | All commands and options |
| [Context Files](https://ctx.ist/home/context-files/) | File formats and structure |
| [Integrations](https://ctx.ist/operations/integrations/) | Claude Code, Codex, OpenCode, Cursor, Aider setup |
| [Integrations](https://ctx.ist/operations/integrations/) | Claude Code, Codex, OpenCode, Pi, Cursor, Aider setup |
| [Operations](https://ctx.ist/operations/) | Runbooks, day-to-day, hub deployment |
| [Security](https://ctx.ist/security/) | Trust model, audit trail, permissions |

Expand Down
4 changes: 4 additions & 0 deletions docs/cli/setup.md
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ ctx setup <tool> [flags]
| `copilot` | GitHub Copilot |
| `copilot-cli` | GitHub Copilot CLI (instructions, skills, agent, MCP) |
| `opencode` | OpenCode (terminal-first AI coding agent) |
| `pi` | Pi coding-agent CLI (pi.dev) |
| `windsurf` | Windsurf IDE |

!!! note "Claude Code Uses the Plugin System"
Expand Down Expand Up @@ -84,4 +85,7 @@ ctx setup opencode --write
# .codex/config.toml, AGENTS.md, and .agents/skills/
ctx setup codex
ctx setup codex --write

# Generate Pi extension, skills, and AGENTS.md
ctx setup pi --write
```
Loading
Loading