spawnfile 0.1.1 → 0.1.3
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 +80 -396
- package/dist/cli/index.js +0 -0
- package/dist/cli/modelCommands.d.ts +3 -0
- package/dist/cli/modelCommands.js +68 -0
- package/dist/cli/runCli.d.ts +23 -2
- package/dist/cli/runCli.js +78 -122
- package/dist/cli/runtimeCommands.d.ts +3 -0
- package/dist/cli/runtimeCommands.js +20 -0
- package/dist/cli/surfaceCommands.d.ts +3 -0
- package/dist/cli/surfaceCommands.js +98 -0
- package/dist/cli/viewCommand.d.ts +3 -0
- package/dist/cli/viewCommand.js +87 -0
- package/dist/compiler/agentSurfaces.js +51 -5
- package/dist/compiler/buildCompilePlan.js +38 -40
- package/dist/compiler/buildCompilePlanRuntime.d.ts +14 -0
- package/dist/compiler/buildCompilePlanRuntime.js +39 -0
- package/dist/compiler/buildCompilePlanTeams.d.ts +5 -0
- package/dist/compiler/buildCompilePlanTeams.js +38 -0
- package/dist/compiler/compilePlanHelpers.js +4 -1
- package/dist/compiler/compileProject.js +62 -13
- package/dist/compiler/compileProjectSupport.d.ts +17 -0
- package/dist/compiler/compileProjectSupport.js +136 -0
- package/dist/compiler/containerArtifacts.d.ts +6 -1
- package/dist/compiler/containerArtifacts.js +26 -4
- package/dist/compiler/containerArtifactsPlans.js +16 -1
- package/dist/compiler/containerArtifactsRender.d.ts +4 -2
- package/dist/compiler/containerArtifactsRender.js +21 -126
- package/dist/compiler/containerArtifactsTypes.d.ts +7 -0
- package/dist/compiler/containerEntrypointRender.d.ts +12 -0
- package/dist/compiler/containerEntrypointRender.js +186 -0
- package/dist/compiler/index.d.ts +4 -0
- package/dist/compiler/index.js +4 -0
- package/dist/compiler/interactiveSurfaceScopes.d.ts +2 -0
- package/dist/compiler/interactiveSurfaceScopes.js +21 -0
- package/dist/compiler/moltnetArtifacts.d.ts +27 -0
- package/dist/compiler/moltnetArtifacts.js +208 -0
- package/dist/compiler/moltnetBinaries.d.ts +4 -0
- package/dist/compiler/moltnetBinaries.js +103 -0
- package/dist/compiler/moltnetClientConfig.d.ts +11 -0
- package/dist/compiler/moltnetClientConfig.js +89 -0
- package/dist/compiler/moltnetRepresentativeResolution.d.ts +16 -0
- package/dist/compiler/moltnetRepresentativeResolution.js +86 -0
- package/dist/compiler/moltnetResolution.d.ts +3 -0
- package/dist/compiler/moltnetResolution.js +182 -0
- package/dist/compiler/moltnetRoomMemberships.d.ts +3 -0
- package/dist/compiler/moltnetRoomMemberships.js +140 -0
- package/dist/compiler/runProject.js +1 -1
- package/dist/compiler/surfaceDefinitions.d.ts +55 -0
- package/dist/compiler/surfaceDefinitions.js +204 -0
- package/dist/compiler/teamContextHelpers.d.ts +18 -0
- package/dist/compiler/teamContextHelpers.js +112 -0
- package/dist/compiler/teamContextSupport.d.ts +4 -0
- package/dist/compiler/teamContextSupport.js +264 -0
- package/dist/compiler/teamContextSupport.testHelpers.d.ts +16 -0
- package/dist/compiler/teamContextSupport.testHelpers.js +68 -0
- package/dist/compiler/teamContextTypes.d.ts +28 -0
- package/dist/compiler/teamContextTypes.js +1 -0
- package/dist/compiler/teamRoster.d.ts +12 -0
- package/dist/compiler/teamRoster.js +48 -0
- package/dist/compiler/teamRosterEntries.d.ts +13 -0
- package/dist/compiler/teamRosterEntries.js +230 -0
- package/dist/compiler/teamRosterTypes.d.ts +45 -0
- package/dist/compiler/teamRosterTypes.js +1 -0
- package/dist/compiler/types.d.ts +90 -6
- package/dist/compiler/updateProjectRuntime.d.ts +9 -0
- package/dist/compiler/updateProjectRuntime.js +67 -0
- package/dist/compiler/updateProjectSurfaces.d.ts +8 -0
- package/dist/compiler/updateProjectSurfaces.js +106 -0
- package/dist/compiler/view/buildOrganizationView.d.ts +2 -0
- package/dist/compiler/view/buildOrganizationView.js +180 -0
- package/dist/compiler/view/index.d.ts +4 -0
- package/dist/compiler/view/index.js +4 -0
- package/dist/compiler/view/renderNetworks.d.ts +2 -0
- package/dist/compiler/view/renderNetworks.js +93 -0
- package/dist/compiler/view/renderTree.d.ts +2 -0
- package/dist/compiler/view/renderTree.js +59 -0
- package/dist/compiler/view/sourcePaths.d.ts +2 -0
- package/dist/compiler/view/sourcePaths.js +19 -0
- package/dist/compiler/view/types.d.ts +80 -0
- package/dist/compiler/view/types.js +1 -0
- package/dist/manifest/loadManifest.js +4 -4
- package/dist/manifest/renderSpawnfile.js +74 -8
- package/dist/manifest/scaffold.js +1 -3
- package/dist/manifest/schemas.d.ts +227 -17
- package/dist/manifest/schemas.js +62 -20
- package/dist/manifest/surfaceSchemas.d.ts +154 -0
- package/dist/manifest/surfaceSchemas.js +77 -5
- package/dist/runtime/common.js +3 -0
- package/dist/runtime/openclaw/adapter.js +38 -5
- package/dist/runtime/openclaw/moltnet.d.ts +12 -0
- package/dist/runtime/openclaw/moltnet.js +124 -0
- package/dist/runtime/openclaw/surfaces.js +3 -0
- package/dist/runtime/picoclaw/adapter.js +27 -8
- package/dist/runtime/picoclaw/pico.d.ts +2 -0
- package/dist/runtime/picoclaw/pico.js +2 -0
- package/dist/runtime/picoclaw/surfaces.js +11 -0
- package/dist/runtime/tinyclaw/adapter.js +22 -8
- package/dist/runtime/tinyclaw/runAuth.js +28 -1
- package/dist/runtime/tinyclaw/surfaces.js +8 -0
- package/dist/runtime/types.d.ts +11 -0
- package/package.json +5 -3
- package/runtimes.yaml +4 -4
package/README.md
CHANGED
|
@@ -1,464 +1,148 @@
|
|
|
1
1
|
# Spawnfile
|
|
2
2
|
|
|
3
|
-
>
|
|
3
|
+
> A spec and compiler for autonomous agent runtimes. Write your agent once, compile for any runtime.
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
`spawnfile compile` lowers that canonical source into runtime-specific config and workspace files. It is not a runtime-to-runtime translator. The compiler starts from the canonical source and emits each declared adapter's output.
|
|
14
|
-
It also emits runnable container artifacts for the compiled output: `Dockerfile`, `entrypoint.sh`, `.env.example`, and a prebuilt `container/rootfs/` tree.
|
|
15
|
-
`spawnfile build` turns that output into a Docker image using the pinned compiled runtime artifacts from `runtimes.yaml`, and `spawnfile run` is the auth-aware wrapper over `docker run`.
|
|
16
|
-
|
|
17
|
-
---
|
|
18
|
-
|
|
19
|
-
## V0.1 Scope
|
|
20
|
-
|
|
21
|
-
Spawnfile v0.1 targets **autonomous agent runtimes** — systems that host agents as long-lived services with markdown workspace identity. It focuses on the portable surface shared across compatible runtimes:
|
|
22
|
-
|
|
23
|
-
- identity and personality docs (SOUL.md, IDENTITY.md, AGENTS.md)
|
|
24
|
-
- memory and heartbeat intent docs
|
|
25
|
-
- skills with SKILL.md
|
|
26
|
-
- MCP declarations
|
|
27
|
-
- runtime binding
|
|
28
|
-
- execution intent (model, workspace, sandbox)
|
|
29
|
-
- team structure (members, hierarchy, shared surfaces)
|
|
30
|
-
- agent-level Discord, Telegram, WhatsApp, and Slack surfaces
|
|
31
|
-
|
|
32
|
-
v0.1 does not try to standardize every runtime-native feature. Beyond the initial Discord, Telegram, WhatsApp, and Slack surfaces, communication surfaces, memory engines, task schedulers, UI surfaces, and other runtime-specific features stay adapter-defined for now.
|
|
33
|
-
|
|
34
|
-
---
|
|
35
|
-
|
|
36
|
-
## Companion Docs
|
|
37
|
-
|
|
38
|
-
- `specs/INDEX.md` - map of all specs with status and relationships
|
|
39
|
-
- `specs/SPEC.md` - canonical Spawnfile source spec
|
|
40
|
-
- `specs/COMPILER.md` - v0.1 compiler architecture, graph resolution, and adapter contract
|
|
41
|
-
- `specs/CONTAINERS.md` - container compilation spec
|
|
42
|
-
- `specs/RUNTIMES.md` - runtime registry, version pinning, and adapter lifecycle
|
|
43
|
-
- `specs/research/` - per-runtime research notes and adapter strategies
|
|
44
|
-
- `fixtures/` - canonical v0.1 source projects for compiler validation
|
|
45
|
-
|
|
46
|
-
---
|
|
47
|
-
|
|
48
|
-
## Technology
|
|
5
|
+
<p align="center">
|
|
6
|
+
<a href="https://www.npmjs.com/package/spawnfile"><img src="https://img.shields.io/npm/v/spawnfile?style=flat-square&color=d4604a&label=npm" alt="npm"></a>
|
|
7
|
+
<a href="https://www.npmjs.com/package/spawnfile"><img src="https://img.shields.io/npm/dm/spawnfile?style=flat-square&color=d4604a" alt="downloads"></a>
|
|
8
|
+
<a href="#from-source"><img src="https://img.shields.io/node/v/spawnfile?style=flat-square&color=d4604a" alt="node"></a>
|
|
9
|
+
<a href="LICENSE"><img src="https://img.shields.io/npm/l/spawnfile?style=flat-square&color=d4604a" alt="MIT"></a>
|
|
10
|
+
<a href="https://spawnfile.com"><img src="https://img.shields.io/website?url=https%3A%2F%2Fspawnfile.com&style=flat-square&label=spawnfile.com&color=d4604a" alt="website"></a>
|
|
11
|
+
</p>
|
|
49
12
|
|
|
50
|
-
|
|
13
|
+
<p align="center">
|
|
14
|
+
<img src="website/public/new-claw-images.png" alt="Spawnfile compiles one agent source into multiple runtimes" width="420" />
|
|
15
|
+
</p>
|
|
51
16
|
|
|
52
|
-
|
|
53
|
-
- CLI: `commander`
|
|
54
|
-
- manifest parsing: `yaml` + `zod`
|
|
55
|
-
- tests: `vitest`
|
|
17
|
+
Spawnfile is a **portable source format** for autonomous agents and teams. You write one canonical project — identity docs, skills, MCP connections, model and sandbox intent, team structure, and declared communication surfaces — and `spawnfile compile` lowers it into the runtime-specific config and workspace each adapter needs.
|
|
56
18
|
|
|
57
|
-
|
|
19
|
+
It's not a runtime-to-runtime translator. The compiler starts from the canonical source, emits each declared adapter's output, and reports per-capability support as `supported`, `degraded`, or `unsupported`.
|
|
58
20
|
|
|
59
|
-
|
|
21
|
+
Pairs with [**Moltnet**](https://moltnet.dev) as the first provider for `team.networks[]`, letting compiled agents share declared rooms, DMs, and history across runtimes without Spawnfile injecting its own message router.
|
|
60
22
|
|
|
61
23
|
## Install
|
|
62
24
|
|
|
63
25
|
```bash
|
|
64
26
|
npm install -g spawnfile
|
|
65
|
-
```
|
|
66
|
-
|
|
67
|
-
Verify:
|
|
68
|
-
|
|
69
|
-
```bash
|
|
70
27
|
spawnfile --help
|
|
71
28
|
```
|
|
72
29
|
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
```bash
|
|
76
|
-
git clone https://github.com/noopolis/spawnfile.git
|
|
77
|
-
cd spawnfile
|
|
78
|
-
nvm use
|
|
79
|
-
npm install
|
|
80
|
-
npm run build
|
|
81
|
-
npm link
|
|
82
|
-
```
|
|
83
|
-
|
|
84
|
-
To clone the target runtimes and generate reference blueprints:
|
|
85
|
-
|
|
86
|
-
```bash
|
|
87
|
-
npm run runtimes:sync
|
|
88
|
-
```
|
|
89
|
-
|
|
90
|
-
This clones each runtime at the version pinned in `runtimes.yaml` and generates blueprints showing the expected config and workspace layout. See `blueprints/` for the output.
|
|
91
|
-
|
|
92
|
-
These clones are for local research, blueprint generation, and adapter work. `spawnfile compile` itself does not need local runtime clones.
|
|
93
|
-
|
|
94
|
-
For local development without linking globally:
|
|
95
|
-
|
|
96
|
-
```bash
|
|
97
|
-
npm run dev -- validate fixtures/single-agent
|
|
98
|
-
```
|
|
99
|
-
|
|
100
|
-
---
|
|
101
|
-
|
|
102
|
-
## Why
|
|
103
|
-
|
|
104
|
-
The autonomous agent runtimes are different, but they already share a meaningful core: markdown workspace identity, skill folders, MCP, model selection, and workspace isolation. Today that core is re-authored by hand for each runtime. Spawnfile makes it canonical.
|
|
105
|
-
|
|
106
|
-
---
|
|
30
|
+
Node.js 22+ required. See [source install](#from-source) for local development.
|
|
107
31
|
|
|
108
|
-
##
|
|
109
|
-
|
|
110
|
-
You write a source project once. Then you compile it:
|
|
32
|
+
## The happy path
|
|
111
33
|
|
|
112
34
|
```bash
|
|
113
|
-
spawnfile init
|
|
114
|
-
spawnfile
|
|
115
|
-
spawnfile
|
|
116
|
-
spawnfile compile
|
|
35
|
+
spawnfile init # scaffold an agent (defaults to openclaw)
|
|
36
|
+
spawnfile validate # check the graph
|
|
37
|
+
spawnfile view . # read-only graph view; writes no files
|
|
38
|
+
spawnfile compile # lower to runtime-native output
|
|
117
39
|
spawnfile auth sync --profile dev --env-file .env
|
|
118
|
-
spawnfile build
|
|
119
|
-
spawnfile run --auth-profile dev
|
|
40
|
+
spawnfile build --tag my-agent # compile + docker build
|
|
41
|
+
spawnfile run --tag my-agent --auth-profile dev
|
|
120
42
|
```
|
|
121
43
|
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
Each adapter maps the canonical project into runtime-native forms. If a runtime cannot preserve a declaration, the compiler reports `supported`, `degraded`, or `unsupported` according to the project's compile policy.
|
|
125
|
-
|
|
126
|
-
Each compile also produces a machine-readable report describing the resolved graph, chosen runtimes, output locations, and capability outcomes.
|
|
127
|
-
|
|
128
|
-
The portable model stays intentionally small:
|
|
44
|
+
Compiled output lands under `.spawn/` by default, including a `Dockerfile`, `entrypoint.sh`, `.env.example`, and a prebuilt `container/rootfs/` tree. `spawnfile build` uses the pinned runtime artifacts from `runtimes.yaml`; it does not rebuild runtimes from source.
|
|
129
45
|
|
|
130
|
-
|
|
131
|
-
- `execution` carries portable intent like model, workspace, and sandbox
|
|
132
|
-
- `agent` may hold internal `subagents`
|
|
133
|
-
- `team` is for first-class agents that coordinate as a group
|
|
46
|
+
## Project structure
|
|
134
47
|
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
## Project Structure
|
|
48
|
+
A Spawnfile project is either an `agent` or a `team`.
|
|
138
49
|
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
### Agent
|
|
50
|
+
**Agent**
|
|
142
51
|
|
|
143
52
|
```text
|
|
144
53
|
my-agent/
|
|
145
54
|
├── Spawnfile
|
|
146
|
-
├── IDENTITY.md
|
|
147
|
-
├── SOUL.md
|
|
148
|
-
├── AGENTS.md
|
|
149
|
-
├── MEMORY.md
|
|
150
|
-
├── HEARTBEAT.md
|
|
151
|
-
├──
|
|
152
|
-
│ └──
|
|
153
|
-
|
|
154
|
-
└──
|
|
155
|
-
├── web_search/
|
|
156
|
-
│ └── SKILL.md
|
|
157
|
-
└── memory_store/
|
|
158
|
-
└── SKILL.md
|
|
55
|
+
├── IDENTITY.md # who the agent is
|
|
56
|
+
├── SOUL.md # tone and personality
|
|
57
|
+
├── AGENTS.md # system prompt
|
|
58
|
+
├── MEMORY.md # long-lived memory
|
|
59
|
+
├── HEARTBEAT.md # periodic prompt for scheduled wakes
|
|
60
|
+
├── skills/
|
|
61
|
+
│ └── web_search/SKILL.md
|
|
62
|
+
└── subagents/
|
|
63
|
+
└── researcher/Spawnfile
|
|
159
64
|
```
|
|
160
65
|
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
### Team
|
|
66
|
+
**Team**
|
|
164
67
|
|
|
165
68
|
```text
|
|
166
69
|
my-team/
|
|
167
70
|
├── Spawnfile
|
|
168
71
|
├── TEAM.md
|
|
169
|
-
├── shared/
|
|
170
|
-
│ └── skills/
|
|
171
|
-
│ └── web_search/
|
|
172
|
-
│ └── SKILL.md
|
|
72
|
+
├── shared/skills/...
|
|
173
73
|
└── agents/
|
|
174
|
-
├── orchestrator/
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
├── researcher/
|
|
178
|
-
│ ├── Spawnfile
|
|
179
|
-
│ └── SOUL.md
|
|
180
|
-
└── writer/
|
|
181
|
-
├── Spawnfile
|
|
182
|
-
└── SOUL.md
|
|
74
|
+
├── orchestrator/Spawnfile
|
|
75
|
+
├── researcher/Spawnfile
|
|
76
|
+
└── writer/Spawnfile
|
|
183
77
|
```
|
|
184
78
|
|
|
185
|
-
|
|
186
|
-
Team members may be on the same runtime or on different runtimes depending on what each member declares.
|
|
79
|
+
Team members may target different runtimes; the compiler resolves each member independently. Subagents are internal helpers owned by a parent agent — not the same thing as team members. Team coordination is through shared declared agent surfaces and declared team networks, not a Spawnfile-owned router.
|
|
187
80
|
|
|
188
|
-
|
|
81
|
+
Not every file is required. Spawnfile names the portable roles; adapters decide how to lower them into runtime-native surfaces. See [`specs/SPEC.md`](specs/SPEC.md) for the full shape.
|
|
189
82
|
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
## Policy
|
|
83
|
+
## Runtime support
|
|
193
84
|
|
|
194
|
-
|
|
85
|
+
v0.1 targets autonomous agent runtimes that share a markdown workspace identity model.
|
|
195
86
|
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
87
|
+
| Runtime | Status | Default | Surfaces |
|
|
88
|
+
|-----------|---------------|---------|-----------------------------------------------|
|
|
89
|
+
| OpenClaw | active | ✅ | Discord, Telegram, WhatsApp, Slack |
|
|
90
|
+
| PicoClaw | active | | Discord, Telegram, Slack (WhatsApp blocked) |
|
|
91
|
+
| TinyClaw | active | | Discord, Telegram, WhatsApp (pairing-gated) |
|
|
92
|
+
| NullClaw | exploratory | | No active adapter yet |
|
|
93
|
+
| ZeroClaw | exploratory | | No active adapter yet |
|
|
201
94
|
|
|
202
|
-
The compiler reports
|
|
95
|
+
Each adapter maps the portable schema into its native forms. The compiler reports a machine-readable `spawnfile-report.json` with the resolved graph, chosen runtimes, and capability outcomes (`supported`, `degraded`, `unsupported`). See [`specs/RUNTIMES.md`](specs/RUNTIMES.md) for the live matrix and pinned versions, or [`runtimes.yaml`](runtimes.yaml) for the registry source of truth.
|
|
203
96
|
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
## The CLI
|
|
207
|
-
|
|
208
|
-
```bash
|
|
209
|
-
spawnfile init
|
|
210
|
-
spawnfile init --runtime tinyclaw
|
|
211
|
-
spawnfile init --team
|
|
212
|
-
spawnfile add agent writer
|
|
213
|
-
spawnfile add subagent critic
|
|
214
|
-
spawnfile add team platform
|
|
215
|
-
spawnfile validate
|
|
216
|
-
spawnfile compile
|
|
217
|
-
spawnfile auth
|
|
218
|
-
spawnfile build
|
|
219
|
-
spawnfile run
|
|
220
|
-
```
|
|
221
|
-
|
|
222
|
-
For example:
|
|
223
|
-
|
|
224
|
-
```bash
|
|
225
|
-
spawnfile init --runtime picoclaw ./agents/researcher
|
|
226
|
-
spawnfile add agent writer ./my-team --runtime tinyclaw
|
|
227
|
-
spawnfile add subagent critic ./my-agent
|
|
228
|
-
spawnfile add team platform ./my-team
|
|
229
|
-
spawnfile validate fixtures/single-agent
|
|
230
|
-
spawnfile compile fixtures/single-agent --out ./bundle/example
|
|
231
|
-
spawnfile auth sync fixtures/single-agent --profile dev --env-file ./.env
|
|
232
|
-
spawnfile build fixtures/single-agent --out ./bundle/example --tag example-agent
|
|
233
|
-
spawnfile run fixtures/single-agent --tag example-agent --auth-profile dev
|
|
234
|
-
```
|
|
235
|
-
|
|
236
|
-
Without `--out`, the compiler writes generated artifacts under `.spawn/`. `spawnfile init` also ensures `.spawn/` is ignored in the project `.gitignore`.
|
|
237
|
-
|
|
238
|
-
The compiler emits runtime-specific artifacts under `.spawn/runtimes/...` by default and writes a machine-readable `spawnfile-report.json`.
|
|
239
|
-
|
|
240
|
-
`spawnfile init` defaults agent scaffolds to `openclaw`. Use `spawnfile init --runtime <name>` to scaffold an agent for a different bundled runtime. `spawnfile init --team` stays runtime-neutral.
|
|
241
|
-
|
|
242
|
-
`spawnfile add` grows an existing manifest graph in place. The target `[path]` is optional and defaults to the current directory. It must point to the parent project directory (or its `Spawnfile`):
|
|
243
|
-
|
|
244
|
-
- `spawnfile add agent <id> [path]` adds `agents/<id>/` under a team
|
|
245
|
-
If `--runtime` is omitted, it uses the same default agent runtime as `spawnfile init`.
|
|
246
|
-
- `spawnfile add subagent <id> [path]` adds `subagents/<id>/` under an agent
|
|
247
|
-
- `spawnfile add team <id> [path]` adds `teams/<id>/` under a team
|
|
248
|
-
|
|
249
|
-
The CLI rejects invalid parent kinds: `add agent` and `add team` only work on team projects, and `add subagent` only works on agent projects.
|
|
250
|
-
|
|
251
|
-
`spawnfile model` edits model intent in place and rewrites touched manifests to the canonical inline shape:
|
|
252
|
-
|
|
253
|
-
- `spawnfile model set <provider> <name> [path]` sets the primary model
|
|
254
|
-
- `spawnfile model add-fallback <provider> <name> [path]` appends a fallback model
|
|
255
|
-
- `spawnfile model clear-fallbacks [path]` removes fallback models
|
|
256
|
-
- if `[path]` points to a team project, `--recursive` is required and only descendant agent manifests are updated; the team manifest itself is left unchanged
|
|
257
|
-
- the first positional argument is always the model provider, not the auth method
|
|
258
|
-
|
|
259
|
-
Team manifests should not declare `execution`. Model, sandbox, and workspace intent belong to agent manifests, not teams.
|
|
260
|
-
|
|
261
|
-
Agent manifests may declare portable communication surfaces under `surfaces`. The first standardized surfaces are Discord, Telegram, WhatsApp, and Slack:
|
|
262
|
-
|
|
263
|
-
```yaml
|
|
264
|
-
surfaces:
|
|
265
|
-
discord:
|
|
266
|
-
access:
|
|
267
|
-
users:
|
|
268
|
-
- "987654321098765432"
|
|
269
|
-
bot_token_secret: DISCORD_BOT_TOKEN
|
|
270
|
-
telegram:
|
|
271
|
-
access:
|
|
272
|
-
users:
|
|
273
|
-
- "123456789"
|
|
274
|
-
chats:
|
|
275
|
-
- "-1001234567890"
|
|
276
|
-
bot_token_secret: TELEGRAM_BOT_TOKEN
|
|
277
|
-
whatsapp:
|
|
278
|
-
access:
|
|
279
|
-
users:
|
|
280
|
-
- "15551234567"
|
|
281
|
-
groups:
|
|
282
|
-
- "120363400000000000@g.us"
|
|
283
|
-
slack:
|
|
284
|
-
access:
|
|
285
|
-
users:
|
|
286
|
-
- "U1234567890"
|
|
287
|
-
channels:
|
|
288
|
-
- "C1234567890"
|
|
289
|
-
bot_token_secret: SLACK_BOT_TOKEN
|
|
290
|
-
app_token_secret: SLACK_APP_TOKEN
|
|
291
|
-
```
|
|
292
|
-
|
|
293
|
-
Discord access may declare:
|
|
294
|
-
|
|
295
|
-
- `mode: pairing | allowlist | open`
|
|
296
|
-
- `users`
|
|
297
|
-
- `guilds`
|
|
298
|
-
- `channels`
|
|
299
|
-
|
|
300
|
-
Telegram access may declare:
|
|
301
|
-
|
|
302
|
-
- `mode: pairing | allowlist | open`
|
|
303
|
-
- `users`
|
|
304
|
-
- `chats`
|
|
305
|
-
|
|
306
|
-
WhatsApp access may declare:
|
|
307
|
-
|
|
308
|
-
- `mode: pairing | allowlist | open`
|
|
309
|
-
- `users`
|
|
310
|
-
- `groups`
|
|
311
|
-
|
|
312
|
-
Slack access may declare:
|
|
313
|
-
|
|
314
|
-
- `mode: pairing | allowlist | open`
|
|
315
|
-
- `users`
|
|
316
|
-
- `channels`
|
|
317
|
-
|
|
318
|
-
If `mode` is omitted and any allowlist fields are present, Spawnfile infers `allowlist`.
|
|
319
|
-
If you want portable runtime behavior, set `access.mode` explicitly. Leaving `access` unset delegates to runtime defaults, which are not identical across runtimes.
|
|
320
|
-
If `bot_token_secret` is omitted, Spawnfile defaults to `DISCORD_BOT_TOKEN` for Discord, `TELEGRAM_BOT_TOKEN` for Telegram, and `SLACK_BOT_TOKEN` for Slack. If `app_token_secret` is omitted on Slack, Spawnfile defaults to `SLACK_APP_TOKEN`.
|
|
321
|
-
WhatsApp has no portable token-secret field in v0.1; session or QR-style auth remains runtime-defined.
|
|
322
|
-
`spawnfile auth sync ... --env-file .env` will collect that env name into the selected auth profile, and `spawnfile run --auth-profile ...` will validate it before container startup.
|
|
323
|
-
|
|
324
|
-
Runtime support is narrower than the portable schema:
|
|
325
|
-
|
|
326
|
-
- `openclaw` supports `pairing`, `allowlist`, and `open` for Discord, Telegram, WhatsApp, and Slack
|
|
327
|
-
- `picoclaw` supports `open` and user allowlists for Discord, Telegram, WhatsApp, and Slack
|
|
328
|
-
- `tinyclaw` supports `pairing` only for Discord, Telegram, and WhatsApp, and does not support Slack in Spawnfile v0.1
|
|
329
|
-
|
|
330
|
-
Practical notes from the current live smoke matrix:
|
|
331
|
-
|
|
332
|
-
- Discord was verified end to end on OpenClaw and PicoClaw, and as a paired DM surface on TinyClaw
|
|
333
|
-
- Telegram was verified end to end on all three runtimes
|
|
334
|
-
- `tinyclaw` required first-contact pairing on Telegram
|
|
335
|
-
- `openclaw` and `picoclaw` both worked on Telegram with `access.mode: open`
|
|
336
|
-
- WhatsApp was verified end to end on OpenClaw
|
|
337
|
-
- `picoclaw` WhatsApp remains blocked in the pinned artifact because `whatsapp_native` is not compiled into the shipped binary
|
|
338
|
-
- `tinyclaw` WhatsApp remains blocked in the shipped container because the upstream client needs a browser runtime
|
|
339
|
-
- Slack was verified end to end on OpenClaw
|
|
340
|
-
- Slack was verified end to end on PicoClaw
|
|
341
|
-
- `picoclaw` replies to channel messages in a Slack thread; direct messages reply inline
|
|
342
|
-
|
|
343
|
-
Useful options:
|
|
344
|
-
|
|
345
|
-
- `--auth <api_key|claude-code|codex|none>` sets the auth method on the edited model target
|
|
346
|
-
- `--key <ENV_NAME>` sets the env var name used by `api_key` auth for custom/local models
|
|
347
|
-
- `--compat <openai|anthropic>` and `--base-url <url>` configure local/custom endpoint targets
|
|
348
|
-
- `--recursive` updates the target project and every descendant manifest in the graph
|
|
349
|
-
|
|
350
|
-
Examples:
|
|
351
|
-
|
|
352
|
-
```bash
|
|
353
|
-
spawnfile model set anthropic claude-opus-4-6 --auth claude-code
|
|
354
|
-
spawnfile model set openai gpt-5.4 --auth codex
|
|
355
|
-
spawnfile model set local qwen2.5:14b --auth none --compat openai --base-url http://host.docker.internal:11434/v1
|
|
356
|
-
spawnfile model set anthropic claude-opus-4-6 . --auth claude-code --recursive
|
|
357
|
-
```
|
|
358
|
-
|
|
359
|
-
`spawnfile compile` also emits under the output root:
|
|
360
|
-
|
|
361
|
-
- final container filesystem output under `.spawn/container/rootfs/...` by default
|
|
362
|
-
- `Dockerfile`, `entrypoint.sh`, `.env.example`
|
|
363
|
-
|
|
364
|
-
`spawnfile build` is the happy path for compile + Docker image build. It compiles the project, then runs `docker build` against the emitted output directory. The generated Dockerfile installs the pinned compiled runtime artifacts for the resolved runtimes; it does not rebuild runtime sources during image build.
|
|
365
|
-
|
|
366
|
-
`spawnfile build` remains secrets-free by default. Runtime and model auth should be prepared locally, then applied at `spawnfile run` time.
|
|
367
|
-
|
|
368
|
-
Model auth can be imported into a local Spawnfile auth profile:
|
|
369
|
-
|
|
370
|
-
```bash
|
|
371
|
-
spawnfile auth sync fixtures/single-agent --profile dev --env-file ./.env
|
|
372
|
-
spawnfile auth show --profile dev
|
|
373
|
-
```
|
|
374
|
-
|
|
375
|
-
Projects declare model auth on each model entry in the Spawnfile, for example:
|
|
376
|
-
|
|
377
|
-
```yaml
|
|
378
|
-
execution:
|
|
379
|
-
model:
|
|
380
|
-
primary:
|
|
381
|
-
provider: anthropic
|
|
382
|
-
name: claude-opus-4-6
|
|
383
|
-
auth:
|
|
384
|
-
method: claude-code
|
|
385
|
-
```
|
|
97
|
+
## Why
|
|
386
98
|
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
```yaml
|
|
390
|
-
execution:
|
|
391
|
-
model:
|
|
392
|
-
primary:
|
|
393
|
-
provider: local
|
|
394
|
-
name: qwen2.5:14b
|
|
395
|
-
auth:
|
|
396
|
-
method: none
|
|
397
|
-
endpoint:
|
|
398
|
-
compatibility: openai
|
|
399
|
-
base_url: http://host.docker.internal:11434/v1
|
|
400
|
-
```
|
|
99
|
+
Autonomous agent runtimes already share a meaningful core: markdown workspace identity, skill folders, MCP, model selection, sandboxing. Today that core is re-authored by hand for each runtime. Spawnfile makes it canonical so one source project can ship to any compatible runtime.
|
|
401
100
|
|
|
402
|
-
|
|
101
|
+
## Docs
|
|
403
102
|
|
|
404
|
-
|
|
103
|
+
Hosted docs with rendered specs, runtime guides, and a capability matrix: **[spawnfile.com](https://spawnfile.com)** — start at [Introduction](https://spawnfile.com/introduction/), [Quickstart](https://spawnfile.com/quickstart/), or the [Runtimes overview](https://spawnfile.com/runtimes/overview/).
|
|
405
104
|
|
|
406
|
-
|
|
105
|
+
The source-of-truth specs live in this repo:
|
|
407
106
|
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
107
|
+
- [`specs/INDEX.md`](specs/INDEX.md) — map of all specs
|
|
108
|
+
- [`specs/SPEC.md`](specs/SPEC.md) — canonical source format
|
|
109
|
+
- [`specs/COMPILER.md`](specs/COMPILER.md) — compiler architecture and adapter contract
|
|
110
|
+
- [`specs/CONTAINERS.md`](specs/CONTAINERS.md) — container compilation
|
|
111
|
+
- [`specs/RUNTIMES.md`](specs/RUNTIMES.md) — runtime registry and version pinning
|
|
112
|
+
- [`specs/SURFACES.md`](specs/SURFACES.md) — messaging surface model
|
|
113
|
+
- [`fixtures/`](fixtures/) — canonical example projects
|
|
411
114
|
|
|
412
|
-
|
|
115
|
+
## From source
|
|
413
116
|
|
|
414
117
|
```bash
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
118
|
+
git clone https://github.com/noopolis/spawnfile.git
|
|
119
|
+
cd spawnfile
|
|
120
|
+
nvm use
|
|
121
|
+
npm install
|
|
122
|
+
npm run build
|
|
123
|
+
npm link
|
|
418
124
|
```
|
|
419
125
|
|
|
420
|
-
|
|
126
|
+
To clone pinned runtimes and generate reference blueprints:
|
|
421
127
|
|
|
422
128
|
```bash
|
|
423
|
-
|
|
424
|
-
cd ./bundle/example
|
|
425
|
-
docker build -t example-agent .
|
|
426
|
-
docker run --env-file .env -p 18789:18789 example-agent
|
|
129
|
+
npm run runtimes:sync
|
|
427
130
|
```
|
|
428
131
|
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
The repo also includes an opt-in Docker auth E2E harness.
|
|
432
|
-
It builds compiled images, starts them with a local Spawnfile auth profile, waits for runtime readiness, sends real prompts, and fails unless the expected sentinel reply comes back.
|
|
433
|
-
|
|
434
|
-
Examples:
|
|
132
|
+
For local development without linking globally:
|
|
435
133
|
|
|
436
134
|
```bash
|
|
437
|
-
npm run
|
|
438
|
-
npm run test:e2e:docker-auth -- --scenario team-multi-runtime --env-file ../headhunter/.env
|
|
135
|
+
npm run dev -- validate fixtures/single-agent
|
|
439
136
|
```
|
|
440
137
|
|
|
441
|
-
|
|
442
|
-
It requires Docker, network access, and real model credentials.
|
|
138
|
+
## Contributing
|
|
443
139
|
|
|
444
|
-
|
|
140
|
+
See [CONTRIBUTING.md](CONTRIBUTING.md) for local setup, tests, and the runtime adapter contract.
|
|
445
141
|
|
|
446
|
-
##
|
|
142
|
+
## License
|
|
447
143
|
|
|
448
|
-
|
|
144
|
+
MIT — see [LICENSE](LICENSE).
|
|
449
145
|
|
|
450
146
|
---
|
|
451
147
|
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
**Spawn** - in computing, you spawn a process. In games, you spawn a character. In biology, you spawn life. Deliberate creation. Independent existence from that point forward.
|
|
455
|
-
|
|
456
|
-
**File** - the atomic unit of software. Something you can read, version, fork, check into git, and own completely. It anchors a project - a directory, a complete picture of what something is.
|
|
457
|
-
|
|
458
|
-
Together: *a canonical source project that spawns an agent and can be compiled into the runtimes that can host it.*
|
|
459
|
-
|
|
460
|
-
---
|
|
461
|
-
|
|
462
|
-
*One source format. Many runtimes. Manifest-driven compilation.*
|
|
463
|
-
|
|
464
|
-
**spawnfile.ai** · **github.com/noopolis/spawnfile**
|
|
148
|
+
**[spawnfile.com](https://spawnfile.com)** · **[github.com/noopolis/spawnfile](https://github.com/noopolis/spawnfile)**
|
package/dist/cli/index.js
CHANGED
|
File without changes
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
export const registerModelCommands = (program, handlers, streams) => {
|
|
2
|
+
const modelCommand = program
|
|
3
|
+
.command("model")
|
|
4
|
+
.description("Edit primary and fallback model declarations");
|
|
5
|
+
modelCommand
|
|
6
|
+
.command("set")
|
|
7
|
+
.argument("<provider>", "Model provider")
|
|
8
|
+
.argument("<name>", "Model name")
|
|
9
|
+
.argument("[path]", "Project directory or Spawnfile path", process.cwd())
|
|
10
|
+
.option("--auth <method>", "Model auth method")
|
|
11
|
+
.option("--key <env>", "Environment variable for api_key auth")
|
|
12
|
+
.option("--compat <compatibility>", "Endpoint compatibility for custom/local models")
|
|
13
|
+
.option("--base-url <url>", "Endpoint base URL for custom/local models")
|
|
14
|
+
.option("--recursive", "Update the target project and its descendants")
|
|
15
|
+
.action(async (provider, name, inputPath, options) => {
|
|
16
|
+
const result = await handlers.setProjectPrimaryModel({
|
|
17
|
+
authKey: options.key,
|
|
18
|
+
authMethod: options.auth,
|
|
19
|
+
endpointBaseUrl: options.baseUrl,
|
|
20
|
+
endpointCompatibility: options.compat,
|
|
21
|
+
name,
|
|
22
|
+
path: inputPath,
|
|
23
|
+
provider,
|
|
24
|
+
recursive: options.recursive
|
|
25
|
+
});
|
|
26
|
+
for (const filePath of result.updatedFiles) {
|
|
27
|
+
streams.stdout(`updated ${filePath}`);
|
|
28
|
+
}
|
|
29
|
+
});
|
|
30
|
+
modelCommand
|
|
31
|
+
.command("add-fallback")
|
|
32
|
+
.argument("<provider>", "Model provider")
|
|
33
|
+
.argument("<name>", "Model name")
|
|
34
|
+
.argument("[path]", "Project directory or Spawnfile path", process.cwd())
|
|
35
|
+
.option("--auth <method>", "Model auth method")
|
|
36
|
+
.option("--key <env>", "Environment variable for api_key auth")
|
|
37
|
+
.option("--compat <compatibility>", "Endpoint compatibility for custom/local models")
|
|
38
|
+
.option("--base-url <url>", "Endpoint base URL for custom/local models")
|
|
39
|
+
.option("--recursive", "Update the target project and its descendants")
|
|
40
|
+
.action(async (provider, name, inputPath, options) => {
|
|
41
|
+
const result = await handlers.addProjectModelFallback({
|
|
42
|
+
authKey: options.key,
|
|
43
|
+
authMethod: options.auth,
|
|
44
|
+
endpointBaseUrl: options.baseUrl,
|
|
45
|
+
endpointCompatibility: options.compat,
|
|
46
|
+
name,
|
|
47
|
+
path: inputPath,
|
|
48
|
+
provider,
|
|
49
|
+
recursive: options.recursive
|
|
50
|
+
});
|
|
51
|
+
for (const filePath of result.updatedFiles) {
|
|
52
|
+
streams.stdout(`updated ${filePath}`);
|
|
53
|
+
}
|
|
54
|
+
});
|
|
55
|
+
modelCommand
|
|
56
|
+
.command("clear-fallbacks")
|
|
57
|
+
.argument("[path]", "Project directory or Spawnfile path", process.cwd())
|
|
58
|
+
.option("--recursive", "Update the target project and its descendants")
|
|
59
|
+
.action(async (inputPath, options) => {
|
|
60
|
+
const result = await handlers.clearProjectModelFallbacks({
|
|
61
|
+
path: inputPath,
|
|
62
|
+
recursive: options.recursive
|
|
63
|
+
});
|
|
64
|
+
for (const filePath of result.updatedFiles) {
|
|
65
|
+
streams.stdout(`updated ${filePath}`);
|
|
66
|
+
}
|
|
67
|
+
});
|
|
68
|
+
};
|