@counterposition/skill-pi 0.1.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.
- package/LICENSE.md +675 -0
- package/README.md +17 -0
- package/package.json +42 -0
- package/skills/pi/LICENSE.md +675 -0
- package/skills/pi/README.md +38 -0
- package/skills/pi/SKILL.md +170 -0
- package/skills/pi/evals/evals.json +50 -0
- package/skills/pi/references/extensions.md +343 -0
- package/skills/pi/references/packages.md +97 -0
- package/skills/pi/references/patterns.md +314 -0
- package/skills/pi/references/providers.md +212 -0
- package/skills/pi/references/sdk.md +177 -0
- package/skills/pi/references/settings.md +170 -0
- package/skills/pi/references/skills.md +111 -0
|
@@ -0,0 +1,177 @@
|
|
|
1
|
+
# SDK
|
|
2
|
+
|
|
3
|
+
The SDK lets you embed Pi programmatically in Node.js applications via `createAgentSession()`.
|
|
4
|
+
|
|
5
|
+
## Installation
|
|
6
|
+
|
|
7
|
+
```bash
|
|
8
|
+
npm install @mariozechner/pi-coding-agent
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
## Quick Start
|
|
12
|
+
|
|
13
|
+
```typescript
|
|
14
|
+
import { createAgentSession } from "@mariozechner/pi-coding-agent";
|
|
15
|
+
|
|
16
|
+
const { session } = await createAgentSession();
|
|
17
|
+
|
|
18
|
+
session.subscribe((event) => {
|
|
19
|
+
if (event.type === "message_update" && event.delta?.type === "text_delta") {
|
|
20
|
+
process.stdout.write(event.delta.text);
|
|
21
|
+
}
|
|
22
|
+
if (event.type === "agent_end") {
|
|
23
|
+
console.log("\nDone.");
|
|
24
|
+
}
|
|
25
|
+
});
|
|
26
|
+
|
|
27
|
+
await session.prompt("List all TypeScript files in the current directory");
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
Run with: `npx tsx my-script.ts`
|
|
31
|
+
|
|
32
|
+
## Factory Options
|
|
33
|
+
|
|
34
|
+
```typescript
|
|
35
|
+
const { session } = await createAgentSession({
|
|
36
|
+
// Authentication
|
|
37
|
+
authStorage: new AuthStorage({ path: "~/.pi/agent/auth.json" }),
|
|
38
|
+
|
|
39
|
+
// Model configuration
|
|
40
|
+
modelRegistry: new ModelRegistry(),
|
|
41
|
+
model: getModel("anthropic", "claude-sonnet-4-20250514"),
|
|
42
|
+
thinkingLevel: "medium",
|
|
43
|
+
|
|
44
|
+
// Working directory
|
|
45
|
+
cwd: process.cwd(),
|
|
46
|
+
|
|
47
|
+
// Agent config directory
|
|
48
|
+
agentDir: "~/.pi/agent",
|
|
49
|
+
|
|
50
|
+
// Tools (built-in presets or custom)
|
|
51
|
+
tools: codingTools(), // Default: read, bash, edit, write
|
|
52
|
+
// tools: readOnlyTools(), // read, grep, find, ls
|
|
53
|
+
// tools: allTools(), // All seven built-in tools
|
|
54
|
+
|
|
55
|
+
// Resource discovery
|
|
56
|
+
resourceLoader: new DefaultResourceLoader(),
|
|
57
|
+
|
|
58
|
+
// Extensions (inline factories)
|
|
59
|
+
extensionFactories: [
|
|
60
|
+
(pi) => {
|
|
61
|
+
pi.on("agent_start", async () => { /* ... */ });
|
|
62
|
+
},
|
|
63
|
+
],
|
|
64
|
+
|
|
65
|
+
// Session persistence
|
|
66
|
+
sessionManager: SessionManager.create("path/to/session.jsonl"),
|
|
67
|
+
// sessionManager: SessionManager.inMemory(), // No persistence
|
|
68
|
+
|
|
69
|
+
// Settings
|
|
70
|
+
settings: new SettingsManager({ /* ... */ }),
|
|
71
|
+
|
|
72
|
+
// System prompt
|
|
73
|
+
systemPrompt: "Custom system prompt",
|
|
74
|
+
});
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
## Key Imports
|
|
78
|
+
|
|
79
|
+
```typescript
|
|
80
|
+
import {
|
|
81
|
+
createAgentSession,
|
|
82
|
+
// Auth & config
|
|
83
|
+
AuthStorage,
|
|
84
|
+
ModelRegistry,
|
|
85
|
+
SettingsManager,
|
|
86
|
+
SessionManager,
|
|
87
|
+
DefaultResourceLoader,
|
|
88
|
+
// Tools
|
|
89
|
+
codingTools,
|
|
90
|
+
readOnlyTools,
|
|
91
|
+
allTools,
|
|
92
|
+
readTool,
|
|
93
|
+
bashTool,
|
|
94
|
+
editTool,
|
|
95
|
+
writeTool,
|
|
96
|
+
grepTool,
|
|
97
|
+
findTool,
|
|
98
|
+
lsTool,
|
|
99
|
+
// Models
|
|
100
|
+
getModel,
|
|
101
|
+
} from "@mariozechner/pi-coding-agent";
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
## Event Types
|
|
105
|
+
|
|
106
|
+
```typescript
|
|
107
|
+
session.subscribe((event) => {
|
|
108
|
+
switch (event.type) {
|
|
109
|
+
// Streaming
|
|
110
|
+
case "message_start": // New assistant message begins
|
|
111
|
+
case "message_update": // Text/thinking/tool-call delta
|
|
112
|
+
case "message_end": // Assistant message complete (includes full message)
|
|
113
|
+
|
|
114
|
+
// Tool execution
|
|
115
|
+
case "tool_execution_start": // Tool begins (toolCallId, toolName)
|
|
116
|
+
case "tool_execution_update": // Partial tool output
|
|
117
|
+
case "tool_execution_end": // Tool complete (toolCallId, result)
|
|
118
|
+
|
|
119
|
+
// Lifecycle
|
|
120
|
+
case "agent_start": // Agent begins processing
|
|
121
|
+
case "agent_end": // Agent finishes
|
|
122
|
+
case "turn_start": // New LLM turn
|
|
123
|
+
case "turn_end": // LLM turn complete
|
|
124
|
+
|
|
125
|
+
// System
|
|
126
|
+
case "auto_compaction_start":
|
|
127
|
+
case "auto_compaction_end":
|
|
128
|
+
case "auto_retry_start":
|
|
129
|
+
case "auto_retry_end":
|
|
130
|
+
}
|
|
131
|
+
});
|
|
132
|
+
```
|
|
133
|
+
|
|
134
|
+
## Session Methods
|
|
135
|
+
|
|
136
|
+
```typescript
|
|
137
|
+
// Send a prompt
|
|
138
|
+
await session.prompt("Do something");
|
|
139
|
+
|
|
140
|
+
// Queue message during active streaming
|
|
141
|
+
session.steer("Actually, do this instead"); // Interrupts current tool execution
|
|
142
|
+
session.followUp("After you're done, also..."); // Queued until agent finishes
|
|
143
|
+
|
|
144
|
+
// Control
|
|
145
|
+
session.abort(); // Cancel current generation
|
|
146
|
+
await session.waitForIdle(); // Wait until agent is idle
|
|
147
|
+
|
|
148
|
+
// Model
|
|
149
|
+
session.setModel(getModel("openai", "gpt-4o"));
|
|
150
|
+
session.setThinkingLevel("high");
|
|
151
|
+
session.cycleModel();
|
|
152
|
+
|
|
153
|
+
// Compaction
|
|
154
|
+
await session.compact();
|
|
155
|
+
|
|
156
|
+
// State
|
|
157
|
+
const messages = session.getMessages();
|
|
158
|
+
const state = session.getState();
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
## Run Modes
|
|
162
|
+
|
|
163
|
+
For non-SDK usage, Pi provides run mode functions:
|
|
164
|
+
|
|
165
|
+
```typescript
|
|
166
|
+
import { runPrintMode, runRpcMode, InteractiveMode } from "@mariozechner/pi-coding-agent";
|
|
167
|
+
|
|
168
|
+
// Print mode (single-shot)
|
|
169
|
+
await runPrintMode(session, { outputFormat: "text" }); // or "json"
|
|
170
|
+
|
|
171
|
+
// RPC mode (JSON-RPC over stdin/stdout)
|
|
172
|
+
await runRpcMode(session);
|
|
173
|
+
|
|
174
|
+
// Interactive mode (full TUI)
|
|
175
|
+
const mode = new InteractiveMode(session);
|
|
176
|
+
await mode.start();
|
|
177
|
+
```
|
|
@@ -0,0 +1,170 @@
|
|
|
1
|
+
# Settings
|
|
2
|
+
|
|
3
|
+
Pi uses hierarchical JSON configuration. Project settings (`.pi/settings.json`) merge over global settings (`~/.pi/agent/settings.json`). Nested objects are deep-merged; project values override global for the same key.
|
|
4
|
+
|
|
5
|
+
Edit settings directly or use `/settings` in interactive mode.
|
|
6
|
+
|
|
7
|
+
## Complete Settings Reference
|
|
8
|
+
|
|
9
|
+
### Model & Thinking
|
|
10
|
+
|
|
11
|
+
```json
|
|
12
|
+
{
|
|
13
|
+
"provider": "anthropic", // Default provider name
|
|
14
|
+
"model": "claude-sonnet-4-20250514", // Default model ID
|
|
15
|
+
"thinkingLevel": "medium", // "off" | "minimal" | "low" | "medium" | "high" | "xhigh"
|
|
16
|
+
"thinkingLevelBudget": null, // Custom token budget per thinking level (overrides defaults)
|
|
17
|
+
"modelCyclePatterns": ["claude-*", "gpt-4o"] // Glob patterns for Ctrl+P model cycling
|
|
18
|
+
}
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
### Compaction
|
|
22
|
+
|
|
23
|
+
```json
|
|
24
|
+
{
|
|
25
|
+
"compaction": {
|
|
26
|
+
"enabled": true, // Enable auto-compaction
|
|
27
|
+
"reserveTokens": 16384, // Tokens to reserve for new responses
|
|
28
|
+
"keepRecentTokens": 20000 // Recent tokens to keep uncompacted
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
### Branch Summary
|
|
34
|
+
|
|
35
|
+
```json
|
|
36
|
+
{
|
|
37
|
+
"branchSummary": {
|
|
38
|
+
"enabled": true, // Summarize when switching branches via /tree
|
|
39
|
+
"maxTokens": 4096, // Max tokens for summary
|
|
40
|
+
"skipPrompt": false // Skip confirmation prompt
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
### Retry
|
|
46
|
+
|
|
47
|
+
```json
|
|
48
|
+
{
|
|
49
|
+
"retry": {
|
|
50
|
+
"maxRetries": 3, // Max automatic retries on transient errors
|
|
51
|
+
"initialDelayMs": 2000, // First retry delay
|
|
52
|
+
"maxDelayMs": 60000 // Max delay (exponential backoff)
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
### Message Delivery
|
|
58
|
+
|
|
59
|
+
```json
|
|
60
|
+
{
|
|
61
|
+
"steeringMode": "all", // "all" | "one-at-a-time" — how steer messages are delivered
|
|
62
|
+
"followUpMode": "all", // "all" | "one-at-a-time" — how follow-up messages are delivered
|
|
63
|
+
"transport": "auto" // "sse" | "websocket" | "auto"
|
|
64
|
+
}
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
### Terminal & Images
|
|
68
|
+
|
|
69
|
+
```json
|
|
70
|
+
{
|
|
71
|
+
"terminal": {
|
|
72
|
+
"showImages": true, // Display images in terminal
|
|
73
|
+
"maxImageWidth": 2000, // Max image dimensions for resizing
|
|
74
|
+
"maxImageHeight": 2000
|
|
75
|
+
},
|
|
76
|
+
"image": {
|
|
77
|
+
"autoResize": true // Auto-resize large images before sending to LLM
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
### Shell
|
|
83
|
+
|
|
84
|
+
```json
|
|
85
|
+
{
|
|
86
|
+
"shellPath": "/bin/bash", // Custom shell path (Windows: "C:\\...\\bash.exe")
|
|
87
|
+
"shellCommandPrefix": "", // Prefix prepended to every bash command
|
|
88
|
+
"npmCommand": "npm" // npm, pnpm, yarn, bun
|
|
89
|
+
}
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
### UI
|
|
93
|
+
|
|
94
|
+
```json
|
|
95
|
+
{
|
|
96
|
+
"theme": "dark", // "dark" | "light" | custom theme name
|
|
97
|
+
"showStartupBanner": true, // Show banner on startup
|
|
98
|
+
"editorPadding": 1, // Lines of padding in editor
|
|
99
|
+
"showAutoComplete": true, // Show autocomplete suggestions
|
|
100
|
+
"cursorStyle": "block" // "block" | "underline" | "bar"
|
|
101
|
+
}
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
### Sessions
|
|
105
|
+
|
|
106
|
+
```json
|
|
107
|
+
{
|
|
108
|
+
"sessionDir": null // Custom session storage path (default: ~/.pi/agent/sessions/)
|
|
109
|
+
}
|
|
110
|
+
```
|
|
111
|
+
|
|
112
|
+
### Resources
|
|
113
|
+
|
|
114
|
+
Load extensions, skills, prompts, and themes from paths or packages:
|
|
115
|
+
|
|
116
|
+
```json
|
|
117
|
+
{
|
|
118
|
+
"extensions": [
|
|
119
|
+
"~/.pi/agent/extensions/my-ext.ts",
|
|
120
|
+
"npm:@foo/pi-extensions"
|
|
121
|
+
],
|
|
122
|
+
"skills": [
|
|
123
|
+
".pi/skills/my-skill",
|
|
124
|
+
"npm:@foo/pi-skills"
|
|
125
|
+
],
|
|
126
|
+
"prompts": [
|
|
127
|
+
"~/.pi/agent/prompts/"
|
|
128
|
+
],
|
|
129
|
+
"themes": [
|
|
130
|
+
"npm:@foo/pi-themes"
|
|
131
|
+
],
|
|
132
|
+
"customPackages": [
|
|
133
|
+
"npm:@foo/pi-package@1.0.0",
|
|
134
|
+
"git:github.com/user/repo",
|
|
135
|
+
"./local/path"
|
|
136
|
+
]
|
|
137
|
+
}
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
### Resource Pattern Matching
|
|
141
|
+
|
|
142
|
+
Resources support include/exclude patterns:
|
|
143
|
+
|
|
144
|
+
```json
|
|
145
|
+
{
|
|
146
|
+
"skills": [
|
|
147
|
+
"npm:@foo/pi-skills", // Include all skills from package
|
|
148
|
+
"!secret-skill", // Exclude by name
|
|
149
|
+
"+override-skill", // Force-include (overrides exclusions)
|
|
150
|
+
"-unwanted-skill" // Force-exclude (overrides inclusions)
|
|
151
|
+
]
|
|
152
|
+
}
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
## Environment Variables
|
|
156
|
+
|
|
157
|
+
| Variable | Effect |
|
|
158
|
+
|----------|--------|
|
|
159
|
+
| `PI_CODING_AGENT_DIR` | Override global config directory (default: `~/.pi/agent/`) |
|
|
160
|
+
| `PI_OFFLINE` | Disable package updates and tool downloads |
|
|
161
|
+
| `ANTHROPIC_API_KEY` | Anthropic API key |
|
|
162
|
+
| `OPENAI_API_KEY` | OpenAI API key |
|
|
163
|
+
| Additional provider env vars | See `references/providers.md` |
|
|
164
|
+
|
|
165
|
+
## Editing Tips
|
|
166
|
+
|
|
167
|
+
- Use `/settings` in interactive mode for a guided editor
|
|
168
|
+
- Project settings are committed to version control (`.pi/settings.json`) for team sharing
|
|
169
|
+
- Global settings (`~/.pi/agent/settings.json`) are personal
|
|
170
|
+
- Settings reload on next agent start — no restart needed for most changes
|
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
# Skills
|
|
2
|
+
|
|
3
|
+
Skills are self-contained capability packages that Pi's agent loads on demand. They follow the [Agent Skills standard](https://github.com/anthropics/agent-skills).
|
|
4
|
+
|
|
5
|
+
## How Skills Work
|
|
6
|
+
|
|
7
|
+
1. At startup, Pi discovers all skills and loads their **name + description** into the system prompt as XML.
|
|
8
|
+
2. When the agent encounters a task matching a skill's description, it uses the `read` tool to load the full `SKILL.md`.
|
|
9
|
+
3. The skill body contains detailed instructions, and may reference additional files in subdirectories.
|
|
10
|
+
|
|
11
|
+
This progressive disclosure keeps the system prompt lean while making deep knowledge available when needed.
|
|
12
|
+
|
|
13
|
+
## Directory Structure
|
|
14
|
+
|
|
15
|
+
```text
|
|
16
|
+
my-skill/
|
|
17
|
+
├── SKILL.md # Required — frontmatter + instructions
|
|
18
|
+
├── scripts/ # Optional — executable helper scripts
|
|
19
|
+
│ └── build.sh
|
|
20
|
+
├── references/ # Optional — docs loaded into context as needed
|
|
21
|
+
│ └── api-reference.md
|
|
22
|
+
└── assets/ # Optional — templates, icons, fonts
|
|
23
|
+
└── template.html
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
## SKILL.md Format
|
|
27
|
+
|
|
28
|
+
```markdown
|
|
29
|
+
---
|
|
30
|
+
name: my-skill
|
|
31
|
+
description: "What this skill does and when to use it. Be specific about trigger phrases and contexts — Pi tends to under-trigger skills, so make descriptions slightly assertive."
|
|
32
|
+
license: MIT
|
|
33
|
+
compatibility: "Requires bash and node tools"
|
|
34
|
+
---
|
|
35
|
+
|
|
36
|
+
# My Skill
|
|
37
|
+
|
|
38
|
+
Instructions for the agent go here. Write in imperative form.
|
|
39
|
+
Use markdown formatting. Reference supporting files with relative paths.
|
|
40
|
+
|
|
41
|
+
## Step 1: Do the thing
|
|
42
|
+
|
|
43
|
+
Read `references/api-reference.md` for the full API spec, then...
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
## Frontmatter Fields
|
|
47
|
+
|
|
48
|
+
| Field | Required | Constraints | Notes |
|
|
49
|
+
|-------|----------|------------|-------|
|
|
50
|
+
| `name` | Yes | 1–64 chars, lowercase `[a-z0-9-]` | Should match directory name |
|
|
51
|
+
| `description` | Yes | Max 1024 chars | Primary trigger mechanism — include trigger phrases |
|
|
52
|
+
| `license` | No | String | License identifier |
|
|
53
|
+
| `compatibility` | No | String | Tool/dependency requirements |
|
|
54
|
+
| `allowed-tools` | No | List | Restrict which tools the skill can use |
|
|
55
|
+
| `disable-model-invocation` | No | Boolean | If true, agent cannot auto-invoke this skill |
|
|
56
|
+
|
|
57
|
+
## Discovery Locations
|
|
58
|
+
|
|
59
|
+
Skills are discovered from (in priority order — first wins on name collision):
|
|
60
|
+
|
|
61
|
+
1. `.pi/skills/` — project-local
|
|
62
|
+
2. `~/.pi/agent/skills/` — global
|
|
63
|
+
3. Installed packages (via `pi install`)
|
|
64
|
+
4. `settings.json` → `skills` array
|
|
65
|
+
5. `pi --skills <path>` CLI argument
|
|
66
|
+
|
|
67
|
+
Discovery respects `.gitignore`, `.ignore`, and `.fdignore` patterns.
|
|
68
|
+
|
|
69
|
+
## Invocation
|
|
70
|
+
|
|
71
|
+
- **Manual:** User types `/skill:my-skill` in the editor
|
|
72
|
+
- **Automatic:** Agent reads the skill when it matches the task (progressive disclosure)
|
|
73
|
+
- **Disable auto-invoke:** Set `disable-model-invocation: true` in frontmatter
|
|
74
|
+
|
|
75
|
+
## Writing Good Skills
|
|
76
|
+
|
|
77
|
+
### Descriptions
|
|
78
|
+
|
|
79
|
+
The description is the **primary trigger mechanism**. Make it assertive and specific:
|
|
80
|
+
|
|
81
|
+
**Bad:** `"A tool for working with Docker"`
|
|
82
|
+
|
|
83
|
+
**Good:** `"How to build, run, and debug Docker containers and docker-compose setups. Use this skill whenever the user mentions Docker, containers, docker-compose, Dockerfiles, container orchestration, or asks about building/deploying containerized applications."`
|
|
84
|
+
|
|
85
|
+
### Body Structure
|
|
86
|
+
|
|
87
|
+
- Keep SKILL.md under 500 lines. If approaching this limit, split detail into `references/` files with clear pointers.
|
|
88
|
+
- Write in imperative form: "Run the build script" not "You should run the build script."
|
|
89
|
+
- Explain **why** behind instructions so the model can adapt to edge cases.
|
|
90
|
+
- Include concrete examples with input/output pairs.
|
|
91
|
+
- For multi-domain skills, organize by variant in `references/` and let SKILL.md route to the right one.
|
|
92
|
+
|
|
93
|
+
### Reference Files
|
|
94
|
+
|
|
95
|
+
- Reference with relative paths: `Read references/aws.md for AWS-specific steps.`
|
|
96
|
+
- For files over 300 lines, include a table of contents at the top.
|
|
97
|
+
- The model reads these with the `read` tool — they don't go into the system prompt.
|
|
98
|
+
|
|
99
|
+
### Helper Scripts
|
|
100
|
+
|
|
101
|
+
Place in `scripts/`. The model can execute them via the `bash` tool. This avoids the model reinventing the wheel for deterministic operations.
|
|
102
|
+
|
|
103
|
+
## Validation
|
|
104
|
+
|
|
105
|
+
Pi validates skills at load time:
|
|
106
|
+
|
|
107
|
+
- Missing `description` → skill not loaded
|
|
108
|
+
- Name > 64 chars → warning
|
|
109
|
+
- Description > 1024 chars → warning
|
|
110
|
+
- Name-directory mismatch → warning
|
|
111
|
+
- Duplicate names → first discovered wins, warning issued
|