dreamteamer 0.31.0 → 0.33.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (66) hide show
  1. package/README.md +4 -2
  2. package/collections/agents.collection.yaml +41 -32
  3. package/collections/collections.collection.yaml +68 -204
  4. package/collections/command-bindings.collection.yaml +37 -43
  5. package/collections/commands.collection.yaml +50 -35
  6. package/collections/mixins.collection.yaml +49 -0
  7. package/collections/modules.collection.yaml +76 -122
  8. package/collections/repos.collection.yaml +53 -56
  9. package/collections/skills.collection.yaml +32 -21
  10. package/collections/ui-views.collection.yaml +57 -46
  11. package/mixins/docs.mixin.yaml +21 -0
  12. package/mixins/entity.mixin.yaml +22 -0
  13. package/package.json +5 -3
  14. package/scripts/migrate-descriptors-v2.mjs +795 -0
  15. package/skills/using-dreamteamer/SKILL.md +32 -25
  16. package/skills/using-dreamteamer/references/agents.md +1 -1
  17. package/skills/using-dreamteamer/references/before-you-build.md +1 -5
  18. package/skills/using-dreamteamer/references/collections.md +460 -288
  19. package/skills/using-dreamteamer/references/commands.md +49 -35
  20. package/skills/using-dreamteamer/references/data-modeling.md +348 -317
  21. package/skills/using-dreamteamer/references/extensions.md +8 -5
  22. package/skills/using-dreamteamer/references/getting-started.md +6 -4
  23. package/skills/using-dreamteamer/references/records.md +59 -33
  24. package/skills/using-dreamteamer/references/skills.md +4 -3
  25. package/skills/using-dreamteamer/references/ui-components.md +30 -32
  26. package/skills/using-dreamteamer/references/ui-views.md +122 -124
  27. package/src/api.d.ts +22 -2
  28. package/src/api.js +16 -1
  29. package/src/check.js +107 -37
  30. package/src/checkout.js +16 -15
  31. package/src/cli.js +147 -71
  32. package/src/collections-cli.js +136 -144
  33. package/src/commit.js +14 -6
  34. package/src/compile-collections.js +346 -0
  35. package/src/compile.js +219 -963
  36. package/src/descriptor-v2.js +165 -0
  37. package/src/descriptor.js +90 -0
  38. package/src/doctor.js +57 -0
  39. package/src/events.js +18 -12
  40. package/src/extensions.js +50 -12
  41. package/src/field-values.js +7 -6
  42. package/src/fields.js +254 -0
  43. package/src/filter.js +45 -1
  44. package/src/fractional-index.js +2 -2
  45. package/src/harnesses.js +82 -54
  46. package/src/init.js +74 -46
  47. package/src/namespace.js +23 -9
  48. package/src/placement.js +219 -0
  49. package/src/presentation.js +153 -299
  50. package/src/record-commands.js +12 -12
  51. package/src/records-api.d.ts +116 -9
  52. package/src/records-api.js +2 -1
  53. package/src/records.js +15 -13
  54. package/src/ref.js +3 -39
  55. package/src/relations.js +23 -24
  56. package/src/runtime.js +12 -35
  57. package/src/schema-ops.js +1188 -1274
  58. package/src/store.js +588 -98
  59. package/src/template.js +100 -24
  60. package/src/temporal.js +11 -3
  61. package/src/views.js +176 -0
  62. package/src/workspace.js +14 -0
  63. package/src/yaml.js +66 -5
  64. package/collection-templates/docs.collection-template.yaml +0 -17
  65. package/collection-templates/entity.collection-template.yaml +0 -20
  66. package/collections/collection-templates.collection.yaml +0 -20
package/README.md CHANGED
@@ -71,8 +71,10 @@ An extension adds verbs, source kinds or harnesses through one contract
71
71
  workspace module (`modules/<id>/package.json` declaring `dreamteamer.extension`) or an installed
72
72
  dependency.
73
73
 
74
- Behaviour proofs, worktrees, the REST API, the NotebookLM exporter and the local Docker host left core
75
- in 0.31.0 and return as extensions. None is published yet.
74
+ Behaviour proofs (`@dreamteamer/proofs`), worktrees (`@dreamteamer/worktrees`), the REST API
75
+ (`@dreamteamer/http`) and the NotebookLM exporter (`@dreamteamer/notebooklm`) are extension packages;
76
+ the local Docker host is the global `dt-docker` bin (`@dreamteamer/docker-workspaces`). A verb typed
77
+ without its package prints the install line.
76
78
 
