@ai-outfitter/outfitter 0.7.2 → 0.8.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/README.md +4 -2
- package/code/pi-extension/src/outfitter-extension.js +720 -0
- package/dist/agents/AgentAdapter.d.ts +2 -0
- package/dist/agents/AgentLaunch.js +5 -0
- package/dist/agents/AgentLaunch.js.map +1 -1
- package/dist/agents/OutfitterDocs.d.ts +2 -0
- package/dist/agents/OutfitterDocs.js +38 -0
- package/dist/agents/OutfitterDocs.js.map +1 -0
- package/dist/agents/pi/PiAdapter.js +15 -14
- package/dist/agents/pi/PiAdapter.js.map +1 -1
- package/dist/agents/pi/PiSkillSources.d.ts +8 -0
- package/dist/agents/pi/PiSkillSources.js +69 -0
- package/dist/agents/pi/PiSkillSources.js.map +1 -0
- package/dist/cli/OutfitterCli.js +7 -2
- package/dist/cli/OutfitterCli.js.map +1 -1
- package/dist/cli/commands/PiLoginLaunch.js +25 -728
- package/dist/cli/commands/PiLoginLaunch.js.map +1 -1
- package/dist/cli/commands/RunCommand.d.ts +4 -17
- package/dist/cli/commands/RunCommand.js +10 -146
- package/dist/cli/commands/RunCommand.js.map +1 -1
- package/dist/cli/commands/SetupCommand.d.ts +4 -63
- package/dist/cli/commands/SetupCommand.js +13 -673
- package/dist/cli/commands/SetupCommand.js.map +1 -1
- package/dist/cli/commands/run/RunLaunchSummary.d.ts +2 -0
- package/dist/cli/commands/run/RunLaunchSummary.js +35 -0
- package/dist/cli/commands/run/RunLaunchSummary.js.map +1 -0
- package/dist/cli/commands/run/RunProfileResolution.d.ts +37 -0
- package/dist/cli/commands/run/RunProfileResolution.js +115 -0
- package/dist/cli/commands/run/RunProfileResolution.js.map +1 -0
- package/dist/cli/commands/setup/SetupPrompts.d.ts +14 -0
- package/dist/cli/commands/setup/SetupPrompts.js +296 -0
- package/dist/cli/commands/setup/SetupPrompts.js.map +1 -0
- package/dist/cli/commands/setup/SetupSourceImport.d.ts +5 -0
- package/dist/cli/commands/setup/SetupSourceImport.js +177 -0
- package/dist/cli/commands/setup/SetupSourceImport.js.map +1 -0
- package/dist/cli/commands/setup/SetupSourceLaunch.d.ts +4 -0
- package/dist/cli/commands/setup/SetupSourceLaunch.js +65 -0
- package/dist/cli/commands/setup/SetupSourceLaunch.js.map +1 -0
- package/dist/cli/commands/setup/SetupStarterSource.d.ts +21 -0
- package/dist/cli/commands/setup/SetupStarterSource.js +133 -0
- package/dist/cli/commands/setup/SetupStarterSource.js.map +1 -0
- package/dist/cli/commands/setup/SetupTypes.d.ts +91 -0
- package/dist/cli/commands/setup/SetupTypes.js +26 -0
- package/dist/cli/commands/setup/SetupTypes.js.map +1 -0
- package/doc/architecture/state_writeback_strategy.md +350 -0
- package/doc/documentation/README.md +21 -0
- package/doc/documentation/cli.md +74 -0
- package/doc/documentation/concepts.md +54 -0
- package/doc/documentation/first-time-cli-agent-users.md +137 -0
- package/doc/documentation/getting-started.md +49 -0
- package/doc/documentation/iterating-on-profiles.md +109 -0
- package/doc/documentation/profile-repository.md +111 -0
- package/doc/documentation/profiles.md +183 -0
- package/doc/documentation/state.md +204 -0
- package/doc/documentation/support-matrix.md +46 -0
- package/doc/documentation/switching-to-outfitter.md +130 -0
- package/doc/documentation/usecases/engineering.md +114 -0
- package/doc/documentation/usecases/organization-profile-catalog.md +140 -0
- package/doc/documentation/usecases/persona-reviews.md +173 -0
- package/doc/philosophy.md +25 -0
- package/package.json +3 -2
|
@@ -0,0 +1,183 @@
|
|
|
1
|
+
# Profiles
|
|
2
|
+
|
|
3
|
+
Profiles define the accoutrements that shape an Outfitter-managed agent launch.
|
|
4
|
+
|
|
5
|
+
A profile can compose:
|
|
6
|
+
|
|
7
|
+
- context and prompts
|
|
8
|
+
- model and provider settings
|
|
9
|
+
- Pi extensions
|
|
10
|
+
- skills
|
|
11
|
+
- subagents
|
|
12
|
+
- DeepWork workflows
|
|
13
|
+
- agent-specific CLI flags and environment variables
|
|
14
|
+
|
|
15
|
+
Profiles can be local to a user or project, inherited from other profiles, or loaded from a shared profile repository. See [Profile repositories](./profile-repository.md) for shared setup sources.
|
|
16
|
+
|
|
17
|
+
## Profile layouts
|
|
18
|
+
|
|
19
|
+
Outfitter supports two profile layouts inside any configured `profile_sources` directory.
|
|
20
|
+
|
|
21
|
+
### Flat profile layout
|
|
22
|
+
|
|
23
|
+
Use the flat layout for small profile catalogs where each profile is mostly YAML and does not need its own resource folder. Each `*.yml` or `*.yaml` file directly under the profile source is a profile. If the file omits `id`, Outfitter uses the filename stem as the profile id.
|
|
24
|
+
|
|
25
|
+
```text
|
|
26
|
+
~/.outfitter/profiles/
|
|
27
|
+
founder.yml
|
|
28
|
+
engineer.yml
|
|
29
|
+
data-analyst.yaml
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
```yaml
|
|
33
|
+
# ~/.outfitter/profiles/founder.yml
|
|
34
|
+
label: Founder
|
|
35
|
+
description: Founder-operator defaults for product, engineering, research, and prose.
|
|
36
|
+
controls:
|
|
37
|
+
append_system_prompt: |
|
|
38
|
+
Think like a founder-operator: connect product judgment, implementation, and evidence.
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
Flat profiles are easy to scan, diff, and copy between setup repositories. Generated Pi prompt exports for flat profiles are written beside the flat file as `<profile-id>.generated-system-prompt.md` when `profile_export` is enabled.
|
|
42
|
+
|
|
43
|
+
### Directory profile layout
|
|
44
|
+
|
|
45
|
+
The original layout is one folder per profile with a required `profile.yml`. Use it when a profile owns prompts, skills, extensions, DeepWork jobs, or CLI-specific files that should travel with that profile.
|
|
46
|
+
|
|
47
|
+
```text
|
|
48
|
+
~/.outfitter/profiles/
|
|
49
|
+
home-default/
|
|
50
|
+
profile.yml
|
|
51
|
+
prompts/
|
|
52
|
+
system.md
|
|
53
|
+
skills/
|
|
54
|
+
extensions/
|
|
55
|
+
deepwork/
|
|
56
|
+
jobs/
|
|
57
|
+
cli_specific/
|
|
58
|
+
pi/
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
```yaml
|
|
62
|
+
# ~/.outfitter/profiles/home-default/profile.yml
|
|
63
|
+
id: home-default
|
|
64
|
+
label: Home Default
|
|
65
|
+
controls:
|
|
66
|
+
system_prompt: ./prompts/system.md
|
|
67
|
+
skills:
|
|
68
|
+
- ./skills/review
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
Directory profiles keep bundled resources close to the profile that references them. Generated Pi prompt exports for directory profiles are written as `generated-system-prompt.md` inside the profile directory when `profile_export` is enabled.
|
|
72
|
+
|
|
73
|
+
## Home and project example
|
|
74
|
+
|
|
75
|
+
A home profile SHOULD hold reusable defaults for one developer.
|
|
76
|
+
A project profile SHOULD live with the repository and add only the behavior that project needs.
|
|
77
|
+
The comments below name the files; each `---` starts a separate YAML document in the same example block.
|
|
78
|
+
|
|
79
|
+
```yaml
|
|
80
|
+
# ~/.outfitter/settings.yml
|
|
81
|
+
default_profile: home-default
|
|
82
|
+
default_agent: pi
|
|
83
|
+
profile_sources:
|
|
84
|
+
- path: ./profiles
|
|
85
|
+
|
|
86
|
+
---
|
|
87
|
+
# ~/.outfitter/profiles/home-default.yml
|
|
88
|
+
id: home-default
|
|
89
|
+
label: Home Default
|
|
90
|
+
description: Reusable personal defaults for Outfitter-managed Pi runs.
|
|
91
|
+
controls:
|
|
92
|
+
provider: openai-codex
|
|
93
|
+
model: gpt-5.5
|
|
94
|
+
thinking: high
|
|
95
|
+
append_system_prompt:
|
|
96
|
+
- |
|
|
97
|
+
Use concise, evidence-backed engineering prose.
|
|
98
|
+
Prefer small, reviewable changes.
|
|
99
|
+
Keep durable decisions in repo files.
|
|
100
|
+
- file: prompts/personal-policy.md
|
|
101
|
+
- repo_file: docs/mission.md
|
|
102
|
+
|
|
103
|
+
---
|
|
104
|
+
# ~/repos/acme/example/.outfitter/settings.yml
|
|
105
|
+
default_profile: acme-example
|
|
106
|
+
profile_export: true
|
|
107
|
+
profile_sources:
|
|
108
|
+
# Relative to this settings.yml; exposes ~/.outfitter/profiles to the project.
|
|
109
|
+
- path: ../../../../.outfitter/profiles
|
|
110
|
+
only:
|
|
111
|
+
- home-default
|
|
112
|
+
- path: ./profiles
|
|
113
|
+
|
|
114
|
+
---
|
|
115
|
+
# ~/repos/acme/example/.outfitter/profiles/acme-example/profile.yml
|
|
116
|
+
id: acme-example
|
|
117
|
+
label: Acme Example
|
|
118
|
+
description: Checked-in project profile for ~/repos/acme/example.
|
|
119
|
+
inherits:
|
|
120
|
+
- home-default
|
|
121
|
+
controls:
|
|
122
|
+
thinking: xhigh
|
|
123
|
+
append_system_prompt:
|
|
124
|
+
- |
|
|
125
|
+
You are working in ~/repos/acme/example.
|
|
126
|
+
Honor the project test contract before calling work complete.
|
|
127
|
+
Prefer repository-local conventions over personal defaults.
|
|
128
|
+
- file: .outfitter/prompts/review-policy.md
|
|
129
|
+
environment:
|
|
130
|
+
ACME_PROJECT: example
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
`home-default` is the home-folder profile: it supplies personal defaults that can work across repositories.
|
|
134
|
+
`acme-example` is the project profile: it inherits those defaults, then overrides the thinking level and adds project-specific prompt and environment settings.
|
|
135
|
+
When a project `settings.yml` declares `profile_sources`, it SHOULD include any home profile source that project profiles inherit from.
|
|
136
|
+
Because `append_system_prompt` composes instead of replacing, the higher-precedence project prompt is passed first and the inherited home prompt follows.
|
|
137
|
+
Typed prompt includes read `{ file: string }` entries before launch and pass the file contents as repeated append-prompt text. Raw strings remain literal prompt text; if a raw string looks like a whole file path, Outfitter warns so the profile can be migrated to `{ file: ... }`.
|
|
138
|
+
|
|
139
|
+
### Append prompt file includes
|
|
140
|
+
|
|
141
|
+
`append_system_prompt` accepts a literal string, a multiline string, `{ file: string }`, `{ repo_file: string }`, or an ordered list mixing those entry types. Outfitter does not support `{ text: ... }`; use raw YAML strings for inline prompt text, `{ file: ... }` for maintained profile/catalog files, and `{ repo_file: ... }` for files that should come from the active project.
|
|
142
|
+
|
|
143
|
+
Profile-owned file includes resolve from the source root of the profile layer that declares the entry, including inherited layers:
|
|
144
|
+
|
|
145
|
+
| Declaring profile location | Include root |
|
|
146
|
+
| ---------------------------------------------------------------------------------- | -------------------------- |
|
|
147
|
+
| `~/.outfitter/profiles/<id>/profile.yml` or `~/.outfitter/profiles/<id>.yml` | `~/.outfitter` |
|
|
148
|
+
| `<project>/.outfitter/profiles/<id>/profile.yml` | `<project>` |
|
|
149
|
+
| Catalog repo `outfitter/profiles/<id>/profile.yml` | Catalog repository root |
|
|
150
|
+
| Explicit `profile_sources[].path` without `.outfitter/` or `outfitter/` convention | The configured source path |
|
|
151
|
+
|
|
152
|
+
`repo_file:` resolves from the active project directory where Outfitter launches the agent. This lets a reusable catalog or home profile request project-local governance context such as `docs/mission.md` without copying those docs into the catalog.
|
|
153
|
+
|
|
154
|
+
Run `outfitter profile lint` to report schema and inheritance errors, missing typed include files, and raw string append-prompt entries that look like file paths. Add `--strict` to exit non-zero for warnings, and `--json` for machine-readable diagnostics.
|
|
155
|
+
|
|
156
|
+
With `profile_export: true`, the selected project directory profile can write `generated-system-prompt.md` beside `profile.yml`.
|
|
157
|
+
For this example, the generated prompt fallback would show the composed prompt inputs like this:
|
|
158
|
+
|
|
159
|
+
```text
|
|
160
|
+
<!-- Generated by Outfitter from Pi runtime ctx.getSystemPrompt(). Safe to review or git-ignore. Do not edit by hand. -->
|
|
161
|
+
# Generated Pi runtime system prompt
|
|
162
|
+
|
|
163
|
+
You are an expert coding assistant operating inside pi, a coding agent harness. You help users by reading files, executing commands, editing code, and writing new files.
|
|
164
|
+
|
|
165
|
+
Available tools:
|
|
166
|
+
- read: Read file contents
|
|
167
|
+
- bash: Execute bash commands (ls, grep, find, etc.)
|
|
168
|
+
- edit: Make precise file edits with exact text replacement, including multiple disjoint edits in one call
|
|
169
|
+
|
|
170
|
+
....
|
|
171
|
+
|
|
172
|
+
## append_system_prompt[0]
|
|
173
|
+
|
|
174
|
+
You are working in ~/repos/acme/example.
|
|
175
|
+
Honor the project test contract before calling work complete.
|
|
176
|
+
Prefer repository-local conventions over personal defaults.
|
|
177
|
+
|
|
178
|
+
## append_system_prompt[1]
|
|
179
|
+
|
|
180
|
+
Use concise, evidence-backed engineering prose.
|
|
181
|
+
Prefer small, reviewable changes.
|
|
182
|
+
Keep durable decisions in repo files.
|
|
183
|
+
```
|
|
@@ -0,0 +1,204 @@
|
|
|
1
|
+
# State persistence
|
|
2
|
+
|
|
3
|
+
Outfitter launches agent CLIs from a temporary composite profile. During a run, Pi, Claude Code, or another adapter may write state such as settings, sessions, plugin installs, caches, auth metadata, or MCP configuration.
|
|
4
|
+
|
|
5
|
+
Outfitter does not silently copy every file back into your profiles. Instead, each adapter declares the state paths it understands, chooses safe defaults, and lets profiles override how writes to those paths are handled.
|
|
6
|
+
|
|
7
|
+
## Default behavior
|
|
8
|
+
|
|
9
|
+
Most users do not need to configure `state_persistence` at all. By default, Outfitter keeps known agent CLI state durable and reports unexpected writes.
|
|
10
|
+
|
|
11
|
+
```yaml
|
|
12
|
+
# This is the behavior most users get without writing any state_persistence block.
|
|
13
|
+
# Known Pi and Claude Code state paths default to symlink, so normal setup survives.
|
|
14
|
+
# Unknown writes default to warn, so surprising files are reported instead of silently persisted.
|
|
15
|
+
state_persistence:
|
|
16
|
+
auth.json: symlink # Pi login/auth state survives future runs.
|
|
17
|
+
settings.json: symlink # Native CLI settings stay durable.
|
|
18
|
+
mcp.json: symlink # MCP/server configuration stays durable.
|
|
19
|
+
plugins/: symlink # Installed plugins can be reused.
|
|
20
|
+
cache/: symlink # Useful package/cache state can be reused.
|
|
21
|
+
sessions/: symlink # Session/project state is durable unless a profile overrides it.
|
|
22
|
+
unknown: warn # Unexpected writes are visible and not silently copied into a profile.
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
Some generated Pi runtime files, such as transformed settings or keybindings, may be treated as one-run generated files even though the underlying state path normally defaults to `symlink`. This keeps Outfitter-managed launch reconciliation from becoming accidental user state.
|
|
26
|
+
|
|
27
|
+
## How state works
|
|
28
|
+
|
|
29
|
+
Outfitter separates runtime files into three groups:
|
|
30
|
+
|
|
31
|
+
1. **Generated profile files** — files Outfitter builds from settings, profiles, templates, and adapter rules. These are temporary and reproducible.
|
|
32
|
+
2. **Declared state paths** — files or directories the selected agent CLI is expected to read or write, such as `settings.json`, `mcp.json`, `plugins/`, or `sessions/`.
|
|
33
|
+
3. **Unknown writes** — anything the agent writes outside declared state paths. Outfitter never silently persists these because it does not know their owner or merge rules.
|
|
34
|
+
|
|
35
|
+
Only declared state paths can be persisted automatically.
|
|
36
|
+
|
|
37
|
+
## Profile option
|
|
38
|
+
|
|
39
|
+
Use `state_persistence` in a profile to override adapter defaults:
|
|
40
|
+
|
|
41
|
+
```yaml
|
|
42
|
+
id: strict-ci
|
|
43
|
+
label: Strict CI
|
|
44
|
+
|
|
45
|
+
# Omitted paths use the selected adapter's default strategy.
|
|
46
|
+
# This profile only overrides paths where CI should be stricter than normal.
|
|
47
|
+
state_persistence:
|
|
48
|
+
settings.json: error # Fail if the agent changes settings during the run.
|
|
49
|
+
mcp.json: error # Fail if tool/server config changes during the run.
|
|
50
|
+
plugins/: error # Fail if plugin state changes during the run.
|
|
51
|
+
unknown: error # Fail if the agent writes an undeclared file.
|
|
52
|
+
|
|
53
|
+
controls:
|
|
54
|
+
thinking: high
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
## Strategies
|
|
58
|
+
|
|
59
|
+
`state_persistence` values can be:
|
|
60
|
+
|
|
61
|
+
```yaml
|
|
62
|
+
state_persistence:
|
|
63
|
+
auth.json: symlink # Persist writes through a durable profile-managed or native CLI path.
|
|
64
|
+
cache/: discard # Allow writes, then throw them away when the run ends.
|
|
65
|
+
plugins/: warn # Allow writes, discard them, and report them after the run.
|
|
66
|
+
settings.json: error # Allow the run, then fail if this path changed.
|
|
67
|
+
mcp.json: prompt # Reserved for future interactive handling; currently diagnostic where allowed.
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
Use `symlink` for state you want to keep, such as login state, durable settings, MCP config, or plugin installs. Use `discard`, `warn`, or `error` for state that should not become part of the durable profile.
|
|
71
|
+
|
|
72
|
+
## User stories
|
|
73
|
+
|
|
74
|
+
### Keep login working
|
|
75
|
+
|
|
76
|
+
```yaml
|
|
77
|
+
# Story: A developer connects Pi to a model provider during first-run setup.
|
|
78
|
+
# Goal: The next `outfitter` launch remembers the login instead of asking again.
|
|
79
|
+
state_persistence:
|
|
80
|
+
auth.json: symlink # Keep provider login/auth metadata durable.
|
|
81
|
+
models.json: symlink # Keep discovered/configured model metadata durable.
|
|
82
|
+
```
|
|
83
|
+
|
|
84
|
+
### Keep shared catalogs clean
|
|
85
|
+
|
|
86
|
+
```yaml
|
|
87
|
+
# Story: A team publishes a shared engineering profile catalog.
|
|
88
|
+
# Goal: MCP config can come from the catalog, but one user's random runtime files
|
|
89
|
+
# should not become shared team state.
|
|
90
|
+
state_persistence:
|
|
91
|
+
mcp.json: symlink # Keep intentional tool/server config durable.
|
|
92
|
+
unknown: warn # Report unexpected writes instead of silently sharing them.
|
|
93
|
+
```
|
|
94
|
+
|
|
95
|
+
### Make CI reproducible
|
|
96
|
+
|
|
97
|
+
```yaml
|
|
98
|
+
# Story: A platform engineer runs an Outfitter profile in CI.
|
|
99
|
+
# Goal: CI should prove the profile is complete, not depend on hidden runtime mutation.
|
|
100
|
+
state_persistence:
|
|
101
|
+
settings.json: error # Settings drift means the profile is incomplete.
|
|
102
|
+
mcp.json: error # Tool config drift should fail the job.
|
|
103
|
+
plugins/: error # Plugin installs/updates should be explicit in the profile.
|
|
104
|
+
unknown: error # Any undeclared write is a reproducibility problem.
|
|
105
|
+
```
|
|
106
|
+
|
|
107
|
+
### Avoid cross-project leakage
|
|
108
|
+
|
|
109
|
+
```yaml
|
|
110
|
+
# Story: A consultant switches between client repositories.
|
|
111
|
+
# Goal: Sessions, caches, and temp files from one client should not show up in another.
|
|
112
|
+
state_persistence:
|
|
113
|
+
sessions/: discard # Throw away conversation/session state after the run.
|
|
114
|
+
cache/: discard # Throw away cache data tied to this run.
|
|
115
|
+
tmp/: discard # Throw away temporary runtime artifacts.
|
|
116
|
+
unknown: warn # Still report surprising writes for investigation.
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
### Experiment without losing visibility
|
|
120
|
+
|
|
121
|
+
```yaml
|
|
122
|
+
# Story: An engineer tries new plugins or package installs locally.
|
|
123
|
+
# Goal: Let the experiment run, but report what changed so the user can decide
|
|
124
|
+
# whether to make it durable later.
|
|
125
|
+
state_persistence:
|
|
126
|
+
plugins/: warn # Allow plugin changes, but do not persist silently.
|
|
127
|
+
unknown: warn # Surface other writes that may need a policy.
|
|
128
|
+
```
|
|
129
|
+
|
|
130
|
+
## Pi state paths
|
|
131
|
+
|
|
132
|
+
The Pi adapter declares these paths:
|
|
133
|
+
|
|
134
|
+
```yaml
|
|
135
|
+
state_persistence:
|
|
136
|
+
auth.json: symlink # Login/auth state; allowed: symlink, error, prompt.
|
|
137
|
+
settings.json: symlink # Pi settings; generated launch transforms may be one-run.
|
|
138
|
+
keybindings.json: symlink # Pi keybindings; Outfitter may generate launch keybindings.
|
|
139
|
+
mcp.json: symlink # MCP/server configuration.
|
|
140
|
+
models.json: symlink # Model/provider metadata.
|
|
141
|
+
trust.json: symlink # Pi trust decisions.
|
|
142
|
+
plugins/: symlink # Pi plugins.
|
|
143
|
+
cache/: symlink # Pi cache data.
|
|
144
|
+
sessions/: symlink # Pi sessions.
|
|
145
|
+
npm/: symlink # Pi npm package installs.
|
|
146
|
+
git/: symlink # Pi git package checkouts.
|
|
147
|
+
tmp/: symlink # Pi temporary runtime tree; allowed: symlink, discard.
|
|
148
|
+
utilities/: symlink # Shared utility binaries such as rg/fd.
|
|
149
|
+
bin/: symlink # Utility binary links.
|
|
150
|
+
unknown: warn # Undeclared writes; allowed: discard, warn, error, prompt.
|
|
151
|
+
```
|
|
152
|
+
|
|
153
|
+
## Claude Code state paths
|
|
154
|
+
|
|
155
|
+
The Claude Code adapter declares these paths:
|
|
156
|
+
|
|
157
|
+
```yaml
|
|
158
|
+
state_persistence:
|
|
159
|
+
settings.json: symlink # Claude Code settings.
|
|
160
|
+
agents/: symlink # Claude agent definitions.
|
|
161
|
+
skills/: symlink # Claude skills.
|
|
162
|
+
commands/: symlink # Claude commands/prompts.
|
|
163
|
+
plugins/: symlink # Claude plugins.
|
|
164
|
+
projects/: symlink # Claude project/session state.
|
|
165
|
+
debug/: symlink # Claude debug state.
|
|
166
|
+
unknown: warn # Undeclared writes; allowed: discard, warn, error, prompt.
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
Claude Code project/session state is represented through `projects/`. If a profile sets `controls.session_directory` or `controls.claude.session_directory`, Outfitter uses that location for Claude project state.
|
|
170
|
+
|
|
171
|
+
## Where durable state lives
|
|
172
|
+
|
|
173
|
+
When a path uses `symlink`, Outfitter looks for a matching file or directory under the selected profile's CLI-specific resources:
|
|
174
|
+
|
|
175
|
+
```text
|
|
176
|
+
profiles/
|
|
177
|
+
default/
|
|
178
|
+
profile.yml
|
|
179
|
+
cli_specific/
|
|
180
|
+
pi/
|
|
181
|
+
settings.json
|
|
182
|
+
mcp.json
|
|
183
|
+
claude/
|
|
184
|
+
settings.json
|
|
185
|
+
skills/
|
|
186
|
+
```
|
|
187
|
+
|
|
188
|
+
If no profile-managed source exists, Outfitter falls back to the native CLI state location for most paths, such as `~/.pi/agent/...` for Pi or `~/.claude/...` for Claude Code.
|
|
189
|
+
|
|
190
|
+
This fallback is not another profile layer. It does not participate in inheritance, merge precedence, or profile controls; it only provides a durable destination for state paths.
|
|
191
|
+
|
|
192
|
+
## When to change defaults
|
|
193
|
+
|
|
194
|
+
Most users can keep the adapter defaults. Override `state_persistence` when you need a profile with a specific state policy:
|
|
195
|
+
|
|
196
|
+
```yaml
|
|
197
|
+
state_persistence:
|
|
198
|
+
cache/: discard # Throwaway demos, sessions, or caches.
|
|
199
|
+
plugins/: warn # Local experimentation is okay but should be visible.
|
|
200
|
+
settings.json: error # CI, reproducibility checks, or locked-down project profiles.
|
|
201
|
+
auth.json: symlink # Intentional durable setup.
|
|
202
|
+
```
|
|
203
|
+
|
|
204
|
+
For the complete adapter contract and rationale, see [State writeback strategy](../architecture/state_writeback_strategy.md).
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
# Adapter support matrix
|
|
2
|
+
|
|
3
|
+
What Outfitter can control per agent CLI today. Pi is the primary and most complete adapter; Claude Code is supported with gaps.
|
|
4
|
+
|
|
5
|
+
Status values:
|
|
6
|
+
|
|
7
|
+
- **Supported** — Outfitter translates this concept for the CLI through at least one native mechanism.
|
|
8
|
+
- **Partial** — some of the concept works today, with documented gaps.
|
|
9
|
+
- **Roadmap** — the CLI appears to support the concept, but Outfitter does not translate it yet.
|
|
10
|
+
|
|
11
|
+
When a profile requests a control an adapter cannot translate, Outfitter warns to stderr; `--strict` makes those warnings fatal.
|
|
12
|
+
|
|
13
|
+
| What you can control | Pi | Claude Code |
|
|
14
|
+
| ------------------------------------------------- | --------- | ----------- |
|
|
15
|
+
| Agent config directory | Supported | Supported |
|
|
16
|
+
| Session directory (`session_directory`) | Supported | Supported |
|
|
17
|
+
| Extensions / plugins (`extensions`) | Supported | Supported |
|
|
18
|
+
| Skills (`skills`) | Supported | Partial |
|
|
19
|
+
| Prompt templates / commands (`prompt_template`) | Supported | Partial |
|
|
20
|
+
| System prompt (`system_prompt`) | Supported | Supported |
|
|
21
|
+
| Appended system prompt (`append_system_prompt`) | Supported | Supported |
|
|
22
|
+
| Model selection (`model`, `provider`, `thinking`) | Supported | Partial |
|
|
23
|
+
| Credentials and environment (`environment`) | Supported | Supported |
|
|
24
|
+
| Tool availability | Roadmap | Roadmap |
|
|
25
|
+
| Context files | Roadmap | Roadmap |
|
|
26
|
+
| Theme / UI presentation | Roadmap | Roadmap |
|
|
27
|
+
| Project override policy | Roadmap | Roadmap |
|
|
28
|
+
| Working directory | Roadmap | Roadmap |
|
|
29
|
+
| Pass-through arguments | Supported | Supported |
|
|
30
|
+
| Bootstrap hook | Supported | Roadmap |
|
|
31
|
+
|
|
32
|
+
## Claude Code notes
|
|
33
|
+
|
|
34
|
+
- **Config and session state** — Outfitter points `CLAUDE_CONFIG_DIR` at the composite profile, declares Claude state paths (`settings.json`, `agents/`, `skills/`, `commands/`, `plugins/`, `projects/`) for persistence, and lets `session_directory` choose where `projects/` session state is symlinked from. There is no standalone session-dir flag.
|
|
35
|
+
- **Skills (Partial)** — native Claude skills work when a profile ships them as `cli_specific/claude/skills/` directories, which Outfitter places in the profiled config directory. The generic `controls.skills` selector is not translated for Claude and warns if requested.
|
|
36
|
+
- **Prompt templates (Partial)** — same shape: native `cli_specific/claude/commands/` directories work, but the generic `controls.prompt_template` selector is not translated and warns.
|
|
37
|
+
- **Model selection (Partial)** — `model` maps to `--model` and `thinking` maps to `--effort`, but `provider` is not translated for Claude and warns if requested.
|
|
38
|
+
- **Extensions** — `controls.extensions` entries are passed as repeated `--plugin-dir` flags.
|
|
39
|
+
- **DeepWork jobs** — the `controls.deepwork` selection is Pi-only today and warns on Claude.
|
|
40
|
+
|
|
41
|
+
## Pi notes
|
|
42
|
+
|
|
43
|
+
- Pi translates the full generic control set: `provider`, `model`, `thinking`, `system_prompt`, `append_system_prompt`, `extensions` (`--extension`), `skills` (`--skill`), `prompt_template` (`--prompt-template`), `environment`, `args`, `session_directory`, and DeepWork job selection.
|
|
44
|
+
- Bootstrap behavior (for example the onboarding flow) uses an explicit Pi bootstrap extension via `--extension`.
|
|
45
|
+
|
|
46
|
+
For the architecture-level definitions behind each row, see [Controllable elements](../architecture/controllable-elements.md).
|
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
# Switching to Outfitter
|
|
2
|
+
|
|
3
|
+
This guide is for people who already use Pi, Claude Code, Codex, Cursor, or another agent CLI and want Outfitter to make that setup repeatable. The goal is not to copy every local experiment into a profile. The goal is to capture the small set of habits that reliably jumpstart the human.
|
|
4
|
+
|
|
5
|
+
## Migration shape
|
|
6
|
+
|
|
7
|
+
1. Keep the current agent CLI installed and working.
|
|
8
|
+
2. Identify the behavior you rely on every week: prompts, planning rules, permission posture, skills, subagents, and state you want preserved.
|
|
9
|
+
3. Create one Outfitter home profile for stable personal defaults.
|
|
10
|
+
4. Add project overlays only where a repository needs different instructions or tools.
|
|
11
|
+
5. Run `outfitter`, compare the session to your old workflow, and tighten the profile before adding more controls.
|
|
12
|
+
|
|
13
|
+
## What to migrate first
|
|
14
|
+
|
|
15
|
+
Migrate durable operating rules before migrating files:
|
|
16
|
+
|
|
17
|
+
- how much autonomy the agent gets;
|
|
18
|
+
- when it must plan before editing;
|
|
19
|
+
- how it should use subagents;
|
|
20
|
+
- what review or test evidence you expect;
|
|
21
|
+
- what writing voice or product judgment it should preserve;
|
|
22
|
+
- which skills/extensions are essential.
|
|
23
|
+
|
|
24
|
+
Leave transient chat tricks behind. If a rule is not worth committing to a profile, it probably belongs in the next prompt, not the baseline.
|
|
25
|
+
|
|
26
|
+
## Home profile template
|
|
27
|
+
|
|
28
|
+
Use this as a commented migration worksheet. The comments are intentionally user-facing: they encode the human jumpstart idea and the writing nucleation seed that should make a fresh session feel like your best existing setup.
|
|
29
|
+
|
|
30
|
+
```yaml
|
|
31
|
+
# ~/.outfitter/settings.yml
|
|
32
|
+
# Human jumpstart: this default profile should make `outfitter` feel like
|
|
33
|
+
# your current best agent setup, but with fewer manual launch steps.
|
|
34
|
+
default_profile: migrated-agent-workbench
|
|
35
|
+
default_agent: pi
|
|
36
|
+
profile_sources:
|
|
37
|
+
- path: ./profiles
|
|
38
|
+
|
|
39
|
+
---
|
|
40
|
+
# ~/.outfitter/profiles/migrated-agent-workbench/profile.yml
|
|
41
|
+
id: migrated-agent-workbench
|
|
42
|
+
label: Migrated Agent Workbench
|
|
43
|
+
# Name the workflow this replaces: "Claude Code defaults", "Codex review mode", etc.
|
|
44
|
+
description: Personal agent-CLI habits migrated into an Outfitter-managed Pi profile.
|
|
45
|
+
|
|
46
|
+
controls:
|
|
47
|
+
# YOLO posture: grant routine local autonomy while keeping irreversible work gated.
|
|
48
|
+
append_system_prompt: |
|
|
49
|
+
You may inspect files, make focused edits, and run local validation commands.
|
|
50
|
+
Ask before deleting files, changing dependencies, pushing, publishing, touching credentials,
|
|
51
|
+
mutating production data, or making irreversible external changes.
|
|
52
|
+
|
|
53
|
+
Plan before broad rewrites. Use acceptance criteria that can be checked from repo state.
|
|
54
|
+
Prefer small commits and explain validation evidence before calling work done.
|
|
55
|
+
|
|
56
|
+
Writing nucleation: treat rough notes as source material, not final requirements.
|
|
57
|
+
Convert ambiguous requests into a short plan, preserve interesting claims, and remove filler.
|
|
58
|
+
|
|
59
|
+
# Keep controls minimal during migration. Add model/thinking/tool settings only when
|
|
60
|
+
# they represent a stable preference rather than a one-off experiment.
|
|
61
|
+
thinking: high
|
|
62
|
+
|
|
63
|
+
# Skills can come from Pi packages, the Outfitter default profile catalog, or project profiles.
|
|
64
|
+
# Add only skills you expect to use repeatedly.
|
|
65
|
+
skills: []
|
|
66
|
+
|
|
67
|
+
# Subagents may be provided by the active Pi/Outfitter profile or project config.
|
|
68
|
+
# Document how you want the lead agent to use them even before adding custom definitions.
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
## Project overlay template
|
|
72
|
+
|
|
73
|
+
Use a project overlay when a repository has instructions that should not leak into every session.
|
|
74
|
+
|
|
75
|
+
```yaml
|
|
76
|
+
# <repo>/.outfitter/settings.yml
|
|
77
|
+
# Project jumpstart: select the repo-specific profile when `outfitter` starts here.
|
|
78
|
+
default_profile: project-workbench
|
|
79
|
+
profile_sources:
|
|
80
|
+
# Import the home profile this project inherits from.
|
|
81
|
+
# Adjust the relative path to match the repo's depth under your home directory.
|
|
82
|
+
- path: ../../.outfitter/profiles
|
|
83
|
+
only:
|
|
84
|
+
- migrated-agent-workbench
|
|
85
|
+
- path: ./profiles
|
|
86
|
+
|
|
87
|
+
---
|
|
88
|
+
# <repo>/.outfitter/profiles/project-workbench/profile.yml
|
|
89
|
+
id: project-workbench
|
|
90
|
+
label: Project Workbench
|
|
91
|
+
inherits:
|
|
92
|
+
- migrated-agent-workbench
|
|
93
|
+
controls:
|
|
94
|
+
append_system_prompt: |
|
|
95
|
+
Use this repository's docs, tests, and issue tracker as the source of truth.
|
|
96
|
+
Record durable decisions in project files, not only in chat.
|
|
97
|
+
Run the narrowest relevant validation before broad checks.
|
|
98
|
+
```
|
|
99
|
+
|
|
100
|
+
## Mapping old habits to Outfitter
|
|
101
|
+
|
|
102
|
+
| Existing habit | Outfitter/Pi shape |
|
|
103
|
+
| ------------------------------------ | -------------------------------------------------------------------------------------------------------- |
|
|
104
|
+
| “Always plan before edits.” | Use the plan extension keybinding (`Shift+Tab` in the default Outfitter Pi setup) before implementation. |
|
|
105
|
+
| “Use YOLO except dangerous actions.” | State allowed local actions and approval gates in the profile. |
|
|
106
|
+
| “Run code review after changes.” | Add or enable a review skill, then invoke it inside Pi with a slash command such as `/skill:review`. |
|
|
107
|
+
| “Spawn a second agent for research.” | Add subagent guidance and use available subagent definitions when active. |
|
|
108
|
+
| “Use browser or GitHub helpers.” | Load the Pi extension/tool package through the profile that needs it. |
|
|
109
|
+
| “Keep project context durable.” | Commit project instructions to `AGENTS.md`; keep personal defaults in the Outfitter home profile. |
|
|
110
|
+
| “Keep a project-specific prompt.” | Add a project overlay that inherits the home profile. |
|
|
111
|
+
|
|
112
|
+
## Check the active capabilities
|
|
113
|
+
|
|
114
|
+
Because tools differ by CLI and profile, start migrated sessions with:
|
|
115
|
+
|
|
116
|
+
```text
|
|
117
|
+
List the active tools, skills, extensions, and subagents. Note which are vanilla Pi, which come from Outfitter's default profile catalog, and which are project-local. Also read AGENTS.md if this repo has one.
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
If a capability only exists because a Pi extension is active, document that in the profile or project README. If a behavior is a project rule rather than a personal preference, put it in `AGENTS.md` so every agent session can inherit it.
|
|
121
|
+
|
|
122
|
+
## Migration checkpoint
|
|
123
|
+
|
|
124
|
+
Run:
|
|
125
|
+
|
|
126
|
+
```bash
|
|
127
|
+
outfitter
|
|
128
|
+
```
|
|
129
|
+
|
|
130
|
+
If the first session does not feel like a better version of your old setup, edit the prompt seed before adding more files. The first win is reliable launch plus useful starting context; broader profile catalogs can come after that baseline holds.
|
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
# Engineering Profile Catalog
|
|
2
|
+
|
|
3
|
+
An engineering profile catalog is a shared setup source for people who write code, review changes, operate infrastructure, and debug production-like systems. It gives engineers a reliable default Pi session without asking each teammate to rebuild the same model, thinking, prompt, skill, and extension choices by hand.
|
|
4
|
+
|
|
5
|
+
For example, `acme-engineering-outfitter` can publish a small catalog with profiles for day-to-day implementation, deeper platform work, and lightweight review or triage.
|
|
6
|
+
|
|
7
|
+
```text
|
|
8
|
+
acme-engineering-outfitter/
|
|
9
|
+
settings.yml
|
|
10
|
+
profiles/
|
|
11
|
+
base-engineering/
|
|
12
|
+
profile.yml
|
|
13
|
+
engineer/
|
|
14
|
+
profile.yml
|
|
15
|
+
platform-engineer/
|
|
16
|
+
profile.yml
|
|
17
|
+
reviewer/
|
|
18
|
+
profile.yml
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
## Catalog settings
|
|
22
|
+
|
|
23
|
+
```yaml
|
|
24
|
+
# acme-engineering-outfitter/settings.yml
|
|
25
|
+
profile_sources:
|
|
26
|
+
- path: ./profiles
|
|
27
|
+
only:
|
|
28
|
+
- engineer
|
|
29
|
+
- platform-engineer
|
|
30
|
+
- reviewer
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
## Shared base profile
|
|
34
|
+
|
|
35
|
+
```yaml
|
|
36
|
+
# profiles/base-engineering/profile.yml
|
|
37
|
+
id: base-engineering
|
|
38
|
+
label: Engineering Base
|
|
39
|
+
template: true
|
|
40
|
+
description: Shared engineering operating rules for code, tests, and infrastructure.
|
|
41
|
+
controls:
|
|
42
|
+
append_system_prompt: |
|
|
43
|
+
Work as a careful engineering agent. Read the relevant code before editing,
|
|
44
|
+
prefer small reversible changes, keep secrets out of logs, run focused tests,
|
|
45
|
+
and return changed files plus verification evidence.
|
|
46
|
+
```
|
|
47
|
+
|
|
48
|
+
## Role profiles
|
|
49
|
+
|
|
50
|
+
Engineering catalogs SHOULD separate routine implementation from high-risk infrastructure and review work. The examples below are role-shaped; replace model IDs and thinking levels with the exact choices exposed by the team's agent providers.
|
|
51
|
+
|
|
52
|
+
```yaml
|
|
53
|
+
# profiles/engineer/profile.yml
|
|
54
|
+
id: engineer
|
|
55
|
+
label: Software Engineer
|
|
56
|
+
description: Default for feature work, bug fixes, and test-backed implementation.
|
|
57
|
+
inherits:
|
|
58
|
+
- base-engineering
|
|
59
|
+
controls:
|
|
60
|
+
provider: anthropic
|
|
61
|
+
model: anthropic/claude-sonnet-4
|
|
62
|
+
thinking: high
|
|
63
|
+
append_system_prompt: |
|
|
64
|
+
Optimize for correct, reviewable implementation. Inspect nearby code and tests,
|
|
65
|
+
make narrow commits, run the smallest meaningful validation, and summarize risks.
|
|
66
|
+
```
|
|
67
|
+
|
|
68
|
+
```yaml
|
|
69
|
+
# profiles/platform-engineer/profile.yml
|
|
70
|
+
id: platform-engineer
|
|
71
|
+
label: Platform Engineer
|
|
72
|
+
description: Higher-caution profile for CI, infrastructure, deployment, and incident work.
|
|
73
|
+
inherits:
|
|
74
|
+
- base-engineering
|
|
75
|
+
controls:
|
|
76
|
+
provider: anthropic
|
|
77
|
+
model: anthropic/claude-opus-4
|
|
78
|
+
thinking: xhigh
|
|
79
|
+
append_system_prompt: |
|
|
80
|
+
Treat infrastructure and production-like systems as high-risk. Diagnose before
|
|
81
|
+
mutating state, name rollback paths, and ask before deploys, credential use,
|
|
82
|
+
payments, or irreversible operations.
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
```yaml
|
|
86
|
+
# profiles/reviewer/profile.yml
|
|
87
|
+
id: reviewer
|
|
88
|
+
label: Code Reviewer
|
|
89
|
+
description: Review-focused profile for diffs, pull requests, and release readiness.
|
|
90
|
+
inherits:
|
|
91
|
+
- base-engineering
|
|
92
|
+
controls:
|
|
93
|
+
provider: openai
|
|
94
|
+
model: openai/gpt-4.1
|
|
95
|
+
thinking: medium
|
|
96
|
+
append_system_prompt: |
|
|
97
|
+
Review for correctness, regression risk, missing tests, unsafe operations,
|
|
98
|
+
unclear rollout paths, and documentation drift. Prioritize actionable findings
|
|
99
|
+
over style nits.
|
|
100
|
+
```
|
|
101
|
+
|
|
102
|
+
## Verification pattern
|
|
103
|
+
|
|
104
|
+
Engineering catalogs SHOULD make verification expectations explicit in prompts or comments so agents return evidence instead of vague completion claims.
|
|
105
|
+
|
|
106
|
+
```yaml
|
|
107
|
+
# profiles/engineer/profile.yml excerpt
|
|
108
|
+
controls:
|
|
109
|
+
append_system_prompt: |
|
|
110
|
+
When you change code, report the exact tests or checks you ran. If a check is
|
|
111
|
+
skipped, say why and name the smallest follow-up validation that would reduce risk.
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
This gives an engineering team a repeatable catalog with safe defaults: fast enough for common implementation, cautious enough for infrastructure, and explicit about verification evidence.
|