@vaclav-synacek/pi-coding-agent-termux 0.45.7 → 0.46.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (106) hide show
  1. package/CHANGELOG.md +30 -0
  2. package/README.md +272 -1323
  3. package/dist/cli.d.ts.map +1 -1
  4. package/dist/cli.js +1 -0
  5. package/dist/cli.js.map +1 -1
  6. package/dist/config.d.ts +2 -0
  7. package/dist/config.d.ts.map +1 -1
  8. package/dist/config.js +2 -0
  9. package/dist/config.js.map +1 -1
  10. package/dist/core/agent-session.d.ts.map +1 -1
  11. package/dist/core/agent-session.js +2 -2
  12. package/dist/core/agent-session.js.map +1 -1
  13. package/dist/core/compaction/compaction.d.ts.map +1 -1
  14. package/dist/core/compaction/compaction.js +6 -5
  15. package/dist/core/compaction/compaction.js.map +1 -1
  16. package/dist/core/keybindings.d.ts +1 -5
  17. package/dist/core/keybindings.d.ts.map +1 -1
  18. package/dist/core/keybindings.js +4 -12
  19. package/dist/core/keybindings.js.map +1 -1
  20. package/dist/core/model-resolver.d.ts.map +1 -1
  21. package/dist/core/model-resolver.js +1 -0
  22. package/dist/core/model-resolver.js.map +1 -1
  23. package/dist/core/tools/edit-diff.d.ts +30 -0
  24. package/dist/core/tools/edit-diff.d.ts.map +1 -1
  25. package/dist/core/tools/edit-diff.js +82 -10
  26. package/dist/core/tools/edit-diff.js.map +1 -1
  27. package/dist/core/tools/edit.d.ts.map +1 -1
  28. package/dist/core/tools/edit.js +16 -13
  29. package/dist/core/tools/edit.js.map +1 -1
  30. package/dist/index.d.ts +1 -0
  31. package/dist/index.d.ts.map +1 -1
  32. package/dist/index.js +2 -0
  33. package/dist/index.js.map +1 -1
  34. package/dist/main.d.ts.map +1 -1
  35. package/dist/main.js +38 -9
  36. package/dist/main.js.map +1 -1
  37. package/dist/modes/interactive/components/bash-execution.d.ts.map +1 -1
  38. package/dist/modes/interactive/components/bash-execution.js +4 -3
  39. package/dist/modes/interactive/components/bash-execution.js.map +1 -1
  40. package/dist/modes/interactive/components/bordered-loader.d.ts.map +1 -1
  41. package/dist/modes/interactive/components/bordered-loader.js +2 -1
  42. package/dist/modes/interactive/components/bordered-loader.js.map +1 -1
  43. package/dist/modes/interactive/components/branch-summary-message.d.ts.map +1 -1
  44. package/dist/modes/interactive/components/branch-summary-message.js +4 -1
  45. package/dist/modes/interactive/components/branch-summary-message.js.map +1 -1
  46. package/dist/modes/interactive/components/compaction-summary-message.d.ts.map +1 -1
  47. package/dist/modes/interactive/components/compaction-summary-message.js +4 -1
  48. package/dist/modes/interactive/components/compaction-summary-message.js.map +1 -1
  49. package/dist/modes/interactive/components/custom-editor.d.ts.map +1 -1
  50. package/dist/modes/interactive/components/custom-editor.js +3 -3
  51. package/dist/modes/interactive/components/custom-editor.js.map +1 -1
  52. package/dist/modes/interactive/components/extension-editor.d.ts +3 -1
  53. package/dist/modes/interactive/components/extension-editor.d.ts.map +1 -1
  54. package/dist/modes/interactive/components/extension-editor.js +14 -8
  55. package/dist/modes/interactive/components/extension-editor.js.map +1 -1
  56. package/dist/modes/interactive/components/extension-input.d.ts.map +1 -1
  57. package/dist/modes/interactive/components/extension-input.js +2 -1
  58. package/dist/modes/interactive/components/extension-input.js.map +1 -1
  59. package/dist/modes/interactive/components/extension-selector.d.ts.map +1 -1
  60. package/dist/modes/interactive/components/extension-selector.js +6 -1
  61. package/dist/modes/interactive/components/extension-selector.js.map +1 -1
  62. package/dist/modes/interactive/components/index.d.ts +1 -0
  63. package/dist/modes/interactive/components/index.d.ts.map +1 -1
  64. package/dist/modes/interactive/components/index.js +1 -0
  65. package/dist/modes/interactive/components/index.js.map +1 -1
  66. package/dist/modes/interactive/components/keybinding-hints.d.ts +41 -0
  67. package/dist/modes/interactive/components/keybinding-hints.d.ts.map +1 -0
  68. package/dist/modes/interactive/components/keybinding-hints.js +61 -0
  69. package/dist/modes/interactive/components/keybinding-hints.js.map +1 -0
  70. package/dist/modes/interactive/components/login-dialog.d.ts.map +1 -1
  71. package/dist/modes/interactive/components/login-dialog.js +4 -3
  72. package/dist/modes/interactive/components/login-dialog.js.map +1 -1
  73. package/dist/modes/interactive/components/session-selector-search.d.ts +21 -0
  74. package/dist/modes/interactive/components/session-selector-search.d.ts.map +1 -0
  75. package/dist/modes/interactive/components/session-selector-search.js +146 -0
  76. package/dist/modes/interactive/components/session-selector-search.js.map +1 -0
  77. package/dist/modes/interactive/components/session-selector.d.ts +7 -1
  78. package/dist/modes/interactive/components/session-selector.d.ts.map +1 -1
  79. package/dist/modes/interactive/components/session-selector.js +35 -8
  80. package/dist/modes/interactive/components/session-selector.js.map +1 -1
  81. package/dist/modes/interactive/components/tool-execution.d.ts.map +1 -1
  82. package/dist/modes/interactive/components/tool-execution.js +14 -8
  83. package/dist/modes/interactive/components/tool-execution.js.map +1 -1
  84. package/dist/modes/interactive/components/tree-selector.d.ts.map +1 -1
  85. package/dist/modes/interactive/components/tree-selector.js +5 -2
  86. package/dist/modes/interactive/components/tree-selector.js.map +1 -1
  87. package/dist/modes/interactive/interactive-mode.d.ts +4 -4
  88. package/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
  89. package/dist/modes/interactive/interactive-mode.js +58 -95
  90. package/dist/modes/interactive/interactive-mode.js.map +1 -1
  91. package/dist/utils/image-convert.d.ts.map +1 -1
  92. package/dist/utils/image-convert.js +12 -14
  93. package/dist/utils/image-convert.js.map +1 -1
  94. package/dist/utils/image-resize.d.ts +2 -2
  95. package/dist/utils/image-resize.d.ts.map +1 -1
  96. package/dist/utils/image-resize.js +102 -122
  97. package/dist/utils/image-resize.js.map +1 -1
  98. package/examples/extensions/plan-mode/README.md +1 -1
  99. package/examples/extensions/plan-mode/index.ts +2 -2
  100. package/examples/extensions/with-deps/package-lock.json +2 -2
  101. package/examples/extensions/with-deps/package.json +1 -1
  102. package/package.json +5 -5
  103. package/dist/utils/vips.d.ts +0 -11
  104. package/dist/utils/vips.d.ts.map +0 -1
  105. package/dist/utils/vips.js +0 -35
  106. package/dist/utils/vips.js.map +0 -1