77
79
  ## Agent-Native Documentation
78
80
 
@@ -1,33 +1,42 @@
1
1
  name: agents
2
- storage: { path: agents, codec: md, shape: file, suffix: agent }
3
- id: { generate: "{{ name | slug }}" }
4
- schema:
5
- type: object
6
- required: [name, description]
7
- properties:
8
- name:
9
- type: string
10
- description: The agent id — must equal the filename, or dispatch misses.
11
- description:
12
- type: string
13
- description: WHEN to dispatch this agent, in one line. The harness matches a request against this, so it is the agent's entire discoverability.
14
- tools:
15
- type: array
16
- items: { type: string }
17
- description: The tools this agent may use. Empty means the harness default set.
18
- model:
19
- type: string
20
- description: Which model to run it on. Omit to inherit the session's.
21
- skills:
22
- type: array
23
- items: { type: string, x-reference: skills }
24
- description: Skills this agent should load. Reference them rather than restating their steps in the body.
25
- instructions:
26
- type: string
27
- format: markdown
28
- x-body: true
29
- description: The agent's system prompt — what it is for and how it should work.
30
- order: 30
31
- list_fields: [name, last-modified, description]
32
- icon: smart_toy
33
- group: system
2
+ record_title: '{{ name }}'
3
+ description: A job that runs in a fresh context with its own tools — dispatched by its `description`.
4
+ use_when: >-
5
+ a job needs a context of its own (a long search, a review, an isolated build) — write it here; when
6
+ telling the current session how is enough, it is a skill instead
7
+ internal: true
8
+ storage:
9
+ path: agents
10
+ format: md
11
+ ids:
12
+ from: '{{ name | slug }}'
13
+ fields:
14
+ name:
15
+ type: string
16
+ required: true
17
+ description: The agent id — must equal the filename, or dispatch misses.
18
+ description:
19
+ type: string
20
+ required: true
21
+ description: WHEN to dispatch this agent, in one line. The harness matches a request against this, so it is the agent's entire discoverability.
22
+ tools:
23
+ type: string
24
+ many: true
25
+ description: The tools this agent may use. Empty means the harness default set.
26
+ model:
27
+ type: string
28
+ description: Which model to run it on. Omit to inherit the session's.
29
+ skills:
30
+ type: skills
31
+ many: true
32
+ description: Skills this agent should load. Reference them rather than restating their steps in the body.
33
+ instructions:
34
+ type: markdown
35
+ body: true
36
+ description: The agent's system prompt — what it is for and how it should work.
37
+ display:
38
+ nav:
39
+ icon: smart_toy
40
+ order: 30
41
+ list:
42
+ columns: [name, last_modified, description]
@@ -1,205 +1,69 @@
1
+ # A collection descriptor, as compile writes it: the authored keys (mixins and overlays merged in) and
2
+ # the `compiled` block holding everything compile decided. The authority on what each authored key
3
+ # means is skills/using-dreamteamer/references/collections.md; every reader asks a compiled
4
+ # descriptor through src/descriptor.js rather than reading these keys directly.
1
5
  name: collections
