@mmmbuto/nexuscrew 0.9.12 → 0.9.13
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/frontend/dist/assets/{index-CBoobbt_.js → index-BBCrZoxR.js} +35 -35
- package/frontend/dist/assets/index-keXh4CAm.css +32 -0
- package/frontend/dist/index.html +2 -2
- package/lib/fleet/builtin.js +7 -4
- package/lib/fleet/catalogs/opencode-go.json +48 -1
- package/lib/fleet/cell-lease-server.js +95 -33
- package/lib/fleet/managed.js +121 -40
- package/lib/mcp/server.js +60 -16
- package/lib/mcp/tools.js +6 -0
- package/package.json +1 -1
- package/skills/cellforge/SKILL.md +169 -0
- package/skills/cellforge/assets/checkpoint.template.md +79 -0
- package/skills/cellforge/assets/internal-prompt.template.md +62 -0
- package/skills/cellforge/references/anatomy.md +73 -0
- package/skills/cellforge/references/audit.md +94 -0
- package/skills/cellforge/references/choosing.md +75 -0
- package/skills/cellforge/references/definition.md +107 -0
- package/skills/cellforge/references/lifecycle.md +100 -0
- package/skills/cellforge/references/operations.md +167 -0
- package/frontend/dist/assets/index-CWMKoCx-.css +0 -32
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
# Internal prompt — starting template
|
|
2
|
+
|
|
3
|
+
This is the short text the cell receives at boot. Keep it a **pointer**, not a
|
|
4
|
+
manual: it is capped at 8 KB, and anything duplicated from the canonical
|
|
5
|
+
documents will disagree with them within a week.
|
|
6
|
+
|
|
7
|
+
Replace every `{{PLACEHOLDER}}`. Delete the sections that do not apply — an
|
|
8
|
+
unedited template produces cells that all describe themselves identically, which
|
|
9
|
+
defeats the point of giving them separate identities.
|
|
10
|
+
|
|
11
|
+
**Never put a credential, token or key in here.** Depending on the engine, this
|
|
12
|
+
text becomes a command-line argument, and command lines are readable by other
|
|
13
|
+
processes belonging to the same user. Refer to the mechanism that holds a
|
|
14
|
+
secret; never to its value.
|
|
15
|
+
|
|
16
|
+
---
|
|
17
|
+
|
|
18
|
+
```
|
|
19
|
+
You are the {{CELL_ID}} cell.
|
|
20
|
+
|
|
21
|
+
PURPOSE. {{One sentence a stranger could act on. Not a department name —
|
|
22
|
+
what this cell produces and for whom.}}
|
|
23
|
+
|
|
24
|
+
YOU OWN. {{The directories, repositories or document areas this cell is
|
|
25
|
+
responsible for.}}
|
|
26
|
+
|
|
27
|
+
NOT YOURS. {{What belongs to other cells. Say who owns it, so a request that
|
|
28
|
+
lands here can be redirected instead of refused.}}
|
|
29
|
+
|
|
30
|
+
FIRST, EVERY SESSION.
|
|
31
|
+
1. Read your canonical prompt and your checkpoint: {{PATH_TO_CANONICAL_DOCS}}
|
|
32
|
+
2. Load your memory: state namespace {{STATE_NAMESPACE}}, journal
|
|
33
|
+
{{JOURNAL_NAMESPACE}}.
|
|
34
|
+
3. If the checkpoint is open, resume from the recorded point before starting
|
|
35
|
+
anything else. If it is closed, do not invent work.
|
|
36
|
+
4. Write the checkpoint at start, at every milestone, at every handoff, and
|
|
37
|
+
when you stop — even if the answer is "nothing changed".
|
|
38
|
+
|
|
39
|
+
NEVER WITHOUT ASKING. {{The irreversible things in this domain: publishing,
|
|
40
|
+
sending, deleting, deploying, spending. Be specific — a vague limit is one
|
|
41
|
+
that gets rationalised away at 2am.}}
|
|
42
|
+
|
|
43
|
+
WHEN YOU ARE UNSURE. Say what you did not verify. An honest gap is useful; a
|
|
44
|
+
plausible reconstruction is not, because it cannot be told apart from a fact.
|
|
45
|
+
|
|
46
|
+
{{OPTIONAL — REVIEW. Who checks this cell's work, and what it may not
|
|
47
|
+
approve on its own.}}
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
---
|
|
51
|
+
|
|
52
|
+
## What makes this prompt work, or not
|
|
53
|
+
|
|
54
|
+
- **The purpose line does most of the work.** If it could describe two different
|
|
55
|
+
cells, it is too vague, and every session will drift a little differently.
|
|
56
|
+
- **"Not yours" prevents more damage than "yours".** Cells collide over
|
|
57
|
+
ownership, not over ambition.
|
|
58
|
+
- **The confirmation list is what the user will thank you for.** It is the part
|
|
59
|
+
that stops a bad afternoon, and it belongs in the prompt rather than in a
|
|
60
|
+
document the cell might not read.
|
|
61
|
+
- **The last line is not decoration.** A cell that reports what it did not check
|
|
62
|
+
is one you can trust on what it did.
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
# Anatomy: the three places a cell lives
|
|
2
|
+
|
|
3
|
+
A cell is complete when all three exist and agree. Most breakage is one of them
|
|
4
|
+
missing or drifting, and none of the three reports the other two.
|
|
5
|
+
|
|
6
|
+
```
|
|
7
|
+
1. DEFINITION the runtime record — engine, cwd, prompt, permissions
|
|
8
|
+
written through the API, never by editing the file
|
|
9
|
+
|
|
10
|
+
2. RUNTIME WORKSPACE ~/NexusFiles/<session>/
|
|
11
|
+
inbox/ outbox/ + links to the cell's canonical documents
|
|
12
|
+
|
|
13
|
+
3. CANONICAL DOCUMENTS <docs-repo>/<cells-path>/<CellId>/
|
|
14
|
+
prompt · checkpoint · history/
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
## 1. Definition
|
|
18
|
+
|
|
19
|
+
Covered in `definition.md`. The thing to carry here: it is what makes the cell
|
|
20
|
+
*run*, and it is the only one of the three that has schema validation. The other
|
|
21
|
+
two are conventions — nothing stops you from creating a malformed workspace, so
|
|
22
|
+
the discipline has to come from you.
|
|
23
|
+
|
|
24
|
+
## 2. Runtime workspace
|
|
25
|
+
|
|
26
|
+
Lives under the files root, in a directory named after the cell's session. What
|
|
27
|
+
you find inside:
|
|
28
|
+
|
|
29
|
+
- **`inbox/`** — files delivered to the cell.
|
|
30
|
+
- **`outbox/`** — files the cell offers back to the operator. Created when first
|
|
31
|
+
needed rather than up front, so its absence on a new cell is normal, not a
|
|
32
|
+
fault.
|
|
33
|
+
- **links to the canonical documents** — the cell's prompt, its checkpoint and
|
|
34
|
+
its history are usually **symbolic links** pointing into the documentation
|
|
35
|
+
repository, not real files.
|
|
36
|
+
|
|
37
|
+
That last point is the one that causes trouble. When you inspect a cell, resolve
|
|
38
|
+
the links before concluding anything: a checkpoint that looks present may be a
|
|
39
|
+
link to a target that no longer exists, which reads as "the file is there" to
|
|
40
|
+
anything that does not follow it. Equally, a *copy* where a link belongs is
|
|
41
|
+
worse than a missing file — it will be edited, it will diverge from the canonical
|
|
42
|
+
version, and both will look authoritative.
|
|
43
|
+
|
|
44
|
+
## 3. Canonical documents
|
|
45
|
+
|
|
46
|
+
The cell's durable identity, versioned in a documentation repository:
|
|
47
|
+
|
|
48
|
+
- **the internal-facing prompt document** — the long-form version of what the
|
|
49
|
+
cell is, which the short boot prompt points at;
|
|
50
|
+
- **the checkpoint** — what the cell is doing right now, kept small enough to be
|
|
51
|
+
read at the start of every session;
|
|
52
|
+
- **`history/`** — previous checkpoints, archived automatically, so the live
|
|
53
|
+
checkpoint never has to carry the past.
|
|
54
|
+
|
|
55
|
+
`lifecycle.md` covers who writes these and when.
|
|
56
|
+
|
|
57
|
+
## Telling a complete cell from a half one
|
|
58
|
+
|
|
59
|
+
Check in this order — it goes from cheapest to most revealing:
|
|
60
|
+
|
|
61
|
+
1. **Does the runtime listing show it**, with the engine and model you expect?
|
|
62
|
+
If the definition is missing, nothing else matters.
|
|
63
|
+
2. **Does the workspace exist**, and do its links resolve to real files? A
|
|
64
|
+
broken link is the most common silent failure.
|
|
65
|
+
3. **Do the documents exist and describe this cell?** A prompt copied from
|
|
66
|
+
another cell and never adapted is technically present and practically
|
|
67
|
+
useless — read it, do not just check that it is there.
|
|
68
|
+
4. **Does the cell have somewhere to write its memory?** See `lifecycle.md`.
|
|
69
|
+
A cell whose memory namespace was never created will appear to work and will
|
|
70
|
+
quietly start every session with nothing.
|
|
71
|
+
|
|
72
|
+
A cell that fails 3 or 4 is the dangerous case: it runs, it answers, and it
|
|
73
|
+
forgets. Nobody notices until someone asks it what it did last week.
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
# Auditing a cell
|
|
2
|
+
|
|
3
|
+
An audit answers one question: **does this cell exist completely, and does it
|
|
4
|
+
match the standard?** Each check below says what to observe, because a check
|
|
5
|
+
whose result you cannot describe in advance is not a check.
|
|
6
|
+
|
|
7
|
+
Report everything, fix nothing until the user agrees. See the rule at the end —
|
|
8
|
+
it is the one that decides whether audits keep getting run.
|
|
9
|
+
|
|
10
|
+
## The checks
|
|
11
|
+
|
|
12
|
+
**1 · The definition loads and is the one you think.**
|
|
13
|
+
Observe the runtime listing, not the definitions file. Expect: the cell present,
|
|
14
|
+
with the engine, model and working directory you expect. A cell absent from the
|
|
15
|
+
listing but present in the file means the document failed validation — the whole
|
|
16
|
+
document, not just that entry.
|
|
17
|
+
|
|
18
|
+
**2 · The working directory is portable.**
|
|
19
|
+
Expect a relative form alongside the absolute one. Older cells often have only
|
|
20
|
+
the absolute path: not broken, but it will not survive being restored on another
|
|
21
|
+
machine. Offer to normalise.
|
|
22
|
+
|
|
23
|
+
**3 · The workspace exists and its links resolve.**
|
|
24
|
+
Expect the cell's directory under the files root, and the document links
|
|
25
|
+
resolving to real files. Two failure shapes: a **dangling link** (looks present
|
|
26
|
+
to anything that does not follow it) and a **real file where a link belongs**
|
|
27
|
+
(will be edited, will diverge, and both copies will look authoritative).
|
|
28
|
+
|
|
29
|
+
**4 · The internal prompt is this cell's.**
|
|
30
|
+
Read it. Expect it to name this cell's purpose and point at its documents.
|
|
31
|
+
A prompt copied from another cell passes every automated check and fails the
|
|
32
|
+
only one that matters. Also confirm it is a *pointer*, not a duplicate of the
|
|
33
|
+
canonical document — duplicates diverge.
|
|
34
|
+
|
|
35
|
+
**5 · No secrets in the prompt.**
|
|
36
|
+
Expect zero credentials, tokens or keys. This is not stylistic: with flag-style
|
|
37
|
+
delivery the prompt becomes a command-line argument, readable by other processes
|
|
38
|
+
of the same user. Report any find as a live exposure, not a style issue, and
|
|
39
|
+
treat rotation as the user's decision to make with full information.
|
|
40
|
+
|
|
41
|
+
**6 · The tool grant matches the purpose.**
|
|
42
|
+
Expect either an explicit server list, or a deliberate decision that this cell
|
|
43
|
+
gets everything. An empty list is the widest possible grant, and it is usually
|
|
44
|
+
absence of a decision rather than a decision. Report it as a question, not a
|
|
45
|
+
defect.
|
|
46
|
+
|
|
47
|
+
**7 · The checkpoint is within limits and correctly shaped.**
|
|
48
|
+
Expect it inside the line and byte limits (`lifecycle.md` gives concrete
|
|
49
|
+
starting numbers), with the sections in the order the install uses — the
|
|
50
|
+
template in `assets/checkpoint.template.md` is the reference shape — and a link
|
|
51
|
+
to the archived history. Over the limit is not a
|
|
52
|
+
style problem: the checkpoint is read at the start of every session.
|
|
53
|
+
|
|
54
|
+
**8 · The checkpoint's state is honest.**
|
|
55
|
+
Expect `open` to mean someone must resume it, and `closed` to mean verified
|
|
56
|
+
completion. The failure to look for is a checkpoint closed after a crash or a
|
|
57
|
+
restart — those interrupt work, they do not finish it.
|
|
58
|
+
|
|
59
|
+
**9 · The memory namespace exists and is split.**
|
|
60
|
+
Expect a state namespace and a journal namespace, scoped to this cell. Do not
|
|
61
|
+
check this by looking for a creation step — on many memory servers a namespace
|
|
62
|
+
simply exists once something is written to it. **Check the round trip**: the
|
|
63
|
+
cell writes its state, and reads it back.
|
|
64
|
+
|
|
65
|
+
Two failures worth naming: memory that never round-trips (the cell starts empty
|
|
66
|
+
every session, which reads as a model problem and can go unnoticed for weeks),
|
|
67
|
+
and **dated keys accumulating in state** (startup gets slower every week, and
|
|
68
|
+
nobody attributes it to this).
|
|
69
|
+
|
|
70
|
+
**10 · One checkpoint per cell per device.**
|
|
71
|
+
If the identity runs on more than one machine, expect one file per device.
|
|
72
|
+
A shared file means each device overwrites the others silently.
|
|
73
|
+
|
|
74
|
+
## Prove the audit can fail
|
|
75
|
+
|
|
76
|
+
Run the checks against a deliberately broken throwaway cell — remove a link,
|
|
77
|
+
close a checkpoint that should be open — and confirm the relevant check goes
|
|
78
|
+
red. A check that has passed on every cell you ever pointed it at may be
|
|
79
|
+
detecting nothing, and you will believe it precisely because it always agrees
|
|
80
|
+
with you.
|
|
81
|
+
|
|
82
|
+
This costs a few minutes once and is the difference between an audit and a
|
|
83
|
+
ritual.
|
|
84
|
+
|
|
85
|
+
## Report before you repair
|
|
86
|
+
|
|
87
|
+
Present findings and proposed fixes, and apply only what the user approves.
|
|
88
|
+
|
|
89
|
+
The reason is practical, not procedural: an audit that silently changes things
|
|
90
|
+
becomes a thing users are afraid to run. You want them running it often, which
|
|
91
|
+
means it must be safe — and "safe" means it never surprises them.
|
|
92
|
+
|
|
93
|
+
When you do apply fixes, apply them one at a time and re-run the specific check
|
|
94
|
+
after each. A batch that fails partway leaves nobody sure which half landed.
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
# Choosing an engine, tools and MCP servers for a purpose
|
|
2
|
+
|
|
3
|
+
This is the step where a cell becomes useful or becomes generic. The goal is a
|
|
4
|
+
recommendation the user can correct, not a questionnaire and not a default.
|
|
5
|
+
|
|
6
|
+
## Start from the work, not from the roles that already exist
|
|
7
|
+
|
|
8
|
+
The strong temptation on an install with existing cells is to clone the nearest
|
|
9
|
+
one. Resist it: you inherit its assumptions, its tool grants and its blind
|
|
10
|
+
spots, and the new cell ends up describing itself in someone else's words.
|
|
11
|
+
|
|
12
|
+
Instead, ask what the work actually looks like, because that maps to engines and
|
|
13
|
+
tools far better than a job title does:
|
|
14
|
+
|
|
15
|
+
- **Is it mostly reading and drafting, or mostly changing things?** Drafting
|
|
16
|
+
work wants a capable model and few dangerous tools. Work that edits real
|
|
17
|
+
systems wants tighter permissions and a reviewer.
|
|
18
|
+
- **Does it need to reach outside** — the web, mail, a calendar, a repository
|
|
19
|
+
host? Each of those is an MCP server, and each is a grant.
|
|
20
|
+
- **How long is a single task?** Work that runs for hours needs a cell that
|
|
21
|
+
checkpoints well and can hand off. Work in short bursts does not.
|
|
22
|
+
- **Does the output need to be trusted by someone else?** If yes, plan a second
|
|
23
|
+
cell to review it. A single cell approving its own work is not a review, and
|
|
24
|
+
no prompt wording changes that.
|
|
25
|
+
|
|
26
|
+
## A role the install has never seen
|
|
27
|
+
|
|
28
|
+
"Marketing", "Support", "Legal ops" — a role with no precedent is the normal
|
|
29
|
+
case, not the exception, and it is where cloning fails hardest.
|
|
30
|
+
|
|
31
|
+
Work it out from first principles:
|
|
32
|
+
|
|
33
|
+
1. **What does it produce?** Documents, decisions, messages, code, analysis.
|
|
34
|
+
2. **What does it need to see** to produce that, and what should it never see?
|
|
35
|
+
This is the MCP list, and phrasing it as "never see" surfaces limits a
|
|
36
|
+
capability list would miss.
|
|
37
|
+
3. **What is irreversible in its domain?** Sending, publishing, spending,
|
|
38
|
+
deleting. These become explicit confirmations in the prompt.
|
|
39
|
+
4. **Who checks it?** Either a person, or a second cell, or nobody — and if
|
|
40
|
+
nobody, say so out loud, because that is a decision.
|
|
41
|
+
|
|
42
|
+
Then propose engine, model and tools with a sentence of reasoning each, and mark
|
|
43
|
+
what you are unsure about. A recommendation with visible reasoning can be
|
|
44
|
+
corrected; a confident list cannot.
|
|
45
|
+
|
|
46
|
+
## Scoping MCP servers
|
|
47
|
+
|
|
48
|
+
A cell with no explicit server list inherits **everything** the client engine
|
|
49
|
+
has. That is the widest grant available, and on most installs it is the default
|
|
50
|
+
simply because nobody set the field.
|
|
51
|
+
|
|
52
|
+
For a new cell, propose the narrow list: the servers its purpose actually needs.
|
|
53
|
+
The cost is one array, and the benefit is that a drafting cell cannot reach a
|
|
54
|
+
tool that deletes things.
|
|
55
|
+
|
|
56
|
+
Two cautions:
|
|
57
|
+
|
|
58
|
+
- **Do not narrow an existing cell without asking.** Something it does today may
|
|
59
|
+
depend on a server you are about to remove, and the failure will appear later
|
|
60
|
+
and somewhere else.
|
|
61
|
+
- **Names, not definitions.** The server definitions live in the client
|
|
62
|
+
configuration and stay there. A per-cell list selects from them; it never
|
|
63
|
+
redefines them, because two definitions of the same server will drift.
|
|
64
|
+
|
|
65
|
+
## Permissions and the reviewer
|
|
66
|
+
|
|
67
|
+
Match the permission posture to what the cell can break, not to how much you
|
|
68
|
+
trust the model. Some engines only accept the standard posture — the API will
|
|
69
|
+
refuse the others, which is a useful signal rather than an obstacle.
|
|
70
|
+
|
|
71
|
+
When work needs a verdict, the reviewer must be **structurally** independent: a
|
|
72
|
+
different cell, which did not do the work and cannot quietly fix it. A cell that
|
|
73
|
+
implements and then audits its own output will approve it — not from
|
|
74
|
+
dishonesty, but because it is checking against the same understanding that
|
|
75
|
+
produced the work. That is the whole reason the second cell exists.
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
# The cell definition
|
|
2
|
+
|
|
3
|
+
The definition is the runtime record of a cell: what it runs, where, with which
|
|
4
|
+
prompt and permissions. It is stored in the fleet definitions file, but **you
|
|
5
|
+
never edit that file** — you go through the API, which validates the whole
|
|
6
|
+
document and refuses to write a state the file format would happily hold.
|
|
7
|
+
|
|
8
|
+
## Write path
|
|
9
|
+
|
|
10
|
+
| operation | endpoint | capability required |
|
|
11
|
+
|---|---|---|
|
|
12
|
+
| create a cell | `POST /define-cell` | `define` |
|
|
13
|
+
| change a cell | `POST /edit-cell` | `edit` |
|
|
14
|
+
| delete a cell | `POST /remove-cell` | `remove` |
|
|
15
|
+
| bulk restore | `POST /restore-cells` | `restore` |
|
|
16
|
+
| create / change / delete an engine | `POST /define-engine`, `/edit-engine`, `/remove-engine` | `define` / `edit` / `remove` |
|
|
17
|
+
|
|
18
|
+
Two behaviours worth knowing before you are surprised by them:
|
|
19
|
+
|
|
20
|
+
- **Read-only mode refuses every write with `403`.** If a define or edit comes
|
|
21
|
+
back refused and the payload looks correct, check whether the fleet provider
|
|
22
|
+
is read-only before you start rewriting the payload.
|
|
23
|
+
- **Validation is all-or-nothing.** A malformed optional field does not collapse
|
|
24
|
+
into "absent" — it fails the whole definition. This is deliberate: absent and
|
|
25
|
+
malformed are opposite outcomes that look alike, and silently treating one as
|
|
26
|
+
the other is how a cell ends up running with a setting nobody chose.
|
|
27
|
+
|
|
28
|
+
## Fields
|
|
29
|
+
|
|
30
|
+
`id` and the tmux session are **immutable after creation** — an edit that
|
|
31
|
+
includes either is refused. Everything else is patchable.
|
|
32
|
+
|
|
33
|
+
| field | required | shape and limit |
|
|
34
|
+
|---|---|---|
|
|
35
|
+
| `id` | yes | `[A-Za-z0-9._-]`, 1–32 chars. Human-readable identity; the dot is allowed |
|
|
36
|
+
| `cwd` | yes | working directory, ≤4096 chars |
|
|
37
|
+
| `cwdRel` | recommended | the same directory expressed relative to the user's home |
|
|
38
|
+
| `engine` | yes | must reference an existing engine id; a dangling reference fails the definition |
|
|
39
|
+
| `boot` | no | boolean, default false — whether the cell starts with the service |
|
|
40
|
+
| `model` / `models` | no | model selection; validated against the engine's catalogue when the engine is managed |
|
|
41
|
+
| `prompt` | no | the internal prompt, ≤8192 bytes |
|
|
42
|
+
| `permissionPolicies` | no | per-engine permission posture; some engines accept only the standard one |
|
|
43
|
+
| `commands` | no | per-engine command string, shell engines only, ≤4096 chars, no control characters |
|
|
44
|
+
| `panelUrl` | no | HTTP(S) endpoint of an associated panel, ≤512 chars |
|
|
45
|
+
| `mcp` | no | **names only**, up to 64, each matching `[a-zA-Z0-9][a-zA-Z0-9_-]{0,63}` |
|
|
46
|
+
| `label`, `tmuxSession` | varies | display label ≤64 chars; session name ≤64 chars, immutable |
|
|
47
|
+
|
|
48
|
+
Ceilings on the document as a whole: **32 cells**, **24 engines**. These are not
|
|
49
|
+
close to most installs, but a restore that silently dropped entries would be
|
|
50
|
+
worse than one that fails, so a document over the cap is rejected rather than
|
|
51
|
+
truncated.
|
|
52
|
+
|
|
53
|
+
## `cwd` and `cwdRel`: portability is a write-time invariant
|
|
54
|
+
|
|
55
|
+
`cwdRel` is the portable form: the working directory relative to the user's
|
|
56
|
+
home. The distinction matters when a definition moves between machines — an
|
|
57
|
+
absolute path that exists on one install may not exist on another, and the cell
|
|
58
|
+
comes back pointing somewhere wrong or nowhere at all.
|
|
59
|
+
|
|
60
|
+
Reading tolerates a definition that has only `cwd`, so older entries keep
|
|
61
|
+
loading. **Writing does not**: create and edit resolve the pair together and
|
|
62
|
+
refuse input that is not portable. When you write a definition, always provide
|
|
63
|
+
the relative form — and when you audit an install, expect to find older cells
|
|
64
|
+
that predate it and offer to normalise them.
|
|
65
|
+
|
|
66
|
+
## `mcp`: the field that grants tools, and why it is probably empty
|
|
67
|
+
|
|
68
|
+
`mcp` lists **which MCP servers this cell gets, by name**. Only names: the
|
|
69
|
+
server definitions live in exactly one place, the client configuration, and
|
|
70
|
+
duplicating them per cell would create two sources of truth that drift.
|
|
71
|
+
|
|
72
|
+
Expect to find this field unset on most installs — and understand what that
|
|
73
|
+
means: **a cell with no `mcp` list inherits every server the client engine has.**
|
|
74
|
+
That is convenient and it is also the widest possible grant.
|
|
75
|
+
|
|
76
|
+
When you create a cell, propose the narrow list that matches its purpose. A
|
|
77
|
+
marketing cell that drafts copy has no business holding a tool that can delete
|
|
78
|
+
files or move money, and the cost of scoping it is one array. Say plainly that
|
|
79
|
+
this is a change from the install's habit, and let the user decide — do not
|
|
80
|
+
narrow an existing cell's tools without asking, because something it does today
|
|
81
|
+
may depend on a server you are about to take away.
|
|
82
|
+
|
|
83
|
+
## The internal prompt, and the one rule about it
|
|
84
|
+
|
|
85
|
+
The internal prompt is the text the cell receives at boot. Keep it small — a
|
|
86
|
+
bootstrap that tells the cell who it is and points at its canonical documents,
|
|
87
|
+
not a copy of them. The limit is 8 KB, but the reason to stay far below it is
|
|
88
|
+
that a prompt duplicating the documents will disagree with them within a week.
|
|
89
|
+
|
|
90
|
+
**How it is delivered depends on the engine**, and this has a security
|
|
91
|
+
consequence:
|
|
92
|
+
|
|
93
|
+
- **flag delivery** — the prompt is appended to the launch command as an
|
|
94
|
+
argument. Command lines are visible to other processes of the same user.
|
|
95
|
+
- **typed delivery** — the prompt is sent into the session after it comes up,
|
|
96
|
+
and re-sent on restart.
|
|
97
|
+
|
|
98
|
+
So: **never put a credential, token or key in a cell prompt.** Refer to the
|
|
99
|
+
mechanism that holds the secret, never the value. This holds regardless of
|
|
100
|
+
delivery mode — you should not have to know the engine's delivery style to be
|
|
101
|
+
safe, and an engine change must never turn a safe prompt into an exposed one.
|
|
102
|
+
|
|
103
|
+
The second consequence: **changing the engine can change whether the prompt
|
|
104
|
+
arrives at all.** Verify delivery after any engine change rather than assuming
|
|
105
|
+
the field carried over — the field is still there either way, which is what
|
|
106
|
+
makes this easy to miss. `operations.md` §Verifying that the prompt actually
|
|
107
|
+
arrived has the method for each delivery mode.
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
# Lifecycle: prompt, checkpoint, history, memory
|
|
2
|
+
|
|
3
|
+
Four mechanisms carry a cell across sessions. They are easy to confuse because
|
|
4
|
+
they all "remember things", so start with what each is actually for:
|
|
5
|
+
|
|
6
|
+
| mechanism | answers | changes |
|
|
7
|
+
|---|---|---|
|
|
8
|
+
| **internal prompt** | who am I, where do I look | rarely — when the purpose changes |
|
|
9
|
+
| **canonical prompt document** | the long-form version of the same | occasionally |
|
|
10
|
+
| **checkpoint** | what am I doing *right now*, and what blocks it | constantly |
|
|
11
|
+
| **memory** | durable facts and a running journal | every session |
|
|
12
|
+
|
|
13
|
+
## The internal prompt: small on purpose
|
|
14
|
+
|
|
15
|
+
The boot prompt should establish identity and point at the canonical documents,
|
|
16
|
+
not restate them. Two reasons, and the second is the one people learn the hard
|
|
17
|
+
way:
|
|
18
|
+
|
|
19
|
+
1. It is capped (8 KB), so a prompt that grows into a manual eventually stops
|
|
20
|
+
fitting.
|
|
21
|
+
2. **Duplicated instructions diverge.** When the prompt and the document say
|
|
22
|
+
different things, the cell follows whichever it read last, and no one can
|
|
23
|
+
tell which that was. One source, one pointer.
|
|
24
|
+
|
|
25
|
+
## The checkpoint: a resume point, not a diary
|
|
26
|
+
|
|
27
|
+
The checkpoint answers "if this session ended right now, what would the next one
|
|
28
|
+
need?" That framing decides what belongs in it far better than any rule.
|
|
29
|
+
|
|
30
|
+
What makes checkpoints work in practice:
|
|
31
|
+
|
|
32
|
+
- **Hard limits.** A line count and a byte size — as a starting point, **200
|
|
33
|
+
lines and 24 KB**, with roughly **three days** of operational detail and older
|
|
34
|
+
work compressed to a summary. They are not bureaucracy: the checkpoint is read
|
|
35
|
+
at the start of every session, so a bloated one costs context forever.
|
|
36
|
+
Nothing in the product enforces this. If the install has tooling that
|
|
37
|
+
validates and archives, use it; if not, the contract still holds and you keep
|
|
38
|
+
it by hand — which mostly means deleting what is no longer true each time you
|
|
39
|
+
write.
|
|
40
|
+
- **A fixed section order**, so a reader finds the current task, the evidence,
|
|
41
|
+
the blockers and the next step in the same place every time.
|
|
42
|
+
- **Automatic archiving.** Replacing the checkpoint should snapshot the previous
|
|
43
|
+
one into a history tree and leave a link behind. This is what lets the live
|
|
44
|
+
file stay short without losing anything: the past is one click away, not in
|
|
45
|
+
your context.
|
|
46
|
+
- **Closed only when verified.** A crash, a reboot, a device change or "I think
|
|
47
|
+
it worked" do not close a task. Open means someone must resume it.
|
|
48
|
+
|
|
49
|
+
**Write it even when nothing happened.** A session that starts, finds nothing to
|
|
50
|
+
do and updates the timestamp is doing the right thing: the next session learns
|
|
51
|
+
that the state was checked at a known moment, which is different from not
|
|
52
|
+
knowing.
|
|
53
|
+
|
|
54
|
+
**One cell writes one checkpoint.** If the same cell identity runs on more than
|
|
55
|
+
one machine, give each device its own checkpoint file — a shared one means each
|
|
56
|
+
device silently overwrites the others, and nobody notices until two sessions
|
|
57
|
+
disagree about reality.
|
|
58
|
+
|
|
59
|
+
## Memory: state and journal are different mechanisms
|
|
60
|
+
|
|
61
|
+
Not two files — two behaviours, and using the wrong one is the usual cause of a
|
|
62
|
+
slow, bloated startup.
|
|
63
|
+
|
|
64
|
+
- **State** — a declarative snapshot of what is true now. Written whole (or
|
|
65
|
+
patched key by key), read at every startup. It must stay lean, which means
|
|
66
|
+
**never accumulate dated keys in it**. "What happened on the 14th" is not
|
|
67
|
+
state; state is "where the work stands".
|
|
68
|
+
- **Journal** — an append-only, bounded event stream. Each entry is stamped and
|
|
69
|
+
old entries are pruned automatically. Bounded is the contract, not a defect:
|
|
70
|
+
anything that must survive pruning does not belong here, it belongs in the
|
|
71
|
+
canonical documents.
|
|
72
|
+
|
|
73
|
+
Because the journal is bounded and multi-writer safe, it is the right place for
|
|
74
|
+
"what I did this session". Because state is read at every boot, it is the wrong
|
|
75
|
+
place for anything historical.
|
|
76
|
+
|
|
77
|
+
**Scoping.** Give each cell its own state and journal namespace, tied to a
|
|
78
|
+
per-cell device identity. Reads are typically open across cells — that is what
|
|
79
|
+
lets one cell understand another's situation — while **writes are scoped to the
|
|
80
|
+
owner**. Design for that: a cell should never need to write outside its own
|
|
81
|
+
namespace to do its job, and if it does, the boundary is drawn wrong.
|
|
82
|
+
|
|
83
|
+
**Getting the namespace to exist** is the memory server's business, not the
|
|
84
|
+
fleet API's, and servers differ: on many, a namespace simply comes into being
|
|
85
|
+
the first time something is written to it, and there is no separate creation
|
|
86
|
+
step to perform. So do not go looking for a command that may not exist — check
|
|
87
|
+
the memory server's own tool surface, and verify the round trip instead: have
|
|
88
|
+
the cell write its state once, then read it back.
|
|
89
|
+
|
|
90
|
+
Verify it, though. A cell whose memory has nowhere to go does not fail loudly;
|
|
91
|
+
it just starts every session empty, and that reads as a model problem rather
|
|
92
|
+
than a setup problem — which is why it can go unnoticed for weeks.
|
|
93
|
+
|
|
94
|
+
## Retiring a cell
|
|
95
|
+
|
|
96
|
+
Removing a cell throws away an identity and orphans its documents. Before doing
|
|
97
|
+
it, confirm with the user and decide explicitly what happens to the canonical
|
|
98
|
+
documents and the memory namespace — usually they should be kept, because they
|
|
99
|
+
are the record of work that actually happened. Stopping a cell is reversible;
|
|
100
|
+
removing its definition and deleting its history is not.
|