package/README.md CHANGED
@@ -1,1392 +1,341 @@
1
- <p align="center">
2
- <a href="https://shittycodingagent.ai">
3
- <img src="https://shittycodingagent.ai/logo.svg" alt="pi logo" width="128">
4
- </a>
5
- </p>
6
- <p align="center">
7
- <a href="https://discord.com/invite/nKXTsAcmbT"><img alt="Discord" src="https://img.shields.io/badge/discord-community-5865F2?style=flat-square&logo=discord&logoColor=white" /></a>
8
- <a href="https://www.npmjs.com/package/@mariozechner/pi-coding-agent"><img alt="npm" src="https://img.shields.io/npm/v/@mariozechner/pi-coding-agent?style=flat-square" /></a>
9
- <a href="https://github.com/badlogic/pi-mono/actions/workflows/ci.yml"><img alt="Build status" src="https://img.shields.io/github/actions/workflow/status/badlogic/pi-mono/ci.yml?style=flat-square&branch=main" /></a>
10
- </p>
11
-
12
- A terminal-based coding agent with multi-model support, mid-session model switching, and a simple CLI for headless coding tasks.
13
-
14
- Works on Linux, macOS, and Windows (requires bash; see [Windows Setup](#windows-setup)).
15
-
16
- ## Table of Contents
17
-
18
- - [Getting Started](#getting-started)
19
- - [Installation](#installation)
20
- - [Windows Setup](#windows-setup)
21
- - [Terminal Setup](#terminal-setup)
22
- - [API Keys & OAuth](#api-keys--oauth)
23
- - [Quick Start](#quick-start)
24
- - [Usage](#usage)
25
- - [Slash Commands](#slash-commands)
26
- - [Editor Features](#editor-features)
27
- - [Keyboard Shortcuts](#keyboard-shortcuts)
28
- - [Custom Keybindings](#custom-keybindings)
29
- - [Bash Mode](#bash-mode)
30
- - [Image Support](#image-support)
31
- - [Sessions](#sessions)
32
- - [Session Management](#session-management)
33
- - [Context Compaction](#context-compaction)
34
- - [Branching](#branching)
35
- - [Configuration](#configuration)
36
- - [Project Context Files](#project-context-files)
37
- - [Custom System Prompt](#custom-system-prompt)
38
- - [Custom Models and Providers](#custom-models-and-providers)
39
- - [Settings File](#settings-file)
40
- - [Customization](#customization)
41
- - [Themes](#themes)
42
- - [Prompt Templates](#prompt-templates)
43
- - [Skills](#skills)
44
- - [Extensions](#extensions)
45
- - [CLI Reference](#cli-reference)
46
- - [Tools](#tools)
47
- - [Programmatic Usage](#programmatic-usage)
48
- - [SDK](#sdk)
49
- - [RPC Mode](#rpc-mode)
50
- - [HTML Export](#html-export)
51
- - [Philosophy](#philosophy)
52
- - [Development](#development)
53
- - [License](#license)
54
-
55
- ---
56
-
57
- ## Getting Started
58
-
59
- ### Installation
60
-
61
- **npm (recommended):**
1
+ # pi-coding-agent-termux
62
2
 
63
- ```bash
64
- npm install -g @mariozechner/pi-coding-agent
65
- ```
3
+ Termux port of [pi-coding-agent](https://github.com/badlogic/pi-mono) - a terminal-based coding agent with multi-model support.
66
4
 
67
- **Standalone binary:**
5
+ **For user documentation, features, and usage instructions, please see the [upstream repository](https://github.com/badlogic/pi-mono/tree/main/packages/coding-agent).**
68
6
 
69
- Download from [GitHub Releases](https://github.com/badlogic/pi-mono/releases):
7
+ This repository maintains a Termux-compatible fork of pi-coding-agent. The port removes problematic dependencies and provides minimal Termux-specific replacements to enable running pi on Android devices via Termux.
70
8
 
71
- | Platform | Archive |
72
- |----------|---------|
73
- | macOS Apple Silicon | `pi-darwin-arm64.tar.gz` |
74
- | macOS Intel | `pi-darwin-x64.tar.gz` |
75
- | Linux x64 | `pi-linux-x64.tar.gz` |
76
- | Linux ARM64 | `pi-linux-arm64.tar.gz` |
77
- | Windows x64 | `pi-windows-x64.zip` |
9
+ ## Installation on Termux
78
10
 
79
11
  ```bash
80
- # macOS/Linux
81
- tar -xzf pi-darwin-arm64.tar.gz
82
- ./pi
83
-
84
- # Windows
85
- unzip pi-windows-x64.zip
86
- pi.exe
12
+ npm install -g @vaclav-synacek/pi-coding-agent-termux
87
13
  ```
88
14
 
89
- **macOS note:** The binary is unsigned. If blocked, run: `xattr -c ./pi`
90
-
91
- **Build from source** (requires [Bun](https://bun.sh) 1.0+):
15
+ Or build from source (on a development machine):
92
16
 
93
17
  ```bash
94
- git clone https://github.com/badlogic/pi-mono.git
95
- cd pi-mono && npm install && npm run build
96
- cd packages/coding-agent && npm run build:binary
97
- ./dist/pi
98
- ```
99
-
100
- ### Windows Setup
101
-
102
- Pi requires a bash shell on Windows. Checked locations (in order):
103
-
104
- 1. Custom path from `~/.pi/agent/settings.json`
105
- 2. Git Bash (`C:\Program Files\Git\bin\bash.exe`)
106
- 3. `bash.exe` on PATH (Cygwin, MSYS2, WSL)
107
-
108
- For most users, [Git for Windows](https://git-scm.com/download/win) is sufficient.
109
-
110
- **Custom shell path:**
111
-
112
- ```json
113
- // ~/.pi/agent/settings.json
114
- {
115
- "shellPath": "C:\\cygwin64\\bin\\bash.exe"
116
- }
117
- ```
118
-
119
- ### Terminal Setup
120
-
121
- Pi uses the [Kitty keyboard protocol](https://sw.kovidgoyal.net/kitty/keyboard-protocol/) for reliable modifier key detection. Most modern terminals support this protocol, but some require configuration.
122
-
123
- **Kitty, iTerm2:** Work out of the box.
124
-
125
- **Ghostty:** Add to your Ghostty config (`~/.config/ghostty/config`):
126
-
127
- ```
128
- keybind = alt+backspace=text:\x1b\x7f
129
- keybind = shift+enter=text:\n
130
- ```
131
-
132
- **wezterm:** Create `~/.wezterm.lua`:
133
-
134
- ```lua
135
- local wezterm = require 'wezterm'
136
- local config = wezterm.config_builder()
137
- config.enable_kitty_keyboard = true
138
- return config
18
+ git clone https://github.com/VaclavSynacek/pi-coding-agent-termux.git
19
+ cd pi-coding-agent-termux
20
+ npm install
21
+ npm run build
22
+ cd packages/coding-agent
23
+ npm pack
24
+ # Transfer the .tgz file to Termux and install it
139
25
  ```
140
26
 
141
- **Windows Terminal:** Does not support the Kitty keyboard protocol. Shift+Enter cannot be distinguished from Enter. Use Ctrl+Enter for multi-line input instead. All other keybindings work correctly.
142
-
143
- ### API Keys & OAuth
144
-
145
- **Option 1: Auth file** (recommended)
146
-
147
- Add API keys to `~/.pi/agent/auth.json`:
148
-
149
- ```json
150
- {
151
- "anthropic": { "type": "api_key", "key": "sk-ant-..." },
152
- "openai": { "type": "api_key", "key": "sk-..." },
153
- "google": { "type": "api_key", "key": "..." }
154
- }
155
- ```
156
-
157
- **Option 2: Environment variables**
158
-
159
- | Provider | Auth Key | Environment Variable |
160
- |----------|--------------|---------------------|
161
- | Anthropic | `anthropic` | `ANTHROPIC_API_KEY` |
162
- | OpenAI | `openai` | `OPENAI_API_KEY` |
163
- | Google | `google` | `GEMINI_API_KEY` |
164
- | Mistral | `mistral` | `MISTRAL_API_KEY` |
165
- | Groq | `groq` | `GROQ_API_KEY` |
166
- | Cerebras | `cerebras` | `CEREBRAS_API_KEY` |
167
- | xAI | `xai` | `XAI_API_KEY` |
168
- | OpenRouter | `openrouter` | `OPENROUTER_API_KEY` |
169
- | Vercel AI Gateway | `vercel-ai-gateway` | `AI_GATEWAY_API_KEY` |
170
- | ZAI | `zai` | `ZAI_API_KEY` |
171
- | MiniMax | `minimax` | `MINIMAX_API_KEY` |
172
-
173
- Auth file keys take priority over environment variables.
174
-
175
- **OAuth Providers:**
176
-
177
- Use `/login` to authenticate with subscription-based or free-tier providers:
178
-
179
- | Provider | Models | Cost |
180
- |----------|--------|------|
181
- | Anthropic (Claude Pro/Max) | Claude models via your subscription | Subscription |
182
- | GitHub Copilot | GPT-4o, Claude, Gemini via Copilot subscription | Subscription |
183
- | Google Gemini CLI | Gemini 2.0/2.5 models | Free (Google account) |
184
- | Google Antigravity | Gemini 3, Claude, GPT-OSS | Free (Google account) |
185
- | OpenAI Codex (ChatGPT Plus/Pro) | Codex models via ChatGPT subscription | Subscription |
186
-
27
+ On Termux:
187
28
  ```bash
188
- pi
189
- /login # Select provider, authorize in browser
29
+ npm install -g /path/to/vaclav-synacek-pi-coding-agent-termux-0.45.7.tgz
190
30
  ```
191
31
 
192
- **Note:** `/login` replaces any existing API key for that provider with OAuth credentials in `auth.json`.
193
-
194
- **GitHub Copilot notes:**
195
- - Press Enter for github.com, or enter your GitHub Enterprise Server domain
196
- - If you get "model not supported" error, enable it in VS Code: Copilot Chat → model selector → select model → "Enable"
197
-
198
- **Google providers notes:**
199
- - Gemini CLI uses the production Cloud Code Assist endpoint (standard Gemini models)
200
- - Antigravity uses a sandbox endpoint with access to Gemini 3, Claude (sonnet/opus thinking), and GPT-OSS models
201
- - Both are free with any Google account, subject to rate limits
202
- - Paid Cloud Code Assist subscriptions: set `GOOGLE_CLOUD_PROJECT` or `GOOGLE_CLOUD_PROJECT_ID` env var to your project ID
203
-
204
- **OpenAI Codex notes:**
205
- - Requires ChatGPT Plus/Pro OAuth (`/login openai-codex`)
206
- - Prompt cache stored under `~/.pi/agent/cache/openai-codex/`
207
- - Intended for personal use with your own subscription; not for resale or multi-user services. For production, use the OpenAI Platform API.
208
-
209
- Credentials stored in `~/.pi/agent/auth.json`. Use `/logout` to clear.
210
-
211
- **Troubleshooting (OAuth):**
212
- - **Port 1455 in use:** Close the conflicting process or paste the auth code/URL when prompted.
213
- - **Token expired / refresh failed:** Run `/login` again for the provider to refresh credentials.
214
- - **Usage limits (429):** Wait for the reset window; pi will surface a friendly message with the approximate retry time.
32
+ **Note**: Building on Termux is not supported because the build tool (`tsgo`) doesn't have ARM64 binaries. Build on a regular machine and transfer the package, or install directly from npm.
215
33
 
216
- **Amazon Bedrock:**
217
-
218
- Amazon Bedrock supports multiple authentication methods:
34
+ For clipboard support, install Termux:API:
219
35
 
220
36
  ```bash
221
- # Option 1: AWS Profile (from ~/.aws/credentials)
222
- export AWS_PROFILE=your-profile-name
223
-
224
- # Option 2: IAM Access Keys
225
- export AWS_ACCESS_KEY_ID=AKIA...
226
- export AWS_SECRET_ACCESS_KEY=...
227
-
228
- # Option 3: Bedrock API Key (bearer token)
229
- export AWS_BEARER_TOKEN_BEDROCK=...
230
-
231
- # Optional: Set region (defaults to us-east-1)
232
- export AWS_REGION=us-east-1
233
-
234
- pi --provider amazon-bedrock --model global.anthropic.claude-sonnet-4-5-20250929-v1:0
37
+ pkg install termux-api
235
38
  ```
236
39
 
237
- See [Supported foundation models in Amazon Bedrock](https://docs.aws.amazon.com/bedrock/latest/userguide/models-supported.html).
40
+ ## Functional Changes in this Port
238
41
 
239
- ### Quick Start
42
+ This port modifies the upstream pi-coding-agent to work on Termux by:
240
43
 
241
- ```bash
242
- export ANTHROPIC_API_KEY=sk-ant-...
243
- pi
244
- ```
44
+ ### 1. Clipboard Integration
45
+ - **Changed**: `@mariozechner/clipboard` made optional (native bindings incompatible with Termux)
46
+ - **Added**: Termux clipboard support via `termux-clipboard-set` and `termux-clipboard-get` commands
47
+ - **Behavior**: Text clipboard works via Termux:API; image clipboard operations are disabled on Termux
48
+ - **Files modified**:
49
+ - `packages/coding-agent/src/utils/clipboard.ts`
50
+ - `packages/coding-agent/src/utils/clipboard-image.ts`
51
+ - `packages/coding-agent/package.json` (clipboard moved to optionalDependencies)
52
+
53
+ ### 2. Image Processing
54
+ - **Changed**: Uses `wasm-vips` for image processing
55
+ - **Note**: Upstream v0.45.7+ migrated from `photon-node` to `wasm-vips` which is WebAssembly-based
56
+ - **Behavior**: Image resizing and conversion work correctly (wasm-vips is platform-independent)
57
+ - **Files modified**: None required - wasm-vips works on all platforms including Termux
58
+
59
+ ### 3. Update Notification
60
+ - **Changed**: Version check and update notification system
61
+ - **Behavior**: Checks for updates against `@vaclav-synacek/pi-coding-agent-termux` on npm (instead of upstream package)
62
+ - **Display**: Shows correct command: `npm install -g @vaclav-synacek/pi-coding-agent-termux`
63
+ - **Files modified**:
64
+ - `packages/coding-agent/src/modes/interactive/interactive-mode.ts` (npm registry URL and install command)
65
+
66
+ ### 4. Optional Dependencies
67
+ - **Changed**: `canvas` moved to optionalDependencies in `packages/ai/package.json`
68
+ - **Reason**: Canvas cannot build on Termux (requires pixman-1), but is only used for ai tests
69
+ - **Behavior**: npm install succeeds on Termux even if canvas build fails
70
+ - **Files modified**: `packages/ai/package.json`
71
+
72
+ ### 5. TypeScript Target
73
+ - **Changed**: `tsconfig.base.json` target set to ES2024
74
+ - **Reason**: Support for regex `v` flag (required by some dependencies)
75
+ - **Files modified**: `tsconfig.base.json`
76
+
77
+ ## Repository Structure & Maintenance
78
+
79
+ This repository follows a structured branching strategy to track upstream releases while maintaining Termux-specific patches:
80
+
81
+ ### Branches
82
+
83
+ - **`master`** - The main Termux port branch
84
+ - Contains Termux-specific modifications applied on top of upstream
85
+ - Rebased onto new upstream versions when they are released
86
+ - Force-pushed after each rebase (history is rewritten)
87
+
88
+ - **`upstream`** - Clean upstream tracking branch
89
+ - Mirrors `https://github.com/badlogic/pi-mono.git` main branch
90
+ - Used as the base for rebasing master
91
+ - Never contains Termux-specific changes
92
+ - Helps maintain transparency about what's changed in the port
93
+
94
+ ### Tags
95
+
96
+ Tags follow the naming convention: `v{UPSTREAM_VERSION}-{PORT_REVISION}`
97
+
98
+ Examples:
99
+ - `v0.45.7-0` - First Termux port of upstream v0.45.7
100
+ - `v0.45.7-1` - Second Termux port of upstream v0.45.7 (port bugfix)
101
+ - `v0.46.0-0` - First Termux port of upstream v0.46.0
102
+
103
+ **Tags are immutable** - once published to npm, a tag is never changed or deleted. This preserves the complete version history.
104
+
105
+ ### Remotes
106
+
107
+ - `origin` - This repository (`VaclavSynacek/pi-coding-agent-termux`)
108
+ - `upstream` - Upstream repository (`badlogic/pi-mono`)
109
+
110
+ ## Maintenance Workflow
111
+
112
+ ### When a New Upstream Version is Released
113
+
114
+ Example: Upstream releases `v0.46.0`
115
+
116
+ 1. **Update upstream branch**
117
+ ```bash
118
+ git checkout upstream
119
+ git fetch upstream
120
+ git merge upstream/main # or git reset --hard upstream/main
121
+ git push origin upstream
122
+ ```
123
+
124
+ 2. **Rebase master onto new upstream version**
125
+ ```bash
126
+ git checkout master
127
+ git rebase v0.46.0 # rebase onto the upstream tag
128
+ ```
129
+
130
+ 3. **Resolve conflicts**
131
+ - Fix any rebase conflicts in Termux-specific patches
132
+ - Pay special attention to files listed in "Functional Changes" section above
133
+ - Ensure patches still apply cleanly and make sense
134
+
135
+ 4. **Test thoroughly**
136
+ - Build the project: `npm install && npm run build`
137
+ - Test on actual Termux device
138
+ - Verify clipboard operations (with Termux:API installed)
139
+ - Test that image operations degrade gracefully
140
+ - Check that all core features work
141
+
142
+ 5. **Update package.json version**
143
+ ```bash
144
+ cd packages/coding-agent
145
+ # Update version to match upstream (e.g., "0.46.0")
146
+ ```
147
+
148
+ 6. **Create immutable release tag**
149
+ ```bash
150
+ git tag -a v0.46.0-0 -m "Termux port of upstream v0.46.0"
151
+ git push origin v0.46.0-0
152
+ ```
153
+
154
+ 7. **Publish to npm**
155
+ ```bash
156
+ cd packages/coding-agent
157
+ npm publish
158
+ ```
159
+
160
+ 8. **Push rebased master**
161
+ ```bash
162
+ git push origin master --force-with-lease
163
+ ```
245
164
 
246
- Then chat:
165
+ ### When Port Needs a Bugfix (Without Upstream Change)
166
+
167
+ Example: Fix a bug in the Termux port of v0.46.0
247
168
 
248
- ```
249
- You: Create a simple Express server in src/server.ts
250
- ```
251
-
252
- The agent reads, writes, and edits files, and executes commands via bash.
253
-
254
- ---
255
-
256
- ## Usage
257
-
258
- ### Slash Commands
259
-
260
- | Command | Description |
261
- |---------|-------------|
262
- | `/settings` | Open settings menu (thinking, theme, message delivery modes, toggles) |
263
- | `/model` | Switch models mid-session. Use `/model <search>` or `provider/model` to prefilter/disambiguate. |
264
- | `/scoped-models` | Enable/disable models for Ctrl+P cycling |
265
- | `/export [file]` | Export session to self-contained HTML |
266
- | `/share` | Upload session as secret GitHub gist, get shareable URL (requires `gh` CLI) |
267
- | `/session` | Show session info: path, message counts, token usage, cost |
268
- | `/name <name>` | Set session display name (shown in session selector) |
269
- | `/hotkeys` | Show all keyboard shortcuts |
270
- | `/changelog` | Display full version history |
271
- | `/tree` | Navigate session tree in-place (search, filter, label entries) |
272
- | `/fork` | Create new conversation fork from a previous message |
273
- | `/resume` | Switch to a different session (interactive selector) |
274
- | `/login` | OAuth login for subscription-based models |
275
- | `/logout` | Clear OAuth tokens |
276
- | `/new` | Start a new session |
277
- | `/copy` | Copy last agent message to clipboard |
278
- | `/compact [instructions]` | Manually compact conversation context |
279
-
280
- ### Editor Features
281
-
282
- **File reference (`@`):** Type `@` to fuzzy-search project files. Respects `.gitignore`.
283
-
284
- **Path completion (Tab):** Complete relative paths, `../`, `~/`, etc.
285
-
286
- **Drag & drop:** Drag files from your file manager into the terminal.
287
-
288
- **Multi-line paste:** Pasted content is collapsed to `[paste #N <lines> lines]` but sent in full.
289
-
290
- **Message queuing:** Submit messages while the agent is working:
291
- - **Enter** queues a *steering* message, delivered after current tool execution (interrupts remaining tools)
292
- - **Alt+Enter** queues a *follow-up* message, delivered only after the agent finishes all work
293
-
294
- Both modes are configurable via `/settings`: "one-at-a-time" delivers messages one by one waiting for responses, "all" delivers all queued messages at once. Press Escape to abort and restore queued messages to editor.
295
-
296
- ### Keyboard Shortcuts
297
-
298
- **Navigation:**
299
-
300
- | Key | Action |
301
- |-----|--------|
302
- | Arrow keys | Move cursor / browse history (Up when empty) |
303
- | Option+Left/Right | Move by word |
304
- | Ctrl+A / Home / Cmd+Left | Start of line |
305
- | Ctrl+E / End / Cmd+Right | End of line |
306
-
307
- **Editing:**
308
-
309
- | Key | Action |
310
- |-----|--------|
311
- | Enter | Send message |
312
- | Shift+Enter | New line (Ctrl+Enter on Windows Terminal) |
313
- | Ctrl+W / Option+Backspace | Delete word backwards |
314
- | Ctrl+U | Delete to start of line |
315
- | Ctrl+K | Delete to end of line |
316
-
317
- **Other:**
318
-
319
- | Key | Action |
320
- |-----|--------|
321
- | Tab | Path completion / accept autocomplete |
322
- | Escape | Cancel autocomplete / abort streaming |
323
- | Ctrl+C | Clear editor (first) / exit (second) |
324
- | Ctrl+D | Exit (when editor is empty) |
325
- | Ctrl+Z | Suspend to background (use `fg` in shell to resume) |
326
- | Shift+Tab | Cycle thinking level |
327
- | Ctrl+P / Shift+Ctrl+P | Cycle models forward/backward (scoped by `--models`) |
328
- | Ctrl+L | Open model selector |
329
- | Ctrl+O | Toggle tool output expansion |
330
- | Ctrl+T | Toggle thinking block visibility |
331
- | Ctrl+G | Edit message in external editor (`$VISUAL` or `$EDITOR`) |
332
- | Ctrl+V | Paste image from clipboard |
333
- | Alt+Up | Restore queued messages to editor |
334
-
335
- ### Custom Keybindings
336
-
337
- All keyboard shortcuts can be customized via `~/.pi/agent/keybindings.json`. Each action can be bound to one or more keys.
338
-
339
- **Key format:** `modifier+key` where modifiers are `ctrl`, `shift`, `alt` and keys are:
340
-
341
- - Letters: `a-z`
342
- - Numbers: `0-9`
343
- - Special keys: `escape`, `tab`, `enter`, `space`, `backspace`, `delete`, `home`, `end`, `up`, `down`, `left`, `right`
344
- - Symbol keys: `` ` ``, `-`, `=`, `[`, `]`, `\`, `;`, `'`, `,`, `.`, `/`, `!`, `@`, `#`, `$`, `%`, `^`, `&`, `*`, `(`, `)`, `_`, `+`, `|`, `~`, `{`, `}`, `:`, `<`, `>`, `?`
345
-
346
- **Configurable actions:**
347
-
348
- | Action | Default | Description |
349
- |--------|---------|-------------|
350
- | `cursorUp` | `up` | Move cursor up |
351
- | `cursorDown` | `down` | Move cursor down |
352
- | `cursorLeft` | `left` | Move cursor left |
353
- | `cursorRight` | `right` | Move cursor right |
354
- | `cursorWordLeft` | `alt+left`, `ctrl+left` | Move cursor word left |
355
- | `cursorWordRight` | `alt+right`, `ctrl+right` | Move cursor word right |
356
- | `cursorLineStart` | `home`, `ctrl+a` | Move to line start |
357
- | `cursorLineEnd` | `end`, `ctrl+e` | Move to line end |
358
- | `deleteCharBackward` | `backspace` | Delete char backward |
359
- | `deleteCharForward` | `delete` | Delete char forward |
360
- | `deleteWordBackward` | `ctrl+w`, `alt+backspace` | Delete word backward |
361
- | `deleteToLineStart` | `ctrl+u` | Delete to line start |
362
- | `deleteToLineEnd` | `ctrl+k` | Delete to line end |
363
- | `newLine` | `shift+enter` | Insert new line |
364
- | `submit` | `enter` | Submit input |
365
- | `tab` | `tab` | Tab/autocomplete |
366
- | `interrupt` | `escape` | Interrupt operation |
367
- | `clear` | `ctrl+c` | Clear editor |
368
- | `exit` | `ctrl+d` | Exit (when empty) |
369
- | `suspend` | `ctrl+z` | Suspend process |
370
- | `cycleThinkingLevel` | `shift+tab` | Cycle thinking level |
371
- | `cycleModelForward` | `ctrl+p` | Next model |
372
- | `cycleModelBackward` | `shift+ctrl+p` | Previous model |
373
- | `selectModel` | `ctrl+l` | Open model selector |
374
- | `expandTools` | `ctrl+o` | Expand tool output |
375
- | `toggleThinking` | `ctrl+t` | Toggle thinking |
376
- | `externalEditor` | `ctrl+g` | Open external editor |
377
- | `followUp` | `alt+enter` | Queue follow-up message |
378
- | `dequeue` | `alt+up` | Restore queued messages to editor |
379
- | `selectUp` | `up` | Move selection up in lists (session picker, model selector) |
380
- | `selectDown` | `down` | Move selection down in lists |
381
- | `selectConfirm` | `enter` | Confirm selection |
382
- | `selectCancel` | `escape`, `ctrl+c` | Cancel selection |
383
-
384
- **Example (Emacs-style):**
385
-
386
- ```json
387
- {
388
- "cursorUp": ["up", "ctrl+p"],
389
- "cursorDown": ["down", "ctrl+n"],
390
- "cursorLeft": ["left", "ctrl+b"],
391
- "cursorRight": ["right", "ctrl+f"],
392
- "cursorWordLeft": ["alt+left", "alt+b"],
393
- "cursorWordRight": ["alt+right", "alt+f"],
394
- "deleteCharForward": ["delete", "ctrl+d"],
395
- "deleteCharBackward": ["backspace", "ctrl+h"],
396
- "newLine": ["shift+enter", "ctrl+j"]
397
- }
398
- ```
399
-
400
- **Example (Vim-style):**
401
-
402
- ```json
403
- {
404
- "cursorUp": ["up", "alt+k"],
405
- "cursorDown": ["down", "alt+j"],
406
- "cursorLeft": ["left", "alt+h"],
407
- "cursorRight": ["right", "alt+l"],
408
- "cursorWordLeft": ["alt+left", "alt+b"],
409
- "cursorWordRight": ["alt+right", "alt+w"],
410
- "deleteCharBackward": ["backspace", "ctrl+h"],
411
- "deleteWordBackward": ["ctrl+w", "alt+backspace"]
412
- }
413
- ```
169
+ 1. **Make fixes on master branch**
170
+ ```bash
171
+ git checkout master
172
+ # Make your fixes
173
+ git commit -m "fix: describe the port-specific fix"
174
+ ```
414
175
 
415
- **Example (symbol keys):**
416
-
417
- ```json
418
- {
419
- "submit": ["enter", "ctrl+j"],
420
- "newLine": ["shift+enter", "ctrl+;"],
421
- "toggleThinking": "ctrl+/",
422
- "cycleModelForward": "ctrl+.",
423
- "cycleModelBackward": "ctrl+,",
424
- "interrupt": ["escape", "ctrl+`"]
425
- }
426
- ```
427
-
428
- > **Note:** Some `ctrl+symbol` combinations overlap with ASCII control characters due to terminal legacy behavior (e.g., `ctrl+[` is the same as Escape, `ctrl+M` is the same as Enter). These can still be used with `ctrl+shift+key` (e.g., `ctrl+shift+]`). See [Kitty keyboard protocol: legacy ctrl mapping of ASCII keys](https://sw.kovidgoyal.net/kitty/keyboard-protocol/#legacy-ctrl-mapping-of-ascii-keys) for all unsupported keys.
176
+ 2. **Update package.json version** (increment port revision)
177
+ ```bash
178
+ cd packages/coding-agent
179
+ # Version stays "0.46.0" (or use "0.46.0-termux.1" if needed)
180
+ ```
181
+
182
+ 3. **Create new port revision tag**
183
+ ```bash
184
+ git tag -a v0.46.0-1 -m "Termux port of upstream v0.46.0 (bugfix)"
185
+ git push origin v0.46.0-1
186
+ ```
187
+
188
+ 4. **Publish to npm**
189
+ ```bash
190
+ cd packages/coding-agent
191
+ npm publish
192
+ ```
429
193
 
430
- ### Bash Mode
194
+ 5. **Push master**
195
+ ```bash
196
+ git push origin master
197
+ ```
198
+
199
+ ### Initial Setup (Already Done)
431
200
 
432
- Prefix commands with `!` to execute them and add output to context:
201
+ This was the initial setup of this repository:
433
202
 
434
- ```
435
- !ls -la
436
- !git status
437
- !cat package.json | jq '.dependencies'
438
- ```
203
+ 1. Created new repository
204
+ 2. Added upstream remote: `git remote add upstream https://github.com/badlogic/pi-mono.git`
205
+ 3. Fetched upstream: `git fetch upstream --tags`
206
+ 4. Created `upstream` branch: `git checkout -b upstream upstream/main`
207
+ 5. Created `master` branch from upstream v0.45.7: `git checkout -b master v0.45.7`
208
+ 6. Applied Termux patches as focused commits
209
+ 7. Tagged first release: `v0.45.7-0`
210
+
211
+ ## Termux Port Commits
212
+
213
+ The Termux port consists of these focused commits (applied on top of upstream):
214
+
215
+ 1. **docs: Add comprehensive Termux port README** - Complete documentation and maintenance instructions
216
+ 2. **feat: Update TypeScript target to ES2024** - Enable modern JavaScript features
217
+ 3. **feat: Make @mariozechner/clipboard optional for Termux compatibility** - Optional require() for clipboard
218
+ 4. **feat: Add Termux clipboard support** - Integration with termux-clipboard-set/get
219
+ 5. **feat: Make @mariozechner/clipboard optional dependency** - Move to optionalDependencies in package.json
220
+ 6. **feat: Update version check to use Termux port package** - Point to @vaclav-synacek/pi-coding-agent-termux
221
+ 7. **feat: Update package.json for Termux port** - Package name and metadata
222
+ 8. **feat: Make canvas optional dependency in ai package** - Allow clean build on Termux
223
+ 9. **chore: Remove package-lock.json** - Platform-independent dependency resolution
224
+
225
+ ## Commit Strategy for Rebasing
226
+
227
+ To make rebasing easier, Termux-specific changes are organized as **minimal, focused commits**:
228
+
229
+ - One commit per logical change
230
+ - Clear commit messages explaining why the change is needed for Termux
231
+ - Avoid mixing unrelated changes
232
+ - Keep patches as small as possible while maintaining functionality
233
+
234
+ This approach ensures that when rebasing onto new upstream versions, conflicts are:
235
+ - Easier to understand and resolve
236
+ - Less likely to occur
237
+ - Clearly attributable to specific Termux requirements
238
+
239
+ ## Development Notes
439
240
 
440
- Output streams in real-time. Press Escape to cancel. Large outputs truncate at 2000 lines / 50KB.
241
+ ### Building (Development Machine Required)
242
+
243
+ **Important**: Building requires `tsgo` which doesn't have Android ARM64 binaries. Build on a regular development machine (Linux/macOS/Windows).
441
244
 
442
- The output becomes part of your next prompt, formatted as:
443
-
444
- ```
445
- Ran `ls -la`
446
-
447
- <output here>
448
- ```
449
-
450
- Run multiple commands before prompting; all outputs are included together.
451
-
452
- ### Image Support
453
-
454
- **Pasting images:** Press `Ctrl+V` to paste an image from your clipboard.
455
-
456
- > **Note:** On macOS, pressing Cmd+C on an image file in Finder copies the file path, not the image contents. Use Preview or another image viewer to copy the actual image, or drag the file onto the terminal instead.
457
-
458
- **Dragging images:** Drag image files onto the terminal to insert their path. On macOS, you can also drag the screenshot thumbnail (after Cmd+Shift+4) directly onto the terminal.
459
-
460
- **Attaching images:** Include image paths in your message:
461
-
462
- ```
463
- You: What's in this screenshot? /path/to/image.png
464
- ```
465
-
466
- Supported formats: `.jpg`, `.jpeg`, `.png`, `.gif`, `.webp`
467
-
468
- **Auto-resize:** Images larger than 2000x2000 pixels are automatically resized to fit within this limit for better compatibility with Anthropic models. The original dimensions are noted in the context so the model can map coordinates back if needed. Disable via `images.autoResize: false` in settings.
469
-
470
- **Inline rendering:** On terminals that support the Kitty graphics protocol (Kitty, Ghostty, WezTerm) or iTerm2 inline images, images in tool output are rendered inline. On unsupported terminals, a text placeholder is shown instead.
471
-
472
- Toggle inline images via `/settings` or set `terminal.showImages: false` in settings.
473
-
474
- ---
475
-
476
- ## Sessions
477
-
478
- Sessions are stored as JSONL files with a **tree structure**. Each entry has an `id` and `parentId`, enabling in-place branching: navigate to any previous point with `/tree`, continue from there, and switch between branches while preserving all history in a single file.
479
-
480
- See [docs/session.md](docs/session.md) for the file format and programmatic API.
481
-
482
- ### Session Management
483
-
484
- Sessions auto-save to `~/.pi/agent/sessions/` organized by working directory.
245
+ This is a monorepo. To build all packages:
485
246
 
486
247
  ```bash
487
- pi --continue # Continue most recent session
488
- pi -c # Short form
489
-
490
- pi --resume # Browse and select from past sessions (Tab to toggle Current Folder / All)
491
- pi -r # Short form
492
-
493
- pi --no-session # Ephemeral mode (don't save)
494
-
495
- pi --session /path/to/file.jsonl # Use specific session file
496
- pi --session a8ec1c2a # Resume by session ID (partial UUID)
497
- ```
498
-
499
- **Resuming by session ID:** The `--session` flag accepts a session UUID (or prefix). Session IDs are visible in filenames under `~/.pi/agent/sessions/<project>/` (e.g., `2025-12-13T17-47-46-817Z_a8ec1c2a-5a5f-4699-88cb-03e7d3cb9292.jsonl`). The UUID is the part after the underscore. You can also search by session ID in the `pi -r` picker.
500
-
501
- ### Context Compaction
502
-
503
- Long sessions can exhaust context windows. Compaction summarizes older messages while keeping recent ones.
504
-
505
- **Manual:** `/compact` or `/compact Focus on the API changes`
506
-
507
- **Automatic:** Enable via `/settings`. When enabled, triggers in two cases:
508
- - **Overflow recovery**: LLM returns context overflow error. Compacts and auto-retries.
509
- - **Threshold maintenance**: Context exceeds `contextWindow - reserveTokens` after a successful turn. Compacts without retry.
510
-
511
- When disabled, neither case triggers automatic compaction (use `/compact` manually if needed).
512
-
513
- **Configuration** (`~/.pi/agent/settings.json`):
514
-
515
- ```json
516
- {
517
- "compaction": {
518
- "enabled": true,
519
- "reserveTokens": 16384,
520
- "keepRecentTokens": 20000
521
- }
522
- }
523
- ```
524
-
525
- > **Note:** Compaction is lossy. The agent loses full conversation access afterward. Size tasks to avoid context limits when possible. For critical context, ask the agent to write a summary to a file, iterate on it until it covers everything, then start a new session with that file. The full session history is preserved in the JSONL file; use `/tree` to revisit any previous point.
526
-
527
- See [docs/compaction.md](docs/compaction.md) for how compaction works internally and how to customize it via extensions.
528
-
529
- ### Branching
530
-
531
- **In-place navigation (`/tree`):** Navigate the session tree without creating new files. Select any previous point, continue from there, and switch between branches while preserving all history.
532
-
533
- - Search by typing, page with ←/→
534
- - Filter modes (Ctrl+O): default → no-tools → user-only → labeled-only → all
535
- - Press `l` to label entries as bookmarks
536
- - When switching branches, you're prompted whether to generate a summary of the abandoned branch (messages up to the common ancestor)
537
-
538
- **Create new session (`/fork`):** Fork to a new session file:
539
-
540
- 1. Opens selector showing all your user messages
541
- 2. Select a message to fork from
542
- 3. Creates new session with history up to that point
543
- 4. Selected message placed in editor for modification
544
-
545
- ---
546
-
547
- ## Configuration
548
-
549
- ### Project Context Files
550
-
551
- Pi loads `AGENTS.md` (or `CLAUDE.md`) files at startup in this order:
552
-
553
- 1. **Global:** `~/.pi/agent/AGENTS.md`
554
- 2. **Parent directories:** Walking up from current directory
555
- 3. **Current directory:** `./AGENTS.md`
556
-
557
- Use these for:
558
- - Project instructions and guidelines
559
- - Common commands and workflows
560
- - Architecture documentation
561
- - Coding conventions
562
- - Testing instructions
563
-
564
- ```markdown
565
- # Common Commands
566
- - npm run build: Build the project
567
- - npm test: Run tests
568
-
569
- # Code Style
570
- - Use TypeScript strict mode
571
- - Prefer async/await over promises
572
- ```
573
-
574
- ### Custom System Prompt
575
-
576
- Replace the default system prompt entirely by creating a `SYSTEM.md` file:
577
-
578
- 1. **Project-local:** `.pi/SYSTEM.md` (takes precedence)
579
- 2. **Global:** `~/.pi/agent/SYSTEM.md` (fallback)
580
-
581
- This is useful when using pi as different types of agents across repos (coding assistant, personal assistant, domain-specific agent, etc.).
582
-
583
- ```markdown
584
- You are a technical writing assistant. Help users write clear documentation.
585
-
586
- Focus on:
587
- - Concise explanations
588
- - Code examples
589
- - Proper formatting
590
- ```
591
-
592
- The `--system-prompt` CLI flag overrides both files. Use `--append-system-prompt` to add to (rather than replace) the prompt.
593
-
594
- ### Custom Models and Providers
595
-
596
- Add custom models (Ollama, vLLM, LM Studio, etc.) via `~/.pi/agent/models.json`:
597
-
598
- ```json
599
- {
600
- "providers": {
601
- "ollama": {
602
- "baseUrl": "http://localhost:11434/v1",
603
- "apiKey": "OLLAMA_API_KEY",
604
- "api": "openai-completions",
605
- "models": [
606
- {
607
- "id": "llama-3.1-8b",
608
- "name": "Llama 3.1 8B (Local)",
609
- "reasoning": false,
610
- "input": ["text"],
611
- "cost": {"input": 0, "output": 0, "cacheRead": 0, "cacheWrite": 0},
612
- "contextWindow": 128000,
613
- "maxTokens": 32000
614
- }
615
- ]
616
- }
617
- }
618
- }
619
- ```
620
-
621
- **Supported APIs:** `openai-completions`, `openai-responses`, `openai-codex-responses`, `anthropic-messages`, `google-generative-ai`
622
-
623
- **API key resolution:** The `apiKey` field is checked as environment variable name first, then used as literal value.
624
-
625
- **API override:** Set `api` at provider level (default for all models) or model level (override per model).
626
-
627
- **Custom headers:**
628
-
629
- ```json
630
- {
631
- "providers": {
632
- "custom-proxy": {
633
- "baseUrl": "https://proxy.example.com/v1",
634
- "apiKey": "YOUR_API_KEY",
635
- "api": "anthropic-messages",
636
- "headers": {
637
- "User-Agent": "Mozilla/5.0 ...",
638
- "X-Custom-Auth": "token"
639
- },
640
- "models": [...]
641
- }
642
- }
643
- }
644
- ```
645
-
646
- **Overriding built-in providers:**
647
-
648
- To route a built-in provider (anthropic, openai, google, etc.) through a proxy without redefining all models, just specify the `baseUrl`:
649
-
650
- ```json
651
- {
652
- "providers": {
653
- "anthropic": {
654
- "baseUrl": "https://my-proxy.example.com/v1"
655
- }
656
- }
657
- }
658
- ```
659
-
660
- All built-in Anthropic models remain available with the new endpoint. Existing OAuth or API key auth continues to work.
661
-
662
- To fully replace a built-in provider with custom models, include the `models` array:
663
-
664
- ```json
665
- {
666
- "providers": {
667
- "anthropic": {
668
- "baseUrl": "https://my-proxy.example.com/v1",
669
- "apiKey": "ANTHROPIC_API_KEY",
670
- "api": "anthropic-messages",
671
- "models": [...]
672
- }
673
- }
674
- }
248
+ # From repository root (on development machine)
249
+ npm install
250
+ npm run build
675
251
  ```
676
252
 
677
- **Authorization header:** Set `authHeader: true` to add `Authorization: Bearer <apiKey>` automatically.
678
-
679
- **OpenAI compatibility (`compat` field):**
680
-
681
- | Field | Description |
682
- |-------|-------------|
683
- | `supportsStore` | Whether provider supports `store` field |
684
- | `supportsDeveloperRole` | Use `developer` vs `system` role |
685
- | `supportsReasoningEffort` | Support for `reasoning_effort` parameter |
686
- | `supportsUsageInStreaming` | Whether provider supports `stream_options: { include_usage: true }`. Default: `true` |
687
- | `maxTokensField` | Use `max_completion_tokens` or `max_tokens` |
688
-
689
- **Live reload:** The file reloads each time you open `/model`. Edit during session; no restart needed.
690
-
691
- **Model selection priority:**
692
- 1. CLI args (`--provider`, `--model`)
693
- 2. First from `--models` scope (new sessions only)
694
- 3. Restored from session (`--continue`, `--resume`)
695
- 4. Saved default from settings
696
- 5. First available model with valid API key
697
-
698
- > pi can help you create custom provider and model configurations.
699
-
700
- ### Settings File
701
-
702
- Settings are loaded from two locations and merged:
703
-
704
- 1. **Global:** `~/.pi/agent/settings.json` - user preferences
705
- 2. **Project:** `<cwd>/.pi/settings.json` - project-specific overrides (version control friendly)
706
-
707
- Project settings override global settings. For nested objects, individual keys merge. Settings changed via TUI (model, thinking level, etc.) are saved to global preferences only.
708
-
709
- Global `~/.pi/agent/settings.json` stores persistent preferences:
710
-
711
- ```json
712
- {
713
- "theme": "dark",
714
- "defaultProvider": "anthropic",
715
- "defaultModel": "claude-sonnet-4-20250514",
716
- "defaultThinkingLevel": "medium",
717
- "enabledModels": ["anthropic/*", "*gpt*", "gemini-2.5-pro:high"],
718
- "steeringMode": "one-at-a-time",
719
- "followUpMode": "one-at-a-time",
720
- "shellPath": "C:\\path\\to\\bash.exe",
721
- "hideThinkingBlock": false,
722
- "collapseChangelog": false,
723
- "compaction": {
724
- "enabled": true,
725
- "reserveTokens": 16384,
726
- "keepRecentTokens": 20000
727
- },
728
- "skills": {
729
- "enabled": true
730
- },
731
- "retry": {
732
- "enabled": true,
733
- "maxRetries": 3,
734
- "baseDelayMs": 2000
735
- },
736
- "terminal": {
737
- "showImages": true
738
- },
739
- "images": {
740
- "autoResize": true,
741
- "blockImages": false
742
- },
743
- "extensions": ["/path/to/extension.ts"]
744
- }
745
- ```
746
-
747
- | Setting | Description | Default |
748
- |---------|-------------|---------|
749
- | `theme` | Color theme name | auto-detected |
750
- | `defaultProvider` | Default model provider | - |
751
- | `defaultModel` | Default model ID | - |
752
- | `defaultThinkingLevel` | Thinking level: `off`, `minimal`, `low`, `medium`, `high`, `xhigh` | - |
753
- | `enabledModels` | Model patterns for cycling. Supports glob patterns (`github-copilot/*`, `*sonnet*`) and fuzzy matching. Same as `--models` CLI flag | - |
754
- | `steeringMode` | Steering message delivery: `all` or `one-at-a-time` | `one-at-a-time` |
755
- | `followUpMode` | Follow-up message delivery: `all` or `one-at-a-time` | `one-at-a-time` |
756
- | `shellPath` | Custom bash path (Windows) | auto-detected |
757
- | `hideThinkingBlock` | Hide thinking blocks in output (Ctrl+T to toggle) | `false` |
758
- | `collapseChangelog` | Show condensed changelog after update | `false` |
759
- | `compaction.enabled` | Enable auto-compaction | `true` |
760
- | `compaction.reserveTokens` | Tokens to reserve before compaction triggers | `16384` |
761
- | `compaction.keepRecentTokens` | Recent tokens to keep after compaction | `20000` |
762
- | `skills.enabled` | Enable skills discovery | `true` |
763
- | `retry.enabled` | Auto-retry on transient errors | `true` |
764
- | `retry.maxRetries` | Maximum retry attempts | `3` |
765
- | `retry.baseDelayMs` | Base delay for exponential backoff | `2000` |
766
- | `terminal.showImages` | Render images inline (supported terminals) | `true` |
767
- | `images.autoResize` | Auto-resize images to 2000x2000 max for better model compatibility | `true` |
768
- | `images.blockImages` | Prevent images from being sent to LLM providers | `false` |
769
- | `doubleEscapeAction` | Action for double-escape with empty editor: `tree` or `branch` | `tree` |
770
- | `extensions` | Additional extension file paths | `[]` |
771
-
772
- ---
773
-
774
- ## Customization
775
-
776
- ### Themes
777
-
778
- Built-in themes: `dark` (default), `light`. Auto-detected on first run.
779
-
780
- Select theme via `/settings` or set in `~/.pi/agent/settings.json`.
781
-
782
- **Custom themes:** Create `~/.pi/agent/themes/*.json`. Custom themes support live reload.
253
+ To build only the coding-agent package:
783
254
 
784
255
  ```bash
785
- mkdir -p ~/.pi/agent/themes
786
- cp $(npm root -g)/@mariozechner/pi-coding-agent/dist/theme/dark.json ~/.pi/agent/themes/my-theme.json
787
- ```
788
-
789
- Select with `/settings`, then edit the file. Changes apply on save.
790
-
791
- > See [Theme Documentation](docs/theme.md) on how to create custom themes in detail. Pi can help you create a new one.
792
-
793
- **VS Code terminal fix:** Set `terminal.integrated.minimumContrastRatio` to `1` for accurate colors.
794
-
795
- ### Prompt Templates
796
-
797
- Define reusable prompts as Markdown files:
798
-
799
- **Locations:**
800
- - Global: `~/.pi/agent/prompts/*.md`
801
- - Project: `.pi/prompts/*.md`
802
-
803
- **Format:**
804
-
805
- ```markdown
806
- ---
807
- description: Review staged git changes
808
- ---
809
- Review the staged changes (`git diff --cached`). Focus on:
810
- - Bugs and logic errors
811
- - Security issues
812
- - Error handling gaps
813
- ```
814
-
815
- Filename (without `.md`) becomes the command name. Description shown in autocomplete.
816
-
817
- **Arguments:**
818
-
819
- ```markdown
820
- ---
821
- description: Create a component
822
- ---
823
- Create a React component named $1 with features: $@
256
+ cd packages/coding-agent
257
+ npm run build
824
258
  ```
825
259
 
826
- Usage: `/component Button "onClick handler" "disabled support"`
827
- - `$1` = `Button`
828
- - `$@` or `$ARGUMENTS` = all arguments joined (`Button onClick handler disabled support`)
829
-
830
- **Namespacing:** Subdirectories create prefixes. `.pi/prompts/frontend/component.md` → `/component (project:frontend)`
260
+ **For Termux deployment**: Build on a development machine, then either:
261
+ 1. Publish to npm and install from there
262
+ 2. Use `npm pack` to create a .tgz file and transfer it to Termux
831
263
 
264
+ **Note**: The optional dependency `canvas` (in packages/ai) may fail to build due to missing native libraries (pixman-1). This is expected and harmless - npm will skip it and continue. Canvas is only used for ai package tests.
832
265
 
833
- ### Skills
266
+ ### Testing on Termux
834
267
 
835
- Skills are self-contained capability packages that the agent loads on-demand. Pi implements the [Agent Skills standard](https://agentskills.io/specification), warning about violations but remaining lenient.
268
+ 1. Install Termux from F-Droid
269
+ 2. Install dependencies:
270
+ ```bash
271
+ pkg update && pkg install git nodejs-lts
272
+ pkg install termux-api # For clipboard support
273
+ ```
274
+ 3. Install the package:
275
+ ```bash
276
+ npm install -g @vaclav-synacek/pi-coding-agent-termux
277
+ ```
278
+ 4. Run: `pi`
836
279
 
837
- A skill provides specialized workflows, setup instructions, helper scripts, and reference documentation for specific tasks. Skills are loaded when the agent decides a task matches the description, or when you explicitly ask to use one. You can also invoke skills directly via `/skill:name` commands (e.g., `/skill:brave-search`).
280
+ **For development/testing unreleased changes**: Build on a development machine, create a tarball with `npm pack`, transfer to Termux, and install with `npm install -g /path/to/package.tgz`.
838
281
 
839
- **Example use cases:**
840
- - Web search and content extraction (Brave Search API)
841
- - Browser automation via Chrome DevTools Protocol
842
- - Google Calendar, Gmail, Drive integration
843
- - PDF/DOCX processing and creation
844
- - Speech-to-text transcription
845
- - YouTube transcript extraction
282
+ ### Comparison with Upstream
846
283
 
847
- **Skill locations:**
848
- - Pi user: `~/.pi/agent/skills/**/SKILL.md` (recursive)
849
- - Pi project: `.pi/skills/**/SKILL.md` (recursive)
850
- - Claude Code: `~/.claude/skills/*/SKILL.md` and `.claude/skills/*/SKILL.md`
851
- - Codex CLI: `~/.codex/skills/**/SKILL.md` (recursive)
852
-
853
- **Format:**
854
-
855
- ```markdown
856
- ---
857
- name: brave-search
858
- description: Web search via Brave Search API. Use for documentation, facts, or web content.
859
- ---
860
-
861
- # Brave Search
862
-
863
- ## Setup
864
- \`\`\`bash
865
- cd /path/to/brave-search && npm install
866
- \`\`\`
867
-
868
- ## Usage
869
- \`\`\`bash
870
- ./search.js "query" # Basic search
871
- ./search.js "query" --content # Include page content
872
- \`\`\`
873
- ```
874
-
875
- - `name`: Required. Must match parent directory name. Lowercase, hyphens, max 64 chars.
876
- - `description`: Required. Max 1024 chars. Determines when the skill is loaded.
877
-
878
- **Disable skills:** `pi --no-skills` or set `skills.enabled: false` in settings.
879
-
880
- > See [docs/skills.md](docs/skills.md) for details, examples, and links to skill repositories. pi can help you create new skills.
881
-
882
- ### Extensions
883
-
884
- Extensions are TypeScript modules that extend pi's behavior.
885
-
886
- **Use cases:**
887
- - **Custom tools** - Register tools callable by the LLM with custom UI and rendering
888
- - **Custom commands** - Add `/commands` for users (e.g., `/deploy`, `/stats`)
889
- - **Event interception** - Block tool calls, modify results, customize compaction
890
- - **State persistence** - Store data in session, reconstruct on reload/fork
891
- - **External integrations** - File watchers, webhooks, git checkpointing
892
- - **Custom UI** - Full TUI control from tools, commands, or event handlers
893
-
894
- **Locations:**
895
- - Global: `~/.pi/agent/extensions/*.ts` or `~/.pi/agent/extensions/*/index.ts`
896
- - Project: `.pi/extensions/*.ts` or `.pi/extensions/*/index.ts`
897
- - CLI: `--extension <path>` or `-e <path>`
898
-
899
- **Dependencies:** Extensions can have their own dependencies. Place a `package.json` next to the extension (or in a parent directory), run `npm install`, and imports are resolved via [jiti](https://github.com/unjs/jiti). See [examples/extensions/with-deps/](examples/extensions/with-deps/).
900
-
901
- #### Custom Tools
902
-
903
- Tools are functions the LLM can call. They appear in the system prompt and can have custom rendering.
904
-
905
- ```typescript
906
- import type { ExtensionAPI } from "@mariozechner/pi-coding-agent";
907
- import { Type } from "@sinclair/typebox";
908
- import { Text } from "@mariozechner/pi-tui";
909
-
910
- export default function (pi: ExtensionAPI) {
911
- pi.registerTool({
912
- name: "deploy",
913
- label: "Deploy",
914
- description: "Deploy the application to production",
915
- parameters: Type.Object({
916
- environment: Type.String({ description: "Target environment" }),
917
- }),
918
-
919
- async execute(toolCallId, params, onUpdate, ctx, signal) {
920
- // Show progress via onUpdate
921
- onUpdate({ status: "Deploying..." });
922
-
923
- // Ask user for confirmation
924
- const ok = await ctx.ui.confirm("Deploy?", `Deploy to ${params.environment}?`);
925
- if (!ok) {
926
- return { content: [{ type: "text", text: "Cancelled" }], details: { cancelled: true } };
927
- }
928
-
929
- // Run shell commands
930
- const result = await ctx.exec("./deploy.sh", [params.environment], { signal });
931
-
932
- return {
933
- content: [{ type: "text", text: result.stdout }],
934
- details: { environment: params.environment, exitCode: result.exitCode },
935
- };
936
- },
937
-
938
- // Custom TUI rendering (optional)
939
- renderCall(args, theme) {
940
- return new Text(theme.bold("deploy ") + theme.fg("accent", args.environment), 0, 0);
941
- },
942
- renderResult(result, options, theme) {
943
- const ok = result.details?.exitCode === 0;
944
- return new Text(ok ? theme.fg("success", "✓ Deployed") : theme.fg("error", "✗ Failed"), 0, 0);
945
- },
946
- });
947
- }
948
- ```
949
-
950
- #### Custom Commands
951
-
952
- Commands are user-invoked via `/name`. They can show custom UI, modify state, or trigger agent turns.
953
-
954
- ```typescript
955
- export default function (pi: ExtensionAPI) {
956
- pi.registerCommand("stats", {
957
- description: "Show session statistics",
958
- handler: async (args, ctx) => {
959
- // Simple notification
960
- ctx.ui.notify(`${ctx.sessionManager.getEntries().length} entries`, "info");
961
- },
962
- });
963
-
964
- pi.registerCommand("todos", {
965
- description: "Interactive todo viewer",
966
- handler: async (args, ctx) => {
967
- // Full custom UI with keyboard handling
968
- await ctx.ui.custom((tui, theme, done) => {
969
- return {
970
- render(width) {
971
- return [
972
- theme.bold("Todos"),
973
- "- [ ] Item 1",
974
- "- [x] Item 2",
975
- "",
976
- theme.fg("dim", "Press Escape to close"),
977
- ];
978
- },
979
- handleInput(data) {
980
- if (matchesKey(data, "escape")) done();
981
- },
982
- };
983
- });
984
- },
985
- });
986
- }
987
- ```
988
-
989
- #### Event Interception
990
-
991
- Subscribe to lifecycle events to block, modify, or observe agent behavior.
992
-
993
- ```typescript
994
- export default function (pi: ExtensionAPI) {
995
- // Block dangerous commands
996
- pi.on("tool_call", async (event, ctx) => {
997
- if (event.toolName === "bash" && /rm -rf/.test(event.input.command as string)) {
998
- const ok = await ctx.ui.confirm("Dangerous!", "Allow rm -rf?");
999
- if (!ok) return { block: true, reason: "Blocked by user" };
1000
- }
1001
- });
1002
-
1003
- // Modify tool results
1004
- pi.on("tool_result", async (event, ctx) => {
1005
- if (event.toolName === "read") {
1006
- // Redact secrets from file contents
1007
- return { modifiedResult: event.result.replace(/API_KEY=\w+/g, "API_KEY=***") };
1008
- }
1009
- });
1010
-
1011
- // Custom compaction
1012
- pi.on("session_before_compact", async (event, ctx) => {
1013
- return { customSummary: "My custom summary of the conversation so far..." };
1014
- });
1015
-
1016
- // Git checkpoint on each turn
1017
- pi.on("turn_end", async (event, ctx) => {
1018
- await ctx.exec("git", ["stash", "push", "-m", `pi-checkpoint-${Date.now()}`]);
1019
- });
1020
- }
1021
- ```
1022
-
1023
- #### State Persistence
1024
-
1025
- Store state in session entries that survive reload and work correctly with branching.
1026
-
1027
- ```typescript
1028
- export default function (pi: ExtensionAPI) {
1029
- let counter = 0;
1030
-
1031
- // Reconstruct state from session history
1032
- const reconstruct = (ctx) => {
1033
- counter = 0;
1034
- for (const entry of ctx.sessionManager.getBranch()) {
1035
- if (entry.type === "custom" && entry.customType === "my_counter") {
1036
- counter = entry.data.value;
1037
- }
1038
- }
1039
- };
1040
-
1041
- pi.on("session_start", async (e, ctx) => reconstruct(ctx));
1042
- pi.on("session_fork", async (e, ctx) => reconstruct(ctx));
1043
- pi.on("session_tree", async (e, ctx) => reconstruct(ctx));
1044
-
1045
- pi.registerCommand("increment", {
1046
- handler: async (args, ctx) => {
1047
- counter++;
1048
- ctx.appendEntry("my_counter", { value: counter }); // Persisted in session
1049
- ctx.ui.notify(`Counter: ${counter}`, "info");
1050
- },
1051
- });
1052
- }
1053
- ```
1054
-
1055
- #### Keyboard Shortcuts
1056
-
1057
- Register custom keyboard shortcuts (shown in `/hotkeys`):
1058
-
1059
- ```typescript
1060
- export default function (pi: ExtensionAPI) {
1061
- pi.registerShortcut("ctrl+shift+d", {
1062
- description: "Deploy to production",
1063
- handler: async (ctx) => {
1064
- ctx.ui.notify("Deploying...", "info");
1065
- await ctx.exec("./deploy.sh", []);
1066
- },
1067
- });
1068
- }
1069
- ```
1070
-
1071
- #### CLI Flags
1072
-
1073
- Register custom CLI flags (parsed automatically, shown in `--help`):
1074
-
1075
- ```typescript
1076
- export default function (pi: ExtensionAPI) {
1077
- pi.registerFlag("dry-run", {
1078
- description: "Run without making changes",
1079
- type: "boolean",
1080
- });
1081
-
1082
- pi.on("tool_call", async (event, ctx) => {
1083
- if (pi.getFlag("dry-run") && event.toolName === "write") {
1084
- return { block: true, reason: "Dry run mode" };
1085
- }
1086
- });
1087
- }
1088
- ```
1089
-
1090
- #### Custom UI
1091
-
1092
- Extensions have full TUI access via `ctx.ui`:
1093
-
1094
- ```typescript
1095
- // Simple prompts
1096
- const confirmed = await ctx.ui.confirm("Title", "Are you sure?");
1097
- const choice = await ctx.ui.select("Pick one", ["Option A", "Option B"]);
1098
- const text = await ctx.ui.input("Enter value");
1099
-
1100
- // Notifications
1101
- ctx.ui.notify("Done!", "success"); // success, info, warning, error
1102
-
1103
- // Status line (persistent in footer, multiple extensions can set their own)
1104
- ctx.ui.setStatus("my-ext", "Processing...");
1105
- ctx.ui.setStatus("my-ext", null); // Clear
1106
-
1107
- // Widgets (above editor)
1108
- ctx.ui.setWidget("my-ext", ["Line 1", "Line 2"]);
1109
-
1110
- // Custom footer (replaces built-in footer)
1111
- ctx.ui.setFooter((tui, theme) => ({
1112
- render(width) { return [theme.fg("dim", "Custom footer")]; },
1113
- invalidate() {},
1114
- }));
1115
- ctx.ui.setFooter(undefined); // Restore built-in footer
1116
-
1117
- // Full custom component with keyboard handling
1118
- await ctx.ui.custom((tui, theme, done) => ({
1119
- render(width) {
1120
- return [
1121
- theme.bold("My Component"),
1122
- theme.fg("dim", "Press Escape to close"),
1123
- ];
1124
- },
1125
- handleInput(data) {
1126
- if (matchesKey(data, "escape")) done();
1127
- },
1128
- }));
1129
- ```
1130
-
1131
- > See [docs/extensions.md](docs/extensions.md) for full API reference.
1132
- > See [docs/tui.md](docs/tui.md) for TUI components and custom rendering.
1133
- > See [examples/extensions/](examples/extensions/) for working examples.
1134
-
1135
- ---
1136
-
1137
- ## CLI Reference
284
+ To see all Termux-specific changes:
1138
285
 
1139
286
  ```bash
1140
- pi [options] [@files...] [messages...]
287
+ git diff upstream master
1141
288
  ```
1142
289
 
1143
- ### Options
1144
-
1145
- | Option | Description |
1146
- |--------|-------------|
1147
- | `--provider <name>` | Provider: `anthropic`, `openai`, `openai-codex`, `google`, `google-vertex`, `amazon-bedrock`, `mistral`, `xai`, `groq`, `cerebras`, `openrouter`, `vercel-ai-gateway`, `zai`, `minimax`, `github-copilot`, `google-gemini-cli`, `google-antigravity`, or custom |
1148
- | `--model <id>` | Model ID |
1149
- | `--api-key <key>` | API key (overrides environment) |
1150
- | `--system-prompt <text\|file>` | Custom system prompt (text or file path) |
1151
- | `--append-system-prompt <text\|file>` | Append to system prompt |
1152
- | `--mode <mode>` | Output mode: `text`, `json`, `rpc` (implies `--print`) |
1153
- | `--print`, `-p` | Non-interactive: process prompt and exit |
1154
- | `--no-session` | Don't save session |
1155
- | `--session <path>` | Use specific session file |
1156
- | `--session-dir <dir>` | Directory for session storage and lookup |
1157
- | `--continue`, `-c` | Continue most recent session |
1158
- | `--resume`, `-r` | Select session to resume |
1159
- | `--models <patterns>` | Comma-separated patterns for Ctrl+P cycling. Supports glob patterns (e.g., `anthropic/*`, `*sonnet*:high`) and fuzzy matching (e.g., `sonnet,haiku:low`) |
1160
- | `--no-tools` | Disable all built-in tools |
1161
- | `--tools <tools>` | Comma-separated tool list (default: `read,bash,edit,write`) |
1162
- | `--thinking <level>` | Thinking level: `off`, `minimal`, `low`, `medium`, `high` |
1163
- | `--extension <path>`, `-e` | Load an extension file (can be used multiple times) |
1164
- | `--no-extensions` | Disable extension discovery (explicit `-e` paths still work) |
1165
- | `--no-skills` | Disable skills discovery and loading |
1166
- | `--skills <patterns>` | Comma-separated glob patterns to filter skills (e.g., `git-*,docker`) |
1167
- | `--export <file> [output]` | Export session to HTML |
1168
- | `--help`, `-h` | Show help |
1169
- | `--version`, `-v` | Show version |
1170
-
1171
- ### File Arguments
1172
-
1173
- Include files with `@` prefix:
290
+ To see changes in a specific file:
1174
291
 
1175
292
  ```bash
1176
- pi @prompt.md "Answer this"
1177
- pi @screenshot.png "What's in this image?"
1178
- pi @requirements.md @design.png "Implement this"
293
+ git diff upstream master packages/coding-agent/src/utils/clipboard.ts
1179
294
  ```
1180
295
 
1181
- Text files wrapped in `<file name="path">content</file>`. Images attached as base64.
1182
-
1183
- ### Examples
1184
-
1185
- ```bash
1186
- # Interactive mode
1187
- pi
1188
-
1189
- # Interactive with initial prompt
1190
- pi "List all .ts files in src/"
1191
-
1192
- # Non-interactive
1193
- pi -p "List all .ts files in src/"
1194
-
1195
- # With files
1196
- pi -p @code.ts "Review this code"
1197
-
1198
- # JSON event stream
1199
- pi --mode json "List files"
1200
-
1201
- # RPC mode (headless)
1202
- pi --mode rpc --no-session
296
+ ## Publishing to npm
1203
297
 
1204
- # Continue session
1205
- pi -c "What did we discuss?"
298
+ The package is published as `@vaclav-synacek/pi-coding-agent-termux` on npm.
1206
299
 
1207
- # Specific model
1208
- pi --provider openai --model gpt-4o "Help me refactor"
1209
-
1210
- # Model cycling with thinking levels
1211
- pi --models sonnet:high,haiku:low
1212
-
1213
- # Limit to specific provider with glob pattern
1214
- pi --models "github-copilot/*"
1215
-
1216
- # Read-only mode
1217
- pi --tools read,grep,find,ls -p "Review the architecture"
1218
-
1219
- # Export session
1220
- pi --export session.jsonl output.html
1221
- ```
1222
-
1223
- ### Environment Variables
1224
-
1225
- | Variable | Description |
1226
- |----------|-------------|
1227
- | `ANTHROPIC_API_KEY`, `OPENAI_API_KEY`, etc. | API keys for providers (see [API Keys & OAuth](#api-keys--oauth)) |
1228
- | `PI_CODING_AGENT_DIR` | Override the agent config directory (default: `~/.pi/agent`) |
1229
- | `PI_SKIP_VERSION_CHECK` | Skip new version check at startup (useful for Nix or other package manager installs) |
1230
- | `VISUAL`, `EDITOR` | External editor for Ctrl+G (e.g., `vim`, `code --wait`) |
1231
-
1232
- ---
1233
-
1234
- ## Tools
1235
-
1236
- ### Default Tools
1237
-
1238
- | Tool | Description |
1239
- |------|-------------|
1240
- | `read` | Read file contents. Images sent as attachments. Text: first 2000 lines, lines truncated at 2000 chars. Use offset/limit for large files. |
1241
- | `write` | Write/overwrite file. Creates parent directories. |
1242
- | `edit` | Replace exact text in file. Must match exactly including whitespace. Fails if text appears multiple times or not found. |
1243
- | `bash` | Execute command. Returns stdout/stderr. Optional `timeout` parameter. |
1244
-
1245
- ### Read-Only Tools
1246
-
1247
- Available via `--tools` flag:
1248
-
1249
- | Tool | Description |
1250
- |------|-------------|
1251
- | `grep` | Search file contents (regex or literal). Respects `.gitignore`. |
1252
- | `find` | Search for files by glob pattern. Respects `.gitignore`. |
1253
- | `ls` | List directory contents. Includes dotfiles. |
1254
-
1255
- Example: `--tools read,grep,find,ls` for code review without modification.
1256
-
1257
- For adding new tools, see [Extensions](#extensions) in the Customization section.
1258
-
1259
- ---
1260
-
1261
- ## Programmatic Usage
1262
-
1263
- ### SDK
1264
-
1265
- For embedding pi in Node.js/TypeScript applications, use the SDK:
1266
-
1267
- ```typescript
1268
- import { createAgentSession, discoverAuthStorage, discoverModels, SessionManager } from "@mariozechner/pi-coding-agent";
1269
-
1270
- const authStorage = discoverAuthStorage();
1271
- const modelRegistry = discoverModels(authStorage);
1272
-
1273
- const { session } = await createAgentSession({
1274
- sessionManager: SessionManager.inMemory(),
1275
- authStorage,
1276
- modelRegistry,
1277
- });
1278
-
1279
- session.subscribe((event) => {
1280
- if (event.type === "message_update" && event.assistantMessageEvent.type === "text_delta") {
1281
- process.stdout.write(event.assistantMessageEvent.delta);
1282
- }
1283
- });
1284
-
1285
- await session.prompt("What files are in the current directory?");
1286
- ```
1287
-
1288
- The SDK provides full control over:
1289
- - Model selection and thinking level
1290
- - System prompt (replace or modify)
1291
- - Tools (built-in subsets, custom tools)
1292
- - Extensions (discovered or via paths)
1293
- - Skills, context files, prompt templates
1294
- - Session persistence (`SessionManager`)
1295
- - Settings (`SettingsManager`)
1296
- - API key resolution and OAuth
1297
-
1298
- **Philosophy:** "Omit to discover, provide to override." Omit an option and pi discovers from standard locations. Provide an option and your value is used.
1299
-
1300
- > See [SDK Documentation](docs/sdk.md) for the full API reference. See [examples/sdk/](examples/sdk/) for working examples from minimal to full control.
1301
-
1302
- ### RPC Mode
1303
-
1304
- For embedding pi from other languages or with process isolation:
300
+ **Publishing steps:**
1305
301
 
1306
302
  ```bash
1307
- pi --mode rpc --no-session
1308
- ```
1309
-
1310
- Send JSON commands on stdin:
1311
- ```json
1312
- {"type":"prompt","message":"List all .ts files"}
1313
- {"type":"abort"}
303
+ cd packages/coding-agent
304
+ npm publish
1314
305
  ```
1315
306
 
1316
- > See [RPC Documentation](docs/rpc.md) for the full protocol.
1317
-
1318
- ### HTML Export
1319
-
1320
- ```bash
1321
- pi --export session.jsonl # Auto-generated filename
1322
- pi --export session.jsonl output.html # Custom filename
1323
- ```
1324
-
1325
- Works with session files.
1326
-
1327
- ---
1328
-
1329
- ## Philosophy
1330
-
1331
- Pi is opinionated about what it won't do. These are intentional design decisions to minimize context bloat and avoid anti-patterns.
1332
-
1333
- **No MCP.** Build CLI tools with READMEs (see [Skills](#skills)). The agent reads them on demand. [Would you like to know more?](https://mariozechner.at/posts/2025-11-02-what-if-you-dont-need-mcp/)
1334
-
1335
- **No sub-agents.** Spawn pi instances via tmux, or [build your own sub-agent tool](examples/extensions/subagent/) with [Extensions](#extensions). Full observability and steerability.
1336
-
1337
- **No permission popups.** Security theater. Run in a container or build your own with [Extensions](#extensions).
307
+ **Key package.json fields:**
308
+ - `name`: `@vaclav-synacek/pi-coding-agent-termux` (different from upstream to avoid conflicts)
309
+ - `version`: Matches upstream version (e.g., `0.46.0`)
310
+ - `description`: "Termux port of pi-coding-agent - Coding agent CLI with read, bash, edit, write tools and session management"
311
+ - `repository`: Points to this repository (`VaclavSynacek/pi-coding-agent-termux`)
312
+ - `homepage`: https://github.com/VaclavSynacek/pi-coding-agent-termux#readme
1338
313
 
1339
- **No plan mode.** Gather context in one session, write plans to file, start fresh for implementation.
314
+ ## Why This Approach?
1340
315
 
1341
- **No built-in to-dos.** They confuse models. Use a TODO.md file, or [build your own](examples/extensions/todo.ts) with [Extensions](#extensions).
316
+ This maintenance strategy provides:
1342
317
 
1343
- **No background bash.** Use tmux. Full observability, direct interaction.
318
+ 1. **Clean separation** - Clear distinction between upstream code and Termux patches
319
+ 2. **Easy updates** - Rebasing makes it straightforward to adopt new upstream features
320
+ 3. **Version history** - Immutable tags preserve every published version
321
+ 4. **Transparency** - Easy to see exactly what's different from upstream
322
+ 5. **Maintainability** - Future maintainers can understand the port structure
323
+ 6. **No upstream dependency** - Port can continue indefinitely without upstream acceptance
1344
324
 
1345
- Read the [blog post](https://mariozechner.at/posts/2025-11-30-pi-coding-agent/) for the full rationale.
325
+ ## Contributing
1346
326
 
1347
- ---
327
+ When contributing Termux-specific changes:
1348
328
 
1349
- ## Development
329
+ 1. Fork this repository
330
+ 2. Create a feature branch from `master`
331
+ 3. Make focused commits with clear messages
332
+ 4. Test on actual Termux device
333
+ 5. Submit pull request
1350
334
 
1351
- ### Forking / Rebranding
1352
-
1353
- Configure via `package.json`:
1354
-
1355
- ```json
1356
- {
1357
- "piConfig": {
1358
- "name": "pi",
1359
- "configDir": ".pi"
1360
- }
1361
- }
1362
- ```
1363
-
1364
- Change `name`, `configDir`, and `bin` field for your fork. Affects CLI banner, config paths, and environment variable names.
1365
-
1366
- ### Path Resolution
1367
-
1368
- Three execution modes: npm install, standalone binary, tsx from source.
1369
-
1370
- **Always use `src/paths.ts`** for package assets:
1371
-
1372
- ```typescript
1373
- import { getPackageDir, getThemeDir } from "./paths.js";
1374
- ```
1375
-
1376
- Never use `__dirname` directly for package assets.
1377
-
1378
- ### Debug Command
1379
-
1380
- `/debug` (hidden) writes rendered lines with ANSI codes to `~/.pi/agent/pi-debug.log` for TUI debugging, as well as the last set of messages that were sent to the LLM.
1381
-
1382
- ---
335
+ For general pi-coding-agent features/bugs, contribute to the [upstream repository](https://github.com/badlogic/pi-mono) instead.
1383
336
 
1384
337
  ## License
1385
338
 
1386
- MIT
1387
-
1388
- ## See Also
339
+ Same as upstream: MIT License
1389
340
 
1390
- - [@mariozechner/pi-ai](https://www.npmjs.com/package/@mariozechner/pi-ai): Core LLM toolkit
1391
- - [@mariozechner/pi-agent](https://www.npmjs.com/package/@mariozechner/pi-agent): Agent framework
1392
- - [@mariozechner/pi-tui](https://www.npmjs.com/package/@mariozechner/pi-tui): Terminal UI components
341
+ See [LICENSE](LICENSE) file for details.