2
- storage: { path: collections, codec: yaml, shape: file, suffix: collection }
3
- id: { generate: "{{ name | slug }}" }
4
- schema:
5
- type: object
6
- required: [name, schema]
7
- # The fields fall into five groups, in this order: IDENTITY (name · singular · title ·
8
- # title_template — what the collection and a record of it are called), RETRIEVAL (description ·
9
- # use_when — what brings a session here), SHAPE (extends · schema · id · sensitive), PLACEMENT
10
- # (storage · module · group — where records live and who owns them), PRESENTATION (order ·
11
- # list_fields · sort_field · icon · ui — how the surfaces show it). A new field joins one of
12
- # these; a field that fits none is a sign it belongs on a record, not on the collection.
13
- properties:
14
- name:
15
- type: string
16
- description: The collection id — must equal the filename, and must be unique across every installed module.
17
- singular:
18
- type: string
19
- description: >-
20
- The word the CLI accepts beside `name` — `dt add task …` for `tasks`. DERIVED by inflection
21
- when absent (`tasks` → `task`, `companies` → `company`, `rnd/projects` → `rnd/project`) and
22
- authored only where inflection is wrong (`people` → `person`, `meeting-analyses` →
23
- `meeting-analysis`). Typed input only: a REFERENCE inside a record still spells the full
24
- name. compile refuses two collections whose name or singular coincide.
25
- description:
26
- type: string
27
- description: >-
28
- What one record IS, in one line — and the neighbour it is NOT, when a confusable one exists
29
- ("the person, never the org — that is `companies`"). Rendered into the orientation block
30
- every agent session loads, so it is retrieval surface, not documentation.
31
- use_when:
32
- type: string
33
- description: >-
34
- The SITUATIONS that should bring a session here, in one clause — rendered under the
35
- description in the orientation block. A description says what a record is; this says when
36
- to reach for the collection, in both directions: to READ ("about to diagnose a defect — search
37
- here first, filtered by repo") and to WRITE ("a thought arrives that has no home yet"). Author
38
- it for every collection whose trigger is not literally "you have one of these": a schema is
39
- designed to be used, and the measured failure is a session inventing a new state or field while
40
- the collection that already modelled it sat in its context. Two rules: it names a situation,
41
- never a procedure (a `how` belongs in the module's skill); and it must not restate the
42
- description — a paraphrase costs every session tokens and dilutes the clauses that carry
43
- signal. Omit only where the noun is the whole trigger.
44
- title:
45
- type: string
46
- description: What to call this collection in the nav and page headers. DERIVED from `name` by title-casing when absent — author it only when that is wrong (`ui-views` → `UI Views`).
47
- title_template:
48
- type: string
49
- description: 'How to label a RECORD of this collection, e.g. `{{ name }}`. DERIVED from the first of title/name/subject the schema declares (else `{{ id }}`). Every reference field pointing at this collection renders its value through this, so it is authored HERE once, not on each referencing field.'
50
- extends:
51
- type: string
52
- description: 'The module collection this one overlays, as `<module>/<collection>`. An overlay adds or narrows fields; it never redefines storage.'
53
- storage:
54
- type: object
55
- description: Where the records live on disk and how they are encoded.
56
- properties:
57
- path:
58
- type: string
59
- description: >-
60
- Folder holding the records, workspace-relative. `data/<collection>` — that is the answer
61
- unless you can state a reason. `state/<collection>` is DEPRECATED as a convention since
62
- 2026-08-31: decision 4 created it for runs, triggers, registries and cursors, all seven
63
- of those collections have been deleted, and the one real operational-data need that
64
- arrived since went to a gitignored `.cache/*.jsonl` because append-only readings are the
65
- wrong shape for records. The mechanism still works and is kept, exactly like `group`
66
- below, so a workspace wanting a second root has one. ⚠ NEVER author `system/` — sources
67
- have lived in `modules/<module>/<kind>/` since the 2026-08-05 flatten, and a `system/`
68
- prefix is only how `runtime.js` recognises a RUNTIME collection in a descriptor compiled
69
- by a pre-flatten engine.
70
- codec:
71
- type: string
72
- enum: [md, yaml, json, file]
73
- default: md
74
- description: 'File format. Use `md` whenever the record has a body a human will read. `file` makes the record an OPAQUE file — any extension, no frontmatter, fields DERIVED (`ext`, `bytes`), written with `add --from <path>` and never with `set`. For icons, logos and images.'
75
- max_bytes:
76
- type: integer
77
- default: 204800
78
- description: '`codec: file` only — the largest a record may be, in bytes. `check` reports anything over it. A record is a small file; a big one belongs outside the vault.'
79
- extensions:
80
- type: array
81
- items: { type: string }
82
- description: '`codec: file` only — the extensions this collection accepts, lowercase and without the dot. Omitted means any.'
83
- shape:
84
- type: string
85
- enum: [file, folder]
86
- default: file
87
- description: One file per record, or one folder per record.
88
- suffix:
89
- type: string
90
- description: 'The middle segment of a record filename: `<id>.<suffix>.<ext>`.'
91
- entry:
92
- type: string
93
- description: Folder shapes only — the file inside the folder that IS the record (e.g. SKILL.md).
94
- repo:
95
- type: string
96
- description: DERIVED by compile, never authored — the workspace-relative root of the git repo holding these records ('.' is the workspace). Set from the owning module's `owns-data`.
97
- id:
98
- type: object
99
- description: How a record's id is derived and what shape it is allowed to take.
100
- properties:
101
- generate:
102
- # ⚠ STRING OR AN ORDERED LIST OF STRINGS, and this schema has to say so or `check` refuses
103
- # the very form 0.25.0 added. `generateId` learned the list in 0.25.0 and THIS declaration
104
- # did not, so a descriptor carrying one compiled fine and then failed `check` with
105
- # "must be string" — the feature was unusable in exactly the workspaces it was written for.
106
- # Missed because the release was smoked with `dt add` against string templates; nothing
107
- # ran `check` over a descriptor that used a list.
108
- # anyOf, NOT oneOf: the validator coerces a single-element array to a string, so
109
- # `['{{ name | slug }}']` matches BOTH branches and `oneOf` (exactly one) rejects it.
110
- anyOf:
111
- - type: string
112
- - type: array
113
- minItems: 1
114
- items: { type: string }
115
- description: >-
116
- Template the id is built from, e.g. `{{ created | date }}--{{ name | slug }}`. Derive it from a field the
117
- record OWNS, never from write time. An ORDERED LIST takes the first template whose fields are all present —
118
- `['{{ code }}', '{{ name | slug }}']` is "the code when there is one, the name otherwise", which is how a
119
- collection keeps a readable latin handle without forcing a field onto every record. A template naming a
120
- missing field is skipped rather than fatal; when every one fails, the last error is the one raised.
121
- pattern:
122
- type: string
123
- description: Regex every id must match. `check` enforces it.
124
- schema:
125
- type: object
126
- description: A JSON Schema for the record's fields — validated against the meta-schema, not typed here. A field's own `description:` is what every surface shows as its explanation.
127
- order:
128
- type: number
129
- description: Sort position in the nav. Lower comes first.
130
- list_fields:
131
- type: array
132
- items: { type: string }
133
- description: The columns a list view shows by default.
134
- sort_field:
135
- type: string
136
- description: >-
137
- Which field carries MANUAL order — the one a drag writes. The field must be declared by this
138
- collection's own schema, and holds a fractional index (`dt move <collection>/<id>`), never an
139
- integer: renumbering is a multi-file commit against git. A surface offers dragging only while
140
- it is sorted by this field, because a handle that reorders nothing is a lie.
141
- icon:
142
- type: string
143
- description: material-symbols-outlined icon name, drawn in the nav and page header. The VS Code tree maps it to the nearest codicon — an unmapped name falls back to a generic cylinder, so pick one that is already mapped or add the row.
144
- unresolved_peers:
145
- type: array
146
- items: { type: string }
147
- description: >-
148
- DERIVED by compile, never authored — the collections THIS one references that its module
149
- declared as a `peerDependencies` peer and nothing installed provides. `check` reads it to
150
- excuse those references as unresolvable rather than wrong, which is what lets a module be
151
- opened on its own. It is stated here as DATA precisely so the record layer never has to
152
- learn what a module is; a bare string list rather than `x-reference: collections`, because
153
- the whole point is that the target is absent.
154
- sensitive:
155
- type: boolean
156
- description: >-
157
- This collection's records must not leave the workspace through an export — `dt export
158
- <target>` writes none of them and names the omission in what it does write (the schema
159
- source, the persona), so a reader knows the gap is deliberate. Set with `dt set
160
- collections/<c> sensitive=true`. For ONE field rather than the collection, mark the field:
161
- `x-sensitive: true` on its property (`dt add-field … --sensitive`). Nothing is inferred
162
- from a name — the mark is the decision.
163
- module:
164
- type: string
165
- description: >-
166
- The module that OWNS this concept, as its bare id — DERIVED by compile from the base source,
167
- and the one field a `dt set` may write: `dt set collections/<c> module=<m>` MOVES the
168
- descriptor into that module. An overlay adds fields to somebody else's collection and does
169
- not take it over, so the owner is the source declaring no `extends`. This is the workspace's
170
- real partition, and what the nav groups by.
171
- overlays:
172
- type: array
173
- items: { type: string }
174
- description: >-
175
- DERIVED by compile, never authored — the modules contributing an `extends:` overlay to this
176
- collection, by id. ABSENT when there are none: an empty list is a statement nobody made.
177
- `dt get collections/<c> --module <m>` prints one contribution alone.
178
- owner:
179
- type: string
180
- x-reference: modules
181
- description: >-
182
- ⚠ COMPAT, ONE RELEASE ONLY — superseded by `module`, which carries the same fact as the bare
183
- id the operator actually types. Kept because a surface groups its nav by this key and reads
184
- it as a reference; both are written by compile until that surface has moved. Removed in the
185
- release after 0.19.0.
186
- group:
187
- type: string
188
- description: >-
189
- The collection's PARTITION — which family of nouns it belongs to, authored freely (`crm`,
190
- `finance`, `family`, `content`…) and set with `dt set collections/<c> group=<g>`. One value
191
- is reserved and load-bearing: `group: system` says the collection is the workspace's own
192
- MACHINERY rather than one of its domain nouns, so it is left out of the generated block's
193
- domain listing, named on the system-collections line instead, and drawn on a surface's
194
- schema surface rather than in the record tree. ⚠ It does NOT change where records live or
195
- whether they can be written — that is `storage.base`, asked separately, and `repos` is the
196
- collection where the two answers split: `group: system` and workspace-stored records the
197
- operator edits by hand. Nearly removed on 2026-08-11, when the nav stopped grouping by it in
198
- favour of `owner` (a module, which has a title of its own) and nothing else read it; kept
199
- then so the change would be a code revert rather than a data migration, and because a
200
- workspace may want a partition that deliberately DIFFERS from its modules. That is what it
201
- became.
202
- order: 10
203
- list_fields: [name, last-modified]
204
- icon: schema
205
- group: system
6
+ record_title: '{{ name }}'
7
+ description: A typed set of records — what one record is, where records live, how ids are made, the fields, and how surfaces draw it.
8
+ use_when: >-
9
+ a new kind of thing has to be kept, or a collection's shape, storage or display changes — write the
10
+ descriptor in a module's collections/ folder and run dt compile; read a compiled one here to learn
11
+ what a collection is
12
+ internal: true
13
+ storage:
14
+ path: collections
15
+ format: yaml
16
+ ids:
17
+ from: '{{ name | slug }}'
18
+ fields:
19
+ name:
20
+ type: string
21
+ required: true
22
+ description: The collection's name — equal to the filename, unique across every installed module, carrying its namespace (`health/visits`).
23
+ title:
24
+ type: string
25
+ description: The human label. Default the title-cased bare name.
26
+ singular:
27
+ type: string
28
+ description: The word the CLI accepts beside the name (`dt add task …`). Default the inflected bare name, namespace kept.
29
+ record_title:
30
+ type: string
31
+ description: How one record is labelled wherever it is referenced, a template. Its first token is the field `dt add <collection> "<title>"` fills.
32
+ description:
33
+ type: string
34
+ description: What one record IS, in one line — naming the confusable neighbour it is not.
35
+ use_when:
36
+ type: string
37
+ description: The situations that should bring a session to this collection, to read it and to write it.
38
+ internal:
39
+ type: boolean
40
+ description: Workspace plumbing rather than a domain noun — left out of the domain listing.
41
+ sensitive:
42
+ type: boolean
43
+ description: Records never leave the workspace through an export.
44
+ storage:
45
+ type: map
46
+ description: Where records live — path, format (md · yaml · json · binary), shape (file · folder), entry, suffix, under { parent, subfolder }, max_bytes, accept.
47
+ ids:
48
+ type: map
49
+ description: How a record's id is made — `from` (a template, or an ordered list of them) and `pattern`.
50
+ fields:
51
+ type: map
52
+ values: map
53
+ description: The fields, in the descriptor's own vocabulary, in form order.
54
+ constraints:
55
+ type: map
56
+ many: true
57
+ description: JSON Schema combinators for a rule across fields.
58
+ display:
59
+ type: map
60
+ description: How surfaces draw it — nav, list, record, form.
61
+ compiled:
62
+ type: map
63
+ description: Written by compile, never authored — defaults, module, repo, runtime, under_collection, mirrors, overlaid_by, unresolved_peers, fields, json_schema.
64
+ display:
65
+ nav:
66
+ icon: schema
67
+ order: 10
68
+ list:
69
+ columns: [name, last_modified]
@@ -1,46 +1,40 @@
1
1
  name: command-bindings
2
+ description: A command applied to a collection, and the record state that makes it available and that means it is done.
3
+ use_when: >-
4
+ a command acts on the records of one collection — bind it here, gated on the record's own fields,
5
+ so `dt next <collection>/<id>` and the orientation block can say what to run on a record and when
6
+ internal: true
2
7
  storage:
3
8
  path: command-bindings
4
- codec: yaml
5
- shape: file
6
- suffix: command-binding
7
- id:
8
- generate: '{{ command | basename }}--{{ collection | basename }}'
9
- schema:
10
- type: object
11
- required:
12
- - command
13
- - collection
14
- properties:
15
- command:
16
- type: string
17
- x-reference: commands
18
- description: The command this binding applies.
19
- collection:
20
- type: string
21
- x-reference: collections
22
- description: The collection the command applies TO — which is what makes `dt next <ref>` able to answer "what can I do with this record".
23
- target:
24
- type: string
25
- enum:
26
- - record
27
- - collection
28
- default: record
29
- description: Whether the command runs against one record or the whole collection.
30
- can-enter:
31
- type: object
32
- description: The record state that makes this command AVAILABLE — a filter over the record's own fields. This is what turns a collection into a queue without any run records.
33
- can-exit:
34
- type: object
35
- description: The record state that means the command has already been DONE. Together with can-enter, the record's own fields are the progress marker.
36
- description:
37
- type: string
38
- description: What applying this command to this collection does, in one line.
39
- order: 45
40
- list_fields:
41
- - command
42
- - collection
43
- - target
44
- - last-modified
45
- icon: bolt
46
- group: system
9
+ format: yaml
10
+ ids:
11
+ from: '{{ command | basename }}--{{ collection | basename }}'
12
+ fields:
13
+ command:
14
+ type: commands
15
+ required: true
16
+ description: The command this binding applies.
17
+ collection:
18
+ type: collections
19
+ required: true
20
+ description: The collection the command applies to — what lets `dt next <ref>` answer "what can I do with this record".
21
+ scope:
22
+ type: string
23
+ default: record
24
+ enum: [record, collection]
25
+ description: Whether the command runs against one record or the whole collection.
26
+ available_when:
27
+ type: map
28
+ description: The record state that makes this command available — a filter over the record's own fields. It turns a collection into a queue with no run records.
29
+ done_when:
30
+ type: map
31
+ description: The record state that means the command has been done. With `available_when`, the record's own fields are the progress marker.
32
+ description:
33
+ type: string
34
+ description: What applying this command to this collection does, in one line.
35
+ display:
36
+ nav:
37
+ icon: bolt
38
+ order: 45
39
+ list:
40
+ columns: [command, collection, scope, last_modified]
@@ -1,36 +1,51 @@
1
1
  name: commands
2
- storage: { path: commands, codec: md, shape: file, suffix: command }
3
- id: { generate: "{{ name | slug }}" }
4
- schema:
5
- type: object
6
- required: [name]
7
- properties:
8
- name:
9
- type: string
10
- description: The command id — must equal the filename, and is what the operator types after the slash.
11
- description:
12
- type: string
13
- description: What this command does, in one line. It is the whole entry in the / picker, so write it for someone scanning.
14
- # native claude-code slash-command frontmatter — compile copies commands verbatim,
15
- # so these flow straight into .claude/commands/<name>.md and the / picker
16
- argument-hint:
17
- type: string
18
- description: What arguments the command takes, shown inline in the / picker.
19
- allowed-tools:
20
- type: string
21
- description: Tools this command may use, when it should be narrower than the session's.
22
- model:
23
- type: string
24
- description: Which model to run it on. Omit to inherit the session's.
25
- disable-model-invocation:
26
- type: boolean
27
- description: Set when only a person may run this — it stops the model invoking it on its own.
28
- prompt:
29
- type: string
30
- format: markdown
31
- x-body: true
32
- description: The command body. Reference the skill that owns the procedure rather than restating its steps — two copies drift.
33
- order: 40
34
- list_fields: [name, last-modified, description]
35
- icon: terminal
36
- group: system
2
+ record_title: '{{ name }}'
3
+ description: A procedure the operator starts by typing its name after a slash — the entry point, never the procedure itself.
4
+ use_when: >-
5
+ a job should start on one typed word, or a chain of jobs should be gated on a record's fields —
6
+ write the entry here and point it at the skill that owns the steps; if a session should find the
7
+ job on its own, it is a skill instead
8
+ internal: true
9
+ storage:
10
+ path: commands
11
+ format: md
12
+ ids:
13
+ from: '{{ name | slug }}'
14
+ fields:
15
+ name:
16
+ type: string
17
+ required: true
18
+ description: The command id — must equal the filename, and is what the operator types after the slash.
19
+ description:
20
+ type: string
21
+ description: What this command does, in one line. It is the whole entry in the / picker, so write it for someone scanning.
22
+ use_when:
23
+ type: string
24
+ description: The situations that should bring a session to this command, one clause. Rendered into the harness's trigger line after the description.
25
+ # Claude Code's own slash-command frontmatter — compile copies a command verbatim into the
26
+ # harness, so these keep the harness's spelling and are marked passthrough.
27
+ argument-hint:
28
+ type: string
29
+ passthrough: true
30
+ description: What arguments the command takes, shown inline in the / picker.
31
+ allowed-tools:
32
+ type: string
33
+ passthrough: true
34
+ description: Tools this command may use, when it should be narrower than the session's.
35
+ model:
36
+ type: string
37
+ description: Which model to run it on. Omit to inherit the session's.
38
+ disable-model-invocation:
39
+ type: boolean
40
+ passthrough: true
41
+ description: Set when only a person may run this — it stops the model invoking it on its own.
42
+ prompt:
43
+ type: markdown
44
+ body: true
45
+ description: The command body. Reference the skill that owns the procedure rather than restating its steps — two copies drift.
46
+ display:
47
+ nav:
48
+ icon: terminal
49
+ order: 40
50
+ list:
51
+ columns: [name, last_modified, description]
@@ -0,0 +1,49 @@
1
+ # The first meta-descriptor written in descriptor format v2: a mixin is itself a partial v2
2
+ # descriptor, so its own shape is stated in the vocabulary it contributes.
3
+ name: mixins
4
+ record_title: '{{ name }}'
5
+ description: A partial descriptor merged into every collection that lists it in `mixins` — shared fields, and where it says so storage, id and display.
6
+ use_when: >-
7
+ several collections in one module need the same fields (provenance, a dated document's id shape) —
8
+ write them once here and list the mixin, rather than restating the fields in every descriptor
9
+ internal: true
10
+ storage:
11
+ path: mixins
12
+ format: yaml
13
+ ids:
14
+ from: '{{ name | slug }}'
15
+ pattern: '^[a-z0-9-]+$'
16
+ fields:
17
+ name:
18
+ type: string
19
+ required: true
20
+ description: The mixin id. Scope it to its module (`clinic-provenance`, not `provenance`) — two modules shipping one id is a compile error, not a merge.
21
+ description:
22
+ type: string
23
+ description: What the mixin contributes, in one line.
24
+ use_when:
25
+ type: string
26
+ description: Which collections should list it.
27
+ fields:
28
+ type: map
29
+ values: map
30
+ description: The fields it contributes, in the descriptor's own field vocabulary. They are inserted before the collection's body field; a name the collection or another mixin also declares is a compile error.
31
+ storage:
32
+ type: map
33
+ description: Storage keys applied where the collection is silent.
34
+ ids:
35
+ type: map
36
+ description: How record ids are made (`from`, `pattern`), applied where the collection is silent.
37
+ display:
38
+ type: map
39
+ description: Display keys applied key by key where the collection is silent.
40
+ constraints:
41
+ type: map
42
+ many: true
43
+ description: JSON Schema combinators appended to the collection's own.
44
+ display:
45
+ nav:
46
+ icon: content_copy
47
+ order: 120
48
+ list:
49
+ columns: [name, description]