feat(providers): add Pi coding agent - #7211
Conversation
|
Important Review skippedAuto reviews are disabled on this repository. Please check the settings in the CodeRabbit UI or the ⚙️ Run configurationConfiguration used: Repository UI Review profile: CHILL Plan: Team Run ID: You can disable this status message by setting the Use the checkbox below for a quick retry:
Warning Your free Security trial is over. An organization admin can upgrade to Advanced for continuous pull request security review or dismiss this notice. Comment |
There was a problem hiding this comment.
Effect service conventions review of the new Pi provider code. Two error-modeling issues found; everything else (namespace subpath imports, Effect.catchTags usage, layer/driver construction acquiring ChildProcessSpawner/FileSystem/IdAllocatorV2/ServerConfig from the environment, Schema.TaggedErrorClass failures) follows the conventions.
Posted via Macroscope — Effect Service Conventions
There was a problem hiding this comment.
One consistency finding on the new web provider icon wiring. Everything else in the web scope (providerDriverMeta.ts, ProviderModelsSection.tsx, contextWindow.ts, session-logic.ts, AddProviderInstanceDialog.tsx) is registry/data-only and matches the existing per-driver patterns.
Posted via Macroscope — UI Consistency
ApprovabilityVerdict: Not approved Macroscope's review found this PR not approvable — This XXL PR adds a complete Pi provider with subprocess RPC, MCP credentials, permission handling, session lifecycle, text generation, and cross-platform UI/state changes. It also modifies shared orchestration behavior and has unresolved resource, permission, correctness, and lifecycle risks that require human review. Not approved because:
Adjust the Minimum Blocking Severity for this repo — including turning it Off — in Settings. You can add or adjust custom eligibility rules. Learn more. |
There was a problem hiding this comment.
One finding on the Pi icon geometry after the tile removal. Everything else in the web scope (provider icon map, driver meta, model placeholder, display-name and picker option entries) follows the existing per-provider patterns.
Posted via Macroscope — UI Consistency
There was a problem hiding this comment.
Effect service conventions: one finding — a raw child-process stderr payload is copied into a log annotation. Elsewhere in this repo process output is reported as lengths only (stdoutLength/stderrLength, lineLength), with explicit tests asserting stderr is not retained in diagnostics.
Posted via Macroscope — Effect Service Conventions
There was a problem hiding this comment.
Two log annotations in the new Pi adapter copy Pi's raw wire error text into the observability stream. Everything else in the Pi files (error attributes, cause handling, driver/layer shape, dependency acquisition) matches the repo's adapter conventions.
Posted via Macroscope — Effect Service Conventions
7c18cde to
f8c8600
Compare
The default thinking level was advertised with the sentinel id "inherit", so re-picking the Default-tagged choice sent "do not change" and silently kept the previously applied level. Give every choice its real level id and apply it explicitly; Pi's discovered default keeps only the Default tag.
The Pi default model advertises no thinking choices, so an unqualified return kept the effort a previous pick had applied. Re-capture the configured thinking baseline and restore it alongside the baseline model replay, with a high-to-default adapter regression test.
The base branch now carries live context usage on provider turns (tokenUsage, pingdotgg#8144) and the web meter reads it from the projection. Pi kept a second owner for the same data: a contextUsage snapshot on the provider thread, refreshed after terminalization and invalidated by hand on rollback. Read Pi's session stats while the turn settles and attach them to the completed provider turn instead, then drop the provider-thread field and its generation bookkeeping. A turn without usable stats simply carries no report, so the meter keeps the last reported turn without adapter-side retention logic. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Switching models kept the previous model's option selections, so an effort picked for one model silently applied to the next. Record sticky options per model slug and resolve them on model switch, falling back to the target model's default instead of carrying anything over.
Storage written before per-model memory existed hydrated an empty map, so the first model switch after upgrading cleared the one remembered effort. Seed the map from each persisted sticky selection that carries options.
Mobile model picks already reset to the target model's advertised default, but nothing remembered an effort you had picked for a specific model. Record explicit option choices per instance and model in a small persisted map, restore them when that model is picked again, and land pending writes on app-update restarts.
Pi RPC get_commands omits TUI builtins, so /compact never appeared in the
composer. Advertise it and send {type: compact} instead of a prompt.
Stop during compact terminates the process because Pi abort does not
cancel manual compaction.
c7c93a5 to
93085e9
Compare
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes using high effort and found 1 potential issue.
❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.
Reviewed by Cursor Bugbot for commit 423ab37. Configure here.
Pi 0.84.4 live-test findingsTested #7211 at 1.
|
Trial layer for pingdotgg#7211 pi-provider. Net of the 18 unique CTM commits at aa38c5d, replayed onto the published trial tip. Adds Pi as an Early Access built-in provider (pi --mode rpc) with native steer, abort-based Stop, official-extension subagent projection, and session-tree rollback. Adapted the replay for this line's older CTM pin: thread fixtures include settledOverrideAt, and Pi select/input/editor questions set multiSelect to false. Shared registry files keep the existing OpenCode 2 entries. Not published to origin/trial/orchestrator-v2.1.
Bring trial Pi spawn discovery in line with the current pingdotgg#7211 pi-provider tip plus StiensWout#35 diagnose-early-pi-rpc-exits git and project package loading.
A first run creates a placeholder provider thread with no native identity, but ensureThread never handed that row to the adapter, so the Pi adapter registered a second row keyed by the session file. Both rows then received updates at turn end, and last-writer-wins on activeProviderThreadId decided at random whether the row carrying contextUsage was active — hiding the composer's context meter on most turns. Pass the run's provider thread through existingProviderThread at both ensureThread call sites so the adapter adopts the orchestration-owned row id (Pi's adopt branch already handles a row without a native ref). The replacement path after a failed resume drops the dead native ref so a fresh session still binds to the same row. OpenCode now only takes its resume path for rows that actually carry a native session, which keeps its behavior unchanged for these new inputs. Reported by @astarktc in pingdotgg#7211. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
discoverPiUserExtensions passed any *.ts/*.js directory entry as an explicit --extension path, including macOS AppleDouble sidecars like "._name.ts". Pi treats a parse failure on an explicit extension path as fatal, so one stale sidecar in ~/.pi/agent/extensions killed every Pi turn with an opaque "pi process closed stdout" error while interactive pi kept working. Skip dot entries, matching pi's own loader. Reported by @astarktc in pingdotgg#7211. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>




Problem
Pi users depend on their existing models, auth, extensions, skills, context files, and native session history. T3 Code did not have a Pi provider, and a shallow CLI wrapper would lose the customization and session behavior that make Pi useful.
Solution
This adds Pi as an Early Access provider on Orchestrator V2:
delegate_tasktool creates durable child threads in the existing subagent UI. User-installed Pisubagentextensions also project progress cards there, without inventing resumable child sessions that Pi does not provide.Pi defaultwhen optional model and command discovery cannot complete. The live interactive session remains authoritative and can handle startup prompts.Pi defaultrestores Pi's own model and thinking level.$skill chips are hoisted to Pi's leading/skill:nameform (all of them, not only the first), and catalog entries without a filesystem path stay listed. Pi's global skill location maps to the personal scope.tokenUsage, the same per-turn report the base branch added for Codex (feat(claude): compact old threads before they burn through usage #8144), so the shared context meter needs no Pi-specific plumbing.agent_settledis not always idle: an extension can start a detached compaction as it fires. The adapter confirms Pi is idle before terminalizing so that recovery stays inside the same turn, and Stop terminates the process once settlement has begun because Pi's generic abort does not cancel detached work.lastErrorso the banner is not blank.The MCP bridge, Pi subagent investigation, and per-model thinking support originated in @mwolson's stacked contribution and retain that authorship. The exit-code diagnostics, explicit thinking levels,
$skill hoisting, retry and compaction work-log items, and idle confirmation before terminalization come from @mwolson's follow-up branch and keep that authorship too. The per-model reasoning-effort memory from that branch is a cross-provider web and mobile change and is left for its own PR.Related work
Closes #397.
Closes #402.
Addresses #6685.
This supersedes the Pi implementations in #2211, #2748, #2800, #2812, #2831, #2856, #3818, #3947, #4355, #4445, #5688, #5882, and #6319.
This incorporates StiensWout#34 by @mwolson.
Validation
unknownerror-channel warnings inProviderSessionManager.test.ts, which the base branch has as well.git diff --check.t3code/codex-turn-mapping(0ae375b).Proof
Provider discovery
End-to-end Pi turn
Context meter persists across turns
The active context stays at 21k/272k while Pi's cumulative session total rises from 90k to 111k after the next completed turn.
Configured thinking default
Pi's effective setting appears as the labeled default while the internal selection continues to inherit from Pi.
Native steering
Checkpoint and Pi session-tree rollback
Clean Stop
Stopping an active Pi turn leaves the expected interrupted terminal and no provider stream error.
Stacked on #2829 (
t3code/codex-turn-mapping) until that branch lands.Built by GPT-5.6 Sol in T3 Code through Codex. Rebase onto the current base, the per-turn usage alignment, and review-feedback integration by Claude Fable 5 in Claude Code.
Note
High Risk
Introduces a large new provider adapter and changes OpenCode thread/session binding and prompt admission, which are security- and orchestration-critical paths; mobile persistence changes affect model/runtime selection across threads.
Overview
Adds Pi as a first-class mobile provider (icon, display label) and ships extensive PiAdapterV2 coverage for RPC turns, MCP injection, skills, compaction, retries, steering, rollback, and session adoption.
Mobile composer now remembers provider option choices per instance/model, persists them in the composer drafts document, and reapplies them when switching models in thread settings, the composer, and new-task flow. Runtime mode pickers are filtered to each model’s
supportedRuntimeModes, with a safe fallback when none are advertised.OpenCodeAdapterV2 treats a completed assistant message as prompt admission when the SDK ignores client message IDs, and binds newly created native sessions to orchestrator placeholder provider-thread rows instead of minting duplicate rows (Pi tests assert the same adoption pattern).
Reviewed by Cursor Bugbot for commit 727d4f6. Bugbot is set up for automated code reviews on this repo. Configure here.
Note
Add
piprovider with RPC adapter, text generation, and session event handlingpiprovider stack: stdio JSONL RPC transport (PiRpc.ts), orchestration adapter (PiAdapterV2.ts), provider driver (PiDriver.ts), status/health checks with minimum version0.80.5(PiProvider.ts), text generation (PiTextGeneration.ts), command/skill translation (PiCommands.ts), thinking capabilities (piThinkingCapabilities.ts), andPiSettingsschema (settings.ts).ProviderSessionManagernow detects session-scoped runtime request events (noproviderTurnId/runId) and ingests them throughProviderEventIngestorV2instead of publishing to subscribers. When the provider reportsstatus=stopped, it gracefully drains subscribers then releases the session withmanual_shutdown.OpenCodeAdapterV2.ensureThreadnow only resumes when an existing provider thread has anativeThreadRef; placeholder rows without one triggersession.createand bind the new native session to the handed-over row.stickyOptionsByModelByProvider/modelOptionMemoryAtom) and runtime mode filtering based onsupportedRuntimeModesdeclared by the provider.ProviderSessionManagerevent pump routes session-scoped runtime request events toProviderEventIngestorV2.ingestNormalizedinstead of subscriber queues; subscriber drain on provider-stop changes release timing.OpenCodeAdapterV2.ensureThreadresume condition changed from any definedexistingProviderThreadto requiringnativeThreadRef.Macroscope summarized 727d4f6.