@younndai/lyt-skills 0.9.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 (43) hide show
  1. package/LICENSE +200 -0
  2. package/NOTICE +23 -0
  3. package/README.md +124 -0
  4. package/dist/commands/skills-install.d.ts +3 -0
  5. package/dist/commands/skills-install.d.ts.map +1 -0
  6. package/dist/commands/skills-install.js +89 -0
  7. package/dist/commands/skills-install.js.map +1 -0
  8. package/dist/commands/skills-list.d.ts +3 -0
  9. package/dist/commands/skills-list.d.ts.map +1 -0
  10. package/dist/commands/skills-list.js +79 -0
  11. package/dist/commands/skills-list.js.map +1 -0
  12. package/dist/commands/skills.d.ts +3 -0
  13. package/dist/commands/skills.d.ts.map +1 -0
  14. package/dist/commands/skills.js +26 -0
  15. package/dist/commands/skills.js.map +1 -0
  16. package/dist/index.d.ts +6 -0
  17. package/dist/index.d.ts.map +1 -0
  18. package/dist/index.js +19 -0
  19. package/dist/index.js.map +1 -0
  20. package/dist/list.d.ts +19 -0
  21. package/dist/list.d.ts.map +1 -0
  22. package/dist/list.js +65 -0
  23. package/dist/list.js.map +1 -0
  24. package/dist/symlink.d.ts +41 -0
  25. package/dist/symlink.d.ts.map +1 -0
  26. package/dist/symlink.js +233 -0
  27. package/dist/symlink.js.map +1 -0
  28. package/package.json +72 -0
  29. package/skills/lyt-capture/SKILL.md +137 -0
  30. package/skills/lyt-decision/SKILL.md +52 -0
  31. package/skills/lyt-handoff/SKILL.md +52 -0
  32. package/skills/lyt-insight/SKILL.md +55 -0
  33. package/skills/lyt-mesh-explore/SKILL.md +190 -0
  34. package/skills/lyt-pattern/SKILL.md +71 -0
  35. package/skills/lyt-plan/SKILL.md +60 -0
  36. package/skills/lyt-pod/SKILL.md +205 -0
  37. package/skills/lyt-primer-context/SKILL.md +206 -0
  38. package/skills/lyt-progress/SKILL.md +48 -0
  39. package/skills/lyt-recall/SKILL.md +98 -0
  40. package/skills/lyt-result/SKILL.md +49 -0
  41. package/skills/lyt-retro/SKILL.md +54 -0
  42. package/skills/lyt-search/SKILL.md +144 -0
  43. package/skills/lyt-sync/SKILL.md +145 -0
@@ -0,0 +1,205 @@
1
+ ---
2
+ name: lyt-pod
3
+ description: >
4
+ Overview of the user's Lyt pod — enumerates all meshes and vaults on this machine, grouped by mesh, with orphan vaults surfaced separately and summary stats (mesh count, vault count, pushable/subscriber/orphan breakdown). Trigger when the user runs /lyt-pod, or says "what's in my pod", "show me my pod", "give me a pod overview", "list all my vaults", "what meshes do I have", "show me everything in my pod", or similar phrasing on a pod-scoped enumeration. Composes `lyt mesh list --json` (mesh-level records) + `lyt vault list --json` (vault-level records) into one agent-facing summary. Read-only; pairs with /lyt-primer-context (agent priming with active arcs + writable status) and /lyt-search (query across the pod).
5
+ visibility: public
6
+ lyt-version: 0.7.0
7
+ capabilities: [read]
8
+ runtimes: [claude, codex, agents]
9
+ requires_writable_vault: false
10
+ ---
11
+
12
+ # /lyt-pod
13
+
14
+ Render an agent-facing overview of the user's Lyt **pod** — every mesh and every vault on this machine — by composing two CLI verbs:
15
+
16
+ 1. `lyt mesh list --json` (shipped v1.B.1) — enumerates meshes the user participates in, including each mesh's main vault, home vaults, and subscribed vaults. Canonical mesh-enumeration verb per `packages/lyt-vault/src/commands/mesh.ts:277` (`buildMeshListSubcommand`).
17
+ 2. `lyt vault list --json` (shipped pre-v1.G.1) — enumerates every registered vault on the machine, with status, path, and per-vault metadata (mesh role, parent vault, tier hint). Canonical vault-enumeration verb per `packages/lyt-vault/src/commands/list.ts:6` (`buildListCommand`).
18
+
19
+ The skill is pure prose around two existing CLI verbs — there is no new CLI verb, no new helper, no lyt-vault change. Both verbs always run on every invocation (default = full pod overview); user signal can narrow the synthesis focus post-facto but does NOT change which verbs run.
20
+
21
+ User-facing language uses **"pod"** throughout — never "federation". "Mesh" stays user-facing (it's the actual unit of grouping). "Federation" is reserved for internal data-layer prose.
22
+
23
+ ## When to invoke
24
+
25
+ When the user runs `/lyt-pod`, or says something like:
26
+
27
+ - "what's in my pod"
28
+ - "show me my pod"
29
+ - "give me a pod overview"
30
+ - "list all my vaults"
31
+ - "what meshes do I have"
32
+ - "show me everything in my pod"
33
+ - "summarize my Lyt setup"
34
+ - "what's on this machine"
35
+
36
+ Invoke this skill **proactively** as the first move whenever the user asks a pod-scoped enumeration question or seems to want a survey of what's installed. Don't bypass it and start grep'ing the filesystem — the registry is the source of truth.
37
+
38
+ If the user wants to drill into a single mesh (vault list + edges for one mesh), prefer `/lyt-mesh-explore` (post-Wave-3 G.9) once it ships. If the user wants per-vault writable status or agent priming, use `/lyt-primer-context`.
39
+
40
+ ## Phase 1 — Determine pod-scope intent
41
+
42
+ The default is **full pod overview** — both verbs run, every mesh and vault rendered. Pick by the user's wording:
43
+
44
+ - **Default — full pod overview.** Use when the user says "my pod", "show me everything", "list all vaults", "what meshes do I have", or omits scope entirely. Run both verbs (Phase 2 + Phase 3) and synthesize a complete pod summary in Phase 4.
45
+ - **Narrow framing on a single mesh.** Use when the user says "focus on the `<name>` mesh", "just show me the `<name>` mesh's vaults", "what's in the `<name>` mesh". **Still run BOTH `lyt mesh list --json` and `lyt vault list --json`** — the CLI verbs do not support `--mesh` filtering on `lyt vault list`. Apply the user's narrow framing at **synthesis time** (Phase 4) by filtering the rendered output. Do NOT invent a CLI flag.
46
+ - **Tombstoned-vault inclusion.** Default = hide soft-tombstoned rollup aggregates (matches CLI default per `packages/lyt-vault/src/commands/list.ts:11-19`). Pass `--include-tombstones` ONLY when the user explicitly says "show tombstoned vaults too", "include deleted vaults", "show buried vaults". Hard-tombstoned vaults (`status='tombstoned'`) are included in the default `lyt vault list` output already; `--no-tombstones` filters them out (do NOT pass by default — they are part of the pod's recent history).
47
+
48
+ The skill never invents mesh or vault names. If the user names one and the post-Phase-2/3 synthesis can't match it, surface the available names and stop — do not guess.
49
+
50
+ ## Phase 2 — Enumerate meshes
51
+
52
+ Run the verb via the Bash tool (or your runtime's shell equivalent). **Pass the argv as an array; never shell-compose the command.** Precedent: lyt-sync's Phase 3 (`spawnSync("git", [..., "-m", message])`), lyt-search's Phase 2 (`spawnSync("lyt", ["search", userQuery, "--json"])`), lyt-primer-context's Phase 2 (`spawnSync("lyt", ["primer", "--scope", scope, ...])`) — same argv-array shape, cross-platform-safe.
53
+
54
+ ```
55
+ # Shell-syntax (DOCUMENTATION ONLY — do NOT compose this as a string):
56
+ lyt mesh list --json
57
+
58
+ # Actual exec shape (argv array; cross-platform-safe):
59
+ spawnSync("lyt", ["mesh", "list", "--json"]);
60
+ ```
61
+
62
+ The CLI emits Lock 0.3 stable-key-ordered JSON on stdout (exit 0 on success). The actual emitted shape (per `packages/lyt-vault/src/commands/mesh.ts:283-317`):
63
+
64
+ ```json
65
+ {
66
+ "meshes": [
67
+ {
68
+ "rid": "mesh:<hex>",
69
+ "rid_hex": "<hex>",
70
+ "name": "<mesh-name>",
71
+ "push_target": "<gh-target>" | null,
72
+ "push_kind": "handle" | "org" | null,
73
+ "main_vault": {
74
+ "rid": "vault:<hex>",
75
+ "rid_hex": "<hex>",
76
+ "name": "<vault-name>"
77
+ } | null,
78
+ "home_vaults": [
79
+ { "rid": "vault:<hex>", "rid_hex": "<hex>", "name": "<vault-name>" }
80
+ ],
81
+ "subscribed_vaults": [
82
+ { "rid": "vault:<hex>", "rid_hex": "<hex>", "name": "<vault-name>" }
83
+ ]
84
+ }
85
+ ]
86
+ }
87
+ ```
88
+
89
+ `home_vaults` includes the main vault (it's a home vault with the additional `★` marker captured separately as `main_vault.rid_hex`). `subscribed_vaults` is the cross-mesh subscription role (mesh M subscribes to vault V owned by another mesh).
90
+
91
+ Empty registry: `{ "meshes": [] }`. Surface "no meshes yet — run `lyt mesh init <name>` to create one" in Phase 4 if both meshes AND vaults arrays are empty.
92
+
93
+ ## Phase 3 — Enumerate vaults
94
+
95
+ Same argv-array invocation pattern.
96
+
97
+ ```
98
+ # Shell-syntax (DOCUMENTATION ONLY):
99
+ lyt vault list --json
100
+
101
+ # Actual exec shape:
102
+ spawnSync("lyt", ["vault", "list", "--json"]);
103
+
104
+ # Counter-case — user explicitly asked for tombstoned-rollup inclusion:
105
+ spawnSync("lyt", ["vault", "list", "--json", "--include-tombstones"]);
106
+ ```
107
+
108
+ The CLI emits Lock 0.3 stable-key-ordered JSON on stdout (per `packages/lyt-vault/src/commands/list.ts:46-49` + `packages/lyt-vault/src/flows/list.ts:32-40`):
109
+
110
+ ```json
111
+ {
112
+ "vaults": [
113
+ {
114
+ "rid": { "0": <int>, "1": <int>, "...": <int>, "15": <int> },
115
+ "ridHex": "<hex>",
116
+ "name": "<vault-name>",
117
+ "path": "<absolute-path>",
118
+ "memscopeRid": { "0": <int>, ... } | null,
119
+ "memscopeRidHex": "<hex>" | null,
120
+ "parentVault": { "0": <int>, ... } | null,
121
+ "parentVaultHex": "<hex>" | null,
122
+ "homeMeshRid": { "0": <int>, ... } | null,
123
+ "homeMeshRidHex": "<hex>" | null,
124
+ "tierHint": "<string>" | null,
125
+ "status": "active" | "disconnected" | "missing" | "tombstoned" | "access_lost",
126
+ "gitUrl": "<url>" | null,
127
+ "createdAt": "<iso>" | null,
128
+ "registeredAt": "<iso>",
129
+ "lastVerifiedAt": "<iso>" | null,
130
+ "verifyFailCount": 0
131
+ }
132
+ ],
133
+ "rollupTombstones": { ... }, // only when --include-tombstones is passed
134
+ "rollupThresholdDays": <int>, // only when --include-tombstones is passed
135
+ "rollupThresholdIso": "<iso>" // only when --include-tombstones is passed
136
+ }
137
+ ```
138
+
139
+ **Field-type note (release review).** The four byte-typed fields (`rid`, `memscopeRid`, `parentVault`, `homeMeshRid`) are `Uint8Array` instances at the source (`packages/lyt-vault/src/registry/repo.ts:22-32`) and pass through `JSON.stringify(result, null, 2)` raw at `commands/list.ts:48`. `JSON.stringify` serializes a `Uint8Array` as a **byte-indexed object** (`{"0": 123, "1": 45, ..., "15": 254}`), NOT a hex string. **Always match on the `*Hex` companion fields** (`ridHex`, `memscopeRidHex`, `parentVaultHex`, `homeMeshRidHex`) — those are guaranteed-string and stable. Treat the raw byte-fields as opaque implementation detail.
140
+
141
+ The vault-list output is the source of truth for **per-vault mesh membership** — match each vault's `homeMeshRidHex` (string) against each mesh's `rid_hex` (string) from Phase 2 to group vaults under their mesh in Phase 4. A vault with `homeMeshRidHex === null` is an **orphan** (registered but not adopted into any mesh — see Phase 4's orphan section).
142
+
143
+ Empty registry: `{ "vaults": [] }`. Surface "no vaults registered yet — run `lyt vault init <name>` to create one" in Phase 4 if both meshes AND vaults arrays are empty.
144
+
145
+ ## Phase 4 — Synthesize pod-overview
146
+
147
+ Render the pod summary as a markdown block. The handler-facing layout:
148
+
149
+ ```
150
+ # Your pod
151
+
152
+ **Summary:** <N> mesh<es> · <M> vault<s> (<P> pushable · <S> subscriber · <O> orphan)
153
+
154
+ ## Meshes
155
+
156
+ ### `<mesh-1-name>` (<K> home vault<s><, J subscribed>)
157
+
158
+ - ★ `<main-vault-name>` — main vault · push target: `<push_kind>:<push_target>`
159
+ - `<home-vault-name>` — home vault
160
+ - ...
161
+ - `<subscribed-vault-name>` — subscribed (cross-mesh)
162
+
163
+ ### `<mesh-2-name>` (<K> home vault<s>)
164
+
165
+ - ★ `<main-vault-name>` — main vault
166
+ - ...
167
+
168
+ ## Orphan vaults (no mesh role)
169
+
170
+ - `<orphan-vault-name>` — heal via `lyt repair --target <orphan-vault-name> --apply --mesh <mesh>` (binds a registered vault to a mesh); `lyt mesh adopt` discovers + adopts gh clusters
171
+ - ...
172
+ ```
173
+
174
+ Synthesis rules:
175
+
176
+ - **Summary line.** `N meshes` = `meshes.length` from Phase 2. `M vaults` = `vaults.length` from Phase 3 (filter out `status='tombstoned'` unless the user explicitly asked for tombstoned inclusion). The `(P pushable · S subscriber · O orphan)` breakdown counts each vault **once** by primary role, with precedence **home > subscriber > orphan** (a vault appearing in BOTH a `home_vaults` array AND any `subscribed_vaults` array is counted as **home**, not subscriber): a vault is **pushable** if it appears in any mesh's `home_vaults` AND that mesh has a non-null `push_target`; **subscriber** if it appears ONLY in `subscribed_vaults` arrays across all meshes (never as a home vault); **orphan** if its `homeMeshRidHex === null` (no mesh role at all).
177
+ - **Mesh grouping.** Sort meshes by name (alphabetical) for stable rendering. Within each mesh: main vault first (marked `★` per `commands/mesh.ts:333` precedent), then other home vaults sorted alphabetically (exclude the main-vault entry from this alphabetic list — it already rendered above with `★`; `home_vaults` includes the main vault per Phase 2 shape, so an LLM iterating the array verbatim would otherwise double-render the main vault), then subscribed vaults grouped at the end with a "subscribed (cross-mesh)" hint.
178
+ - **Push-target hint.** Surface `push target: <push_kind>:<push_target>` next to the main vault when `push_target !== null`. Skip the hint when null (mesh is local-only).
179
+ - **Orphan section.** Always include the heading even when empty (rendering "(none)" under it) — handlers parsing the output can rely on the section's presence. Each orphan vault gets a one-line heal suggestion: `lyt repair --target <orphan-vault-name> --apply --mesh <mesh>` (the canonical heal — binds a registered vault to a known mesh). A vault that is _registered-but-mesh-unlinked_ (the adopt mesh-link drift) heals via `lyt repair --apply` with **no args** (`lyt doctor` flags it). `lyt mesh adopt` remains for gh **cluster-discovery** of un-registered repos — not for re-linking an already-registered vault.
180
+ - **User narrow framing.** If the user signaled a single mesh in Phase 1, render only that mesh's section under `## Meshes` plus the orphan section. Surface a one-line "(showing 1 of N meshes — re-invoke /lyt-pod for full overview)" hint.
181
+ - **Large pod truncation.** If the combined vault count exceeds ~50 across all meshes, render the summary line + per-mesh counts and offer a "show all with `lyt vault list`" follow-up rather than dumping every vault inline. Do not silently drop entries.
182
+ - **Empty pod.** If both `meshes.length === 0` AND `vaults.length === 0`, render: "**Your pod is empty.** Run `lyt mesh init <name>` to create your first mesh, or `lyt vault init <name>` to register a standalone vault. See `/lyt-mesh-explore` once you have one."
183
+ - **Use "pod" framing throughout.** Never write "federation" in handler-facing prose. "Mesh" is user-facing (the actual group). "Pod" is the user's set of meshes + vaults on this machine.
184
+
185
+ ## Rules
186
+
187
+ - **MUST pass argv as an array** (`spawnSync("lyt", ["mesh", "list", "--json"])` and `spawnSync("lyt", ["vault", "list", "--json"])`), not template-interpolated into a shell command string. Both verbs accept simple argv with no user-supplied tokens, so the shell-injection surface is small — but argv parity matches lyt-sync + lyt-search + lyt-primer-context for cross-platform reliability.
188
+ - **MUST pass `--json`** on every invocation. Human-readable output is not a contract this skill parses.
189
+ - **MUST run BOTH verbs on every invocation.** The default is full pod overview; even when the user signals a narrow mesh framing, the vault list is needed to compute the orphan section and the summary-line counts. Do not skip one verb to "save time" — synthesis quality drops.
190
+ - **MUST use "pod" framing in user-facing output.** Never write "federation" in handler-facing prose; "federation" is internal data-layer vocabulary only.
191
+ - **MUST surface the orphan-vault section** even when empty (render "(none)" under the heading) so handlers can rely on its presence.
192
+ - **MUST cite `lyt mesh list` as the canonical mesh-enumeration verb.** Some sibling SKILL.md files cite a different mesh-enumeration verb that does not exist; the canonical verb is `lyt mesh list` per `packages/lyt-vault/src/commands/mesh.ts:277`. Do not propagate the sibling error here.
193
+ - **MUST cite `lyt vault info <name>` with a positional argument only.** The verb accepts a positional `<name>` per `packages/lyt-vault/src/commands/info.ts:20-26`; the only flag is `--json`. The pod skill does not call `vault info` at all (per-vault writable status is `/lyt-primer-context`'s job — pulling it here would duplicate that surface).
194
+ - **MUST NOT pass `--include-tombstones` by default.** Pass only on explicit user signal ("show tombstoned vaults", "include deleted vaults", "show buried vaults"). Default = hide soft-tombstoned rollup aggregates per CLI default.
195
+ - **MUST NOT pass `--no-tombstones` by default.** Hard-tombstoned vaults (`status='tombstoned'`) are part of the pod's recent history; rendering them with a `[tombstoned]` status marker is the correct default. Pass `--no-tombstones` only on explicit user signal ("hide tombstones", "skip buried vaults").
196
+ - **MUST NOT modify or write any file.** This is a read-only skill (`requires_writable_vault: false`). If the user wants the pod overview persisted to a Figment, run `/lyt-capture` separately on the formatted output.
197
+ - **MUST NOT shell-compose any verb invocation.** Argv-array always (parity with lyt-sync + lyt-search + lyt-primer-context).
198
+ - **MUST NOT invent CLI flags for filtering.** The CLI verbs do not support `--mesh` filtering on `lyt vault list`; user narrow framing is synthesis-time filtering in Phase 4, not CLI-level filtering.
199
+
200
+ ## Companion skills
201
+
202
+ - **/lyt-mesh-explore** — drill into a single mesh (vault list + edges + subscriptions). Pair after `/lyt-pod` when the user picks one mesh to investigate (post-Wave-3 G.9).
203
+ - **/lyt-primer-context** — prime an agent with Lyt-scoped context (top keywords, active arcs, writable status). Pair after `/lyt-pod` when the user wants the agent to start working in a specific vault — use `--scope vault --target <name>` per the chosen vault.
204
+ - **/lyt-search** — query across the pod with the tiered-cascade engine. Pair after `/lyt-pod` when the user wants to look up specific content rather than survey what exists.
205
+ - **/lyt-sync** — pull/commit/push a vault. Run before `/lyt-pod` if the user has unpushed local edits and wants the registry to reflect them (registry rows update on vault init/adopt; `/lyt-sync` doesn't change the pod shape but does freshen `lastVerifiedAt`).
@@ -0,0 +1,206 @@
1
+ ---
2
+ name: lyt-primer-context
3
+ description: >
4
+ Prime an agent with Lyt-scoped context — for a vault, a mesh, or the whole pod — by composing `lyt primer` (top keywords + active arcs + recent activity + top lanes) and `lyt vault info --json` (writable status for vault-scope). Trigger when the user runs /lyt-primer-context, or says "prime me for X", "give me context on this vault", "what's been happening in my pod lately", "what arcs are active in mesh Y", "give the agent context before X", or similar phrasing on a scope they want surfaced for agent priming. Wraps `lyt primer` (v1.D.4) + `lyt vault info --json` (v1.G.2 6-reason writable contract) — composes both into an agent-facing summary. Read-only; pairs with /lyt-search (query-driven recall) and /lyt-capture (write).
5
+ visibility: public
6
+ lyt-version: 0.6.0
7
+ capabilities: [read]
8
+ runtimes: [claude, codex, agents]
9
+ requires_writable_vault: false
10
+ ---
11
+
12
+ # /lyt-primer-context
13
+
14
+ Prime an agent with Lyt-scoped context for a **vault**, a **mesh**, or the whole **pod** by composing two CLI verbs:
15
+
16
+ 1. `lyt primer --scope <vault|mesh|federation> [--target <name>] --json --dry-run` (shipped v1.D.4) — aggregates top keywords, active arcs, recent activity, and top lanes across the scope into a Lock 0.3 stable-key-ordered JSON payload (including the full primer markdown body).
17
+ 2. `lyt vault info <name> --json` (shipped v1.G.2; 6-reason writable contract) — only for vault-scope priming, fetches `writable` + `writableDetermination` so the skill can surface a capability hint to the agent ("you can /lyt-capture here" vs reason-specific guidance).
18
+
19
+ The skill is pure prose around two existing CLI verbs — there is no new CLI verb, no new helper, no lyt-vault change. The skill READS; it does not write (except the CLI's atomic primer-file write on non-dry-run, which is opt-in per Phase 2 the ratified default).
20
+
21
+ ## When to invoke
22
+
23
+ When the user runs `/lyt-primer-context`, or says something like:
24
+
25
+ - "prime me for `<vault|mesh|pod-scoped task>`"
26
+ - "give me context on this vault"
27
+ - "what's been happening in my pod lately"
28
+ - "what arcs are active in mesh `<name>`"
29
+ - "give the agent context before `<task>`"
30
+ - "prime the agent for working in `<vault>`"
31
+ - "what's the current state of my `<mesh>` mesh"
32
+
33
+ Invoke this skill **proactively** before a knowledge-work task whenever the agent needs scope-wide situational awareness (recent activity, dominant themes, in-progress arcs). Don't bypass it and start fabricating context.
34
+
35
+ ## Phase 1 — Determine scope + target from user signal
36
+
37
+ The `lyt primer` verb requires `--scope` and rejects ambiguity. Pick by the user's wording (default is federation when no scope signal):
38
+
39
+ - **Default — federation (entire pod, every vault across every mesh).** Use when the user says "my pod", "all my vaults", "across everything", or omits scope entirely. Invocation: `lyt primer --scope federation --json --dry-run` (no `--target`; CLI ignores it for federation scope).
40
+ - **Single mesh.** Use `--scope mesh --target <name>` when the user says "in mesh `<name>`", "for the `<name>` mesh", "across my `<name>` mesh".
41
+ - **Single vault.** Use `--scope vault --target <name>` when the user says "in vault `<name>`", "for my `<name>` vault", "for this vault". For "this vault", resolve from the env-default chain (mirrors lyt-sync Phase 1): `$LYT_ACTIVE_VAULT` env var, then `~/lyt/vaults/<handle>/main/` convention, then ask the user — do not guess from cwd.
42
+
43
+ **Resolve names before passing them.** Don't guess at mesh/vault names — when the user names one:
44
+
45
+ 1. Run `lyt vault list --json` (vaults) or `lyt mesh list --json` (meshes) first. `lyt mesh list` is the canonical mesh-enumeration verb (per `packages/lyt-vault/src/commands/mesh.ts:32`); both verbs emit Lock 0.3 stable-key-ordered JSON on `--json`.
46
+ 2. Match the user's term to the listed names (exact, then case-insensitive, then prefix).
47
+ 3. **Reject any resolved name that begins with `-` or `--`** before passing it to `--target <name>` — closes the flag-injection surface the same way lyt-sync (Phase 1) and lyt-search (Phase 1) do (family: G.2 CR-1 gh-flag-injection). Vault and mesh names are user-controlled at vault-init / mesh-create time; a vault literally named `--evil` would otherwise smuggle a flag-shaped token into the verb's argv.
48
+ 4. If no match (or the only match is `--`-leading), tell the user the available names and stop — do not invent a name.
49
+
50
+ The `--scope federation` invocation MUST NOT pass `--target` — the CLI ignores it for federation scope but it's noise; only pass `--target` for vault/mesh scopes.
51
+
52
+ ## Phase 2 — Invoke `lyt primer`
53
+
54
+ Run the verb via the Bash tool (or your runtime's shell equivalent). **Pass scope and target as separate argv arguments; never shell-compose the command.** The matching precedent is lyt-search's Phase 2 (`spawnSync("lyt", ["search", userQuery, "--json"])`) and lyt-sync's Phase 3 (`spawnSync("git", ["-C", vaultPath, "commit", "-m", message])`) — argv-array shape, cross-platform-safe.
55
+
56
+ ```
57
+ # Shell-syntax (DOCUMENTATION ONLY — do NOT compose this as a string):
58
+ lyt primer --scope <scope> [--target <name>] --json --dry-run
59
+
60
+ # Actual exec shape (argv array; cross-platform-safe):
61
+ spawnSync("lyt", ["primer", "--scope", scope, "--target", target, "--json", "--dry-run"]);
62
+ # or for federation scope (no --target):
63
+ spawnSync("lyt", ["primer", "--scope", "federation", "--json", "--dry-run"]);
64
+ ```
65
+
66
+ Key rules:
67
+
68
+ - `--scope` is **mandatory** (CLI rejects with `error: "invalid-scope"`, exit 1, if missing or unrecognised). The skill always passes one; default to `federation` when no user signal.
69
+ - `--target <name>` is **required** for `--scope vault` and `--scope mesh`; **omitted** for `--scope federation`. CLI rejects missing target with `error: "missing-target"`, exit 1.
70
+ - `--json` is **mandatory** for this skill. Without it, the CLI prints human-readable output that the skill can't reliably parse.
71
+ - `--dry-run` is the **default for this skill** (ratified default). The CLI's non-dry-run mode atomically writes the primer markdown to `<vault>/.lyt/primers/{scope}-primer.md`; the skill READS the result for agent priming and does not need that persisted file as a side-effect of every invocation. Pass `--dry-run` unless the user explicitly asks to regenerate the on-disk primer ("refresh the primer file", "regenerate the on-disk primer" — then omit `--dry-run`).
72
+ - `--top-keywords <n>`, `--top-arcs <n>`, `--provenance-days <n>` are advanced flags. Apply only when the user explicitly signals a cap ("top 50 keywords", "last 30 days of activity"); otherwise rely on CLI defaults (20 / 10 / 7).
73
+
74
+ ## Phase 3 — Parse the JSON output
75
+
76
+ The CLI emits Lock 0.3 stable-key-ordered JSON on stdout (exit 0 on success). The actual emitted shape (per `packages/lyt/src/commands/primer.ts:174-215`):
77
+
78
+ ```json
79
+ {
80
+ "scope": "vault" | "mesh" | "federation",
81
+ "scopeTarget": "<name>" | null,
82
+ "primerPath": "<vault>/.lyt/primers/<scope>-primer.md" | null,
83
+ "dryRun": true | false,
84
+ "vaultsScanned": ["<vault1>", "<vault2>"],
85
+ "topKeywords": [
86
+ { "keyword": "<term>", "score": 0.92, "totalMemCount": 12, "lastSeen": "ISO8601" }
87
+ ],
88
+ "topArcs": [
89
+ {
90
+ "name": "<arc-name>",
91
+ "category": "<category>",
92
+ "lastTouched": "ISO8601",
93
+ "vaultName": "<vault>",
94
+ "memberCount": 7
95
+ }
96
+ ],
97
+ "recentActivity": [
98
+ {
99
+ "ts": 1717200000,
100
+ "tsIso": "ISO8601",
101
+ "targetType": "<kind>",
102
+ "targetId": "<rid-or-id>",
103
+ "src": "<source>",
104
+ "vaultName": "<vault>",
105
+ "idHex": "<rid-hex>"
106
+ }
107
+ ],
108
+ "topLanes": [
109
+ { "name": "<lane-name>", "keywords": ["<kw1>", "<kw2>"], "memCount": 5, "vaultName": "<vault>" }
110
+ ],
111
+ "markdown": "<full primer markdown body — what would be written to .lyt/primers/{scope}-primer.md>",
112
+ "durationMs": 47
113
+ }
114
+ ```
115
+
116
+ On `--dry-run`: `primerPath` is the path the CLI WOULD write to (not null — it's pre-computed), but no file is written. `dryRun: true` confirms this. On non-dry-run: `dryRun: false` and the file at `primerPath` is freshly written (atomic).
117
+
118
+ Failure modes (CLI emits to stderr; exit non-zero):
119
+
120
+ - **Invalid scope** (exit 1) → `{ "error": "invalid-scope", "value": "<bad>", "message": "..." }`. Skill-level bug if hit — Phase 1 should have prevented it; surface the message and stop.
121
+ - **Missing target** (exit 1) → `{ "error": "missing-target", "scope": "<vault|mesh>", "message": "..." }`. Skill-level bug — Phase 1 should have resolved a name; surface and stop.
122
+ - **Invalid `--top-keywords` / `--top-arcs` / `--provenance-days`** (exit 1) → `{ "error": "invalid-<flag>", "value": "<bad>", "message": "..." }`. Re-invoke with CLI defaults.
123
+ - **Underlying flow throws** (exit 2) → `{ "error": "primer-generate-error", "message": "..." }`. Surface verbatim; suggest a narrower scope.
124
+
125
+ ## Phase 4 — Fetch writable status (vault-scope ONLY)
126
+
127
+ **Skip this phase for `--scope mesh` and `--scope federation`** — those scopes span multiple vaults and there's no single writable status to surface (per the ratified default). For mesh/federation, jump to Phase 5 and present the primer summary alone. The agent can re-invoke `/lyt-primer-context` per-vault with `--scope vault --target <name>` if it needs write-action guidance for a specific vault.
128
+
129
+ For `--scope vault --target <name>`, invoke `lyt vault info <name> --json` via Bash (argv-array form):
130
+
131
+ ```
132
+ # Shell-syntax (DOCUMENTATION ONLY):
133
+ lyt vault info <name> --json
134
+
135
+ # Actual exec shape:
136
+ # `vaultName` MUST be the same Phase-1-resolved name (already passed through
137
+ # the `--`-leading rejection check); do not re-resolve from a different source
138
+ # at Phase 4, or the flag-injection defense is dropped.
139
+ spawnSync("lyt", ["vault", "info", vaultName, "--json"]);
140
+ ```
141
+
142
+ Parse the `vault.writable` + `vault.writableDetermination` fields per the v1.G.2 read-only-awareness contract (see `packages/lyt-vault/src/flows/writability.ts:42-48`). The verdict is tri-state (`true | false | "unknown"`); the determination is one of **6 reasons** the skill must branch on explicitly in Phase 5.
143
+
144
+ ## Phase 5 — Synthesize agent-facing context
145
+
146
+ Render the agent-priming output as a markdown block. Layout:
147
+
148
+ ```
149
+ # Primer for <scope>: <target-or-pod>
150
+
151
+ **Top keywords:** <keyword1> (<score1>) · <keyword2> (<score2>) · … · <keywordN> (<scoreN>)
152
+
153
+ **Active arcs (top-N):**
154
+ - <arc-name> · <category> · last touched <ISO> · vault <vault> · <memberCount> members
155
+ - …
156
+
157
+ **Active lanes (top-N):**
158
+ - <lane-name> · keywords [<kw1>, <kw2>] · <memCount> members · vault <vault>
159
+ - …
160
+
161
+ **Recent activity (last N days):**
162
+ - <tsIso> — <targetType> in <vaultName>: <targetId>
163
+ - …
164
+
165
+ **Capability hint (vault-scope only):**
166
+ <one of the 6 reason-specific messages — see the table below>
167
+
168
+ **Primer markdown** (full body, truncated to ≤200 lines with ellipsis if longer):
169
+ <markdown payload from CLI>
170
+ ```
171
+
172
+ ### Capability hint — 6-reason writable contract (vault-scope only)
173
+
174
+ For vault-scope invocations, surface a reason-specific capability hint based on `writable` + `writableDetermination`. The actual reason strings emitted by `vault info --json` (per `packages/lyt-vault/src/flows/writability.ts`) are listed in the **emitted name** column. The **semantic name** column gives the human-readable synonym some briefs use; the SKILL.md handler-facing prose uses the semantic name, but the comparison MUST be against the emitted name.
175
+
176
+ | Emitted name (writableDetermination) | Semantic name | writable | Phase 5 capability hint |
177
+ | ------------------------------------ | --------------------------- | ----------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
178
+ | `gh-viewerCanPush-true` | **home-pushable-true** | `true` | ✓ This vault is yours and pushable — you can `/lyt-capture` here. |
179
+ | `gh-viewerCanPush-false` | **home-not-pushable-false** | `false` | ⚠ This vault is yours but you lack push permission. Request write access from the owner, or capture into a vault you own. |
180
+ | `subscriber-default-false` | (subscriber) | `false` | ⚠ This is a subscriber vault — pull-only. Capture into your home vault instead. |
181
+ | `gh-unavailable` | (gh-offline) | `"unknown"` | ⚠ Writable status unknown — gh CLI offline / rate-limited. Re-check when network is available. |
182
+ | `no-remote` | (no-remote) | `"unknown"` | ⚠ Writable status unknown — vault has no git remote configured. Configure with `gh repo create` or `git remote add origin <url>`. |
183
+ | `orphan-vault` | (orphan) | `"unknown"` | ⚠ Writable status unknown — vault has no mesh role (orphan). Heal: `lyt repair --apply` (fixes the adopt mesh-link drift, no args needed); a truly un-adopted vault: `lyt repair --target <vault> --apply --mesh <mesh>`. `lyt doctor` diagnoses. |
184
+
185
+ **Note on emitted vs semantic names.** The brief that authored this skill (v1.G.7 handoff) lists `home-pushable-true` / `home-not-pushable-false` as semantic aliases for the first two reasons. The actual strings emitted by `writability.ts` are `gh-viewerCanPush-true` / `gh-viewerCanPush-false`. The semantic names are kept here as documentation aliases so future renames of the underlying enum (e.g. when the gh-probe naming hardens in v1.G.2.1) don't silently break the skill prose. The 4 unchanged reason strings (`subscriber-default-false`, `gh-unavailable`, `no-remote`, `orphan-vault`) match in both surfaces. **Comparison code MUST use the emitted name; handler-facing prose uses either.**
186
+
187
+ ## Rules
188
+
189
+ - **MUST pass `--scope`, `--target` (if applicable), and `--json` as separate argv arguments**, not template-interpolated into a shell command string. Mesh/vault names CAN contain shell metacharacters (backticks, `$()`, `;`, `&&`) — those MUST be conveyed as one argv element per name.
190
+ - **MUST pass `--json`** on every invocation. Human-readable output is not a contract this skill parses.
191
+ - **MUST pass `--dry-run`** UNLESS the user explicitly asks to regenerate the on-disk primer file (the ratified default counter-case). Otherwise every priming call pollutes `<vault>/.lyt/primers/`.
192
+ - **MUST resolve mesh/vault names via `lyt vault list --json` or `lyt mesh list --json` before passing `--target`.** Do not guess names.
193
+ - **MUST reject `--`-leading names** from `lyt vault list --json` / `lyt mesh list --json` results before passing them to `--target` (G.6 inherited defense; family: G.2 CR-1 gh-flag-injection).
194
+ - **MUST branch on all 6 writable reasons in Phase 5 (vault-scope).** Each has a distinct capability hint; collapsing them into a generic "can't write" message loses semantic signal the agent needs to recover.
195
+ - **MUST NOT call `lyt primer` without `--scope`.** The CLI rejects with `error: "invalid-scope"`, exit 1.
196
+ - **MUST NOT call `lyt primer` with `--scope vault` or `--scope mesh` without `--target`.** The CLI rejects with `error: "missing-target"`, exit 1.
197
+ - **MUST NOT call `lyt vault info` for `--scope mesh` or `--scope federation`.** Phase 4 is skipped for those scopes (the ratified default); the primer summary alone is the output.
198
+ - **MUST NOT modify or write any file.** This is a read-only skill (`requires_writable_vault: false`). The CLI's atomic primer-file write on non-dry-run is opt-in via the the ratified default counter-case; the skill itself never writes.
199
+ - **MUST NOT compose shell command strings.** Argv-array always (parity with lyt-sync + lyt-search).
200
+ - **MUST NOT silently degrade `writable === "unknown"` to a "writable" hint.** Surface the reason-specific guidance.
201
+
202
+ ## Companion skills
203
+
204
+ - **/lyt-search** — query-driven recall (NOT primer aggregation). Use after priming when the agent needs to look up specific content. Companion: prime first, then search the cued surfaces.
205
+ - **/lyt-capture** — write a Figment. Use after priming when the Phase 5 capability hint is `home-pushable-true` (✓) and the agent has a captureable insight.
206
+ - **/lyt-sync** — pull/commit/push a vault. Run BEFORE priming if the user has unpushed local edits and wants the primer's recent-activity surface to reflect them.
@@ -0,0 +1,48 @@
1
+ ---
2
+ name: lyt-progress
3
+ description: >
4
+ Write a mid-session progress update as a Lyt Figment. Trigger when the user runs /lyt-progress, or says "write a progress update", "log where we are", "status update", "I'm blocked". Wraps `lyt pattern run work-management progress`. Writes to <vault>/Projects/<project>/work/<date>-progress-<slug>.md.
5
+ visibility: public
6
+ lyt-version: 0.2.0
7
+ capabilities: [write]
8
+ runtimes: [claude, codex, agents]
9
+ requires_writable_vault: true
10
+ ---
11
+
12
+ # /lyt-progress
13
+
14
+ Capture mid-session status — where we are, what's done, what's in flight, blockers, next steps. Superseded by `/lyt-result` at session end.
15
+
16
+ ## When to invoke
17
+
18
+ - `/lyt-progress` slash trigger
19
+ - "where are we"
20
+ - "log progress" / "checkpoint" / "status update"
21
+ - when a session has been running >2hr OR has hit a blocker
22
+
23
+ ## Phase 1 — Resolve target
24
+
25
+ Same chain as `/lyt-plan`: `--vault` arg → `$LYT_ACTIVE_VAULT` → cwd detect → `<handle>/main` default. Project + slug similarly resolved.
26
+
27
+ ## Phase 2 — Run the verb
28
+
29
+ ```
30
+ lyt pattern run work-management progress --vault <vault> --project <project> --slug <slug>
31
+ ```
32
+
33
+ ## Phase 3 — Fill the body
34
+
35
+ Sections to fill:
36
+
37
+ - **Where we are** — one-paragraph state of play
38
+ - **What's done** — bullets
39
+ - **What's in flight** — bullets
40
+ - **Blockers** — bullets
41
+ - **Next steps** — bullets
42
+
43
+ If this progress closes a plan, set `parent_plan:` frontmatter to the wikilink of the plan.
44
+
45
+ ## Companion skills
46
+
47
+ - `/lyt-plan` — pre-action design (parent)
48
+ - `/lyt-result` — post-action outcome (closes this progress)
@@ -0,0 +1,98 @@
1
+ ---
2
+ name: lyt-recall
3
+ description: >
4
+ Search a Lyt vault by keyword. Trigger when the user runs /lyt-recall <query>, or asks "what did I write about X", "find my notes on X", "recall X from my vault", "search my vault for X", or similar phrasing. Returns matching Figments with relative path, title, and 2-line snippet around each match. Wraps `lyt pattern run knowledge-capture recall` for the report artifact (optional). Companion to lyt-capture.
5
+ visibility: public
6
+ lyt-version: 0.2.0
7
+ capabilities: [search]
8
+ runtimes: [claude, codex, agents]
9
+ requires_writable_vault: false
10
+ ---
11
+
12
+ # /lyt-recall
13
+
14
+ Search a Lyt vault by keyword. A Lyt vault is a folder of markdown Figments under `<vault>/notes/` (and elsewhere). v1 search is filesystem grep; libSQL FTS5 + vector ranking lands in a later phase.
15
+
16
+ ## When to invoke
17
+
18
+ When the user runs `/lyt-recall <query>`, or says something like:
19
+
20
+ - "what did I write about <topic>"
21
+ - "find my notes on <topic>"
22
+ - "recall <topic> from my vault"
23
+ - "search my vault for <topic>"
24
+ - "have I captured anything about <topic>"
25
+
26
+ If the user asks a question that depends on prior captured knowledge, invoke this skill proactively — don't fabricate; check the vault first.
27
+
28
+ ## Phase 1 — Resolve the target vault
29
+
30
+ Same resolution chain as `/lyt-capture`:
31
+
32
+ 1. `--vault <path>` arg
33
+ 2. `$LYT_ACTIVE_VAULT` env var
34
+ 3. cwd-based detection via `lyt vault info --by-path <cwd>`
35
+ 4. `~/lyt/vaults/<handle>/main/` default
36
+
37
+ If the resolved path is missing or has no `.lyt/vault.yon`, tell the user and stop — don't grep random directories.
38
+
39
+ ## Phase 2 — Search
40
+
41
+ 1. **Run the Grep tool** with:
42
+
43
+ - `pattern`: the user's query (case-insensitive by default)
44
+ - `path`: the resolved vault path
45
+ - `glob`: `**/*.md`
46
+ - `output_mode`: `content`
47
+ - `-i`: `true`
48
+ - `-n`: `true`
49
+ - `-C`: `2` (two lines of context around each match)
50
+ - `head_limit`: 30
51
+
52
+ 2. **If zero matches**, broaden the query:
53
+
54
+ - Split into individual terms (whitespace-separated).
55
+ - Run separate grep calls, one per term.
56
+ - Union the results.
57
+ - If still zero, tell the user: _"No Figments in `<vault>` match `<query>`. Try a broader term or different phrasing."_ Then stop.
58
+
59
+ ## Phase 3 — Present results
60
+
61
+ For each unique matching file (deduplicate by path), surface:
62
+
63
+ - **Path** — relative to the vault root (e.g., `notes/2026-05-24-q4-planning.md`)
64
+ - **Title** — read the file's frontmatter `title:` if present; otherwise the filename slug
65
+ - **Snippet** — the matched line plus 1 line of context above/below
66
+
67
+ Cap at the first 10 distinct files. If there are more, mention the count and offer to narrow the query.
68
+
69
+ Format example:
70
+
71
+ > **Found 3 matches in `~/lyt/vaults/<handle>/main/`:**
72
+ >
73
+ > 1. **notes/2026-05-24-q4-planning.md** — "Q4 planning"
74
+ > > ...the auth rewrite is a P0 for Q4...
75
+ > 2. **notes/2026-05-23-auth-decisions.md** — "Auth rewrite decisions"
76
+ > > ...moving to OAuth, deprecating session tokens by EOQ...
77
+
78
+ ## Optional: persist the recall report as a Figment
79
+
80
+ If the user wants the recall results saved (e.g., for inclusion in a `/lyt-plan` or `/lyt-result`), run:
81
+
82
+ ```
83
+ lyt pattern run knowledge-capture recall --vault <vault> --slug <query-as-slug>
84
+ ```
85
+
86
+ That writes a recall-report Figment at `<vault>/notes/recall-<date>-<slug>.md` with frontmatter capturing the query. The body is then filled in with the match list.
87
+
88
+ ## Rules
89
+
90
+ - **Never open or modify files** beyond the optional recall-report write.
91
+ - **Stay inside the resolved vault.** Don't grep the user's filesystem at large.
92
+ - **Don't fabricate hits.** If the grep returns nothing, say so.
93
+ - **Don't paraphrase across Figments.** Each match shown is the literal vault content; the user gets the raw recall, not a synthesis.
94
+ - libSQL FTS5 / vector / cross-vault search are deferred to a later phase. v1 is grep.
95
+
96
+ ## Companion skill
97
+
98
+ To add new content to the vault, use `/lyt-capture`.
@@ -0,0 +1,49 @@
1
+ ---
2
+ name: lyt-result
3
+ description: >
4
+ Write a post-action result as a Lyt Figment — the default catch-all at session end. Trigger when the user runs /lyt-result, or says "write a result", "what shipped", "wrap up the session", "log the outcome". Wraps `lyt pattern run work-management result`. Writes to <vault>/Projects/<project>/work/<date>-result-<slug>.md.
5
+ visibility: public
6
+ lyt-version: 0.2.0
7
+ capabilities: [write]
8
+ runtimes: [claude, codex, agents]
9
+ requires_writable_vault: true
10
+ ---
11
+
12
+ # /lyt-result
13
+
14
+ Capture the post-action outcome — what was delivered, what changed, what didn't get done. The default catch-all artifact at the end of every meaningful session.
15
+
16
+ ## When to invoke
17
+
18
+ - `/lyt-result` slash trigger
19
+ - session end: "wrap this up", "log the outcome"
20
+ - after a commit / push / deploy
21
+
22
+ ## Phase 1 — Resolve target
23
+
24
+ Same chain as `/lyt-plan`. Slug usually matches the parent plan's slug (set `parent_plan` frontmatter wikilink).
25
+
26
+ ## Phase 2 — Run the verb
27
+
28
+ ```
29
+ lyt pattern run work-management result --vault <vault> --project <project> --slug <slug>
30
+ ```
31
+
32
+ ## Phase 3 — Fill the body
33
+
34
+ Sections to fill:
35
+
36
+ - **Outcome** — what got delivered. Reference commits if applicable (set `commits:` frontmatter array).
37
+ - **What changed** — files, behaviors, decisions
38
+ - **What didn't get done** — deferred / blocked / cut
39
+ - **Cross-references** — plan link, commits, follow-ups
40
+
41
+ ## Promotion
42
+
43
+ If the result teaches something durable about THIS project, **rename in place** to `<date>-insight-<slug>.md` and update `type: insight` in frontmatter — no folder move, no link rot. If the lesson is project-agnostic, write a `Nuggets/<subject>/<date>-nugget-<slug>.md` instead.
44
+
45
+ ## Companion skills
46
+
47
+ - `/lyt-plan` — pre-action design (parent of this result)
48
+ - `/lyt-insight` — promoted result with durable project lesson
49
+ - `/lyt-retro` — deliberate retrospective after a meaningful arc