@lythos/skill-deck 0.14.2 → 0.14.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -8,16 +8,16 @@
8
8
 
9
9
  ```bash
10
10
  # Add a skill from skills.sh (owner/repo syntax — no conversion needed)
11
- bunx @lythos/skill-deck@0.14.2 add vercel-labs/agent-skills
11
+ bunx @lythos/skill-deck@0.14.4 add vercel-labs/agent-skills
12
12
 
13
13
  # Or with @skill filter (same as npx skills add):
14
- bunx @lythos/skill-deck@0.14.2 add mattpocock/skills@tdd
14
+ bunx @lythos/skill-deck@0.14.4 add mattpocock/skills@tdd
15
15
 
16
16
  # Or FQ locator:
17
- bunx @lythos/skill-deck@0.14.2 add github.com/anthropics/skills/skills/frontend-design
17
+ bunx @lythos/skill-deck@0.14.4 add github.com/anthropics/skills/skills/frontend-design
18
18
 
19
19
  # Sync working set (deny-by-default):
20
- bunx @lythos/skill-deck@0.14.2 link
20
+ bunx @lythos/skill-deck@0.14.4 link
21
21
  ```
22
22
 
23
23
  ## For AI Agents
@@ -25,7 +25,7 @@ bunx @lythos/skill-deck@0.14.2 link
25
25
  This package exposes a **CLI**. Invoke via:
26
26
 
27
27
  ```bash
28
- bunx @lythos/skill-deck@0.14.2 <command> [options]
28
+ bunx @lythos/skill-deck@0.14.4 <command> [options]
29
29
  ```
30
30
 
31
31
  No installation required. `bunx` auto-downloads the package.
@@ -73,15 +73,15 @@ prompt = "Search for latest info, then generate professional document with diagr
73
73
 
74
74
  | Situation | Command |
75
75
  |-----------|---------|
76
- | Sync working set with `skill-deck.toml` | `bunx @lythos/skill-deck@0.14.2 link` |
77
- | Validate `skill-deck.toml` before committing | `bunx @lythos/skill-deck@0.14.2 validate` |
78
- | Download a skill to cold pool and add to deck | `bunx @lythos/skill-deck@0.14.2 add owner/repo` |
79
- | Pull latest versions of declared skills | `bunx @lythos/skill-deck@0.14.2 refresh` |
80
- | Refresh a single skill by alias | `bunx @lythos/skill-deck@0.14.2 refresh tdd` |
81
- | Remove a skill from deck and working set | `bunx @lythos/skill-deck@0.14.2 remove tdd` |
82
- | Switch skill to symlink mode (live) | `bunx @lythos/skill-deck@0.14.2 to-symlink tdd` |
83
- | Switch skill to snapshot mode (pinned) | `bunx @lythos/skill-deck@0.14.2 to-snapshot tdd` |
84
- | Use a custom deck file or working dir | `bunx @lythos/skill-deck@0.14.2 link --deck ./my-deck.toml --workdir /path/to/project` |
76
+ | Sync working set with `skill-deck.toml` | `bunx @lythos/skill-deck@0.14.4 link` |
77
+ | Validate `skill-deck.toml` before committing | `bunx @lythos/skill-deck@0.14.4 validate` |
78
+ | Download a skill to cold pool and add to deck | `bunx @lythos/skill-deck@0.14.4 add owner/repo` |
79
+ | Pull latest versions of declared skills | `bunx @lythos/skill-deck@0.14.4 refresh` |
80
+ | Refresh a single skill by alias | `bunx @lythos/skill-deck@0.14.4 refresh tdd` |
81
+ | Remove a skill from deck and working set | `bunx @lythos/skill-deck@0.14.4 remove tdd` |
82
+ | Switch skill to symlink mode (live) | `bunx @lythos/skill-deck@0.14.4 to-symlink tdd` |
83
+ | Switch skill to snapshot mode (pinned) | `bunx @lythos/skill-deck@0.14.4 to-snapshot tdd` |
84
+ | Use a custom deck file or working dir | `bunx @lythos/skill-deck@0.14.4 link --deck ./my-deck.toml --workdir /path/to/project` |
85
85
 
86
86
  ### Commands
87
87
 
@@ -143,7 +143,7 @@ source = "https://github.com/lythos-labs/lythoskill/blob/HEAD/skills/lythoskill-
143
143
  EOF
144
144
 
145
145
  # 2. Link — creates symlinks in .claude/skills/
146
- bunx @lythos/skill-deck@0.14.2 link
146
+ bunx @lythos/skill-deck@0.14.4 link
147
147
  ```
148
148
 
149
149
  ### Key Concepts
@@ -229,7 +229,7 @@ Caution: deck's deny-by-default will remove any skills not declared in your deck
229
229
 
230
230
  | Symptom | Cause | Fix |
231
231
  |---------|-------|-----|
232
- | `❌ Skill not found: <name>` | Skill declared in deck but not in cold pool | `bunx @lythos/skill-deck@0.14.2 add github.com/owner/repo/skill` or clone manually into cold pool |
232
+ | `❌ Skill not found: <name>` | Skill declared in deck but not in cold pool | `bunx @lythos/skill-deck@0.14.4 add github.com/owner/repo/skill` or clone manually into cold pool |
233
233
  | `link` skips entries with warnings | Real files/directories exist in working set (not symlinks) | Delete the real directories in `working_set` and re-run `link`. Never create directories manually there |
234
234
  | `refresh` reports "Not a git repository" | Skill was copied (not cloned) into cold pool | Re-clone with `git clone` or use `deck add` which clones by default |
235
235
  | `deck update` prints deprecation warning | `update` was renamed to `refresh` in v0.8+ | Use `deck refresh` instead |
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lythos/skill-deck",
3
- "version": "0.14.2",
3
+ "version": "0.14.4",
4
4
  "description": "Declarative skill deck governance — cold pool, working set, deny-by-default",
5
5
  "keywords": [
6
6
  "ai-agent",
@@ -31,8 +31,8 @@
31
31
  ],
32
32
  "dependencies": {
33
33
  "@iarna/toml": "^2.2.5",
34
- "@lythos/cold-pool": "^0.14.2",
35
- "@lythos/infra": "^0.14.2",
34
+ "@lythos/cold-pool": "^0.14.4",
35
+ "@lythos/infra": "^0.14.4",
36
36
  "yaml": "^2.8.3",
37
37
  "zod": "^4.3.6"
38
38
  },
package/src/add.ts CHANGED
@@ -183,7 +183,7 @@ function exitInvalidLocator(locator: string): never {
183
183
  console.error(` owner/repo@skill — skills.sh syntax`)
184
184
  console.error(` owner/repo/subpath — subdirectory`)
185
185
  console.error(` github:owner/repo — explicit GitHub prefix`)
186
- console.error(` localhost/<name> — local-only skill`)
186
+ console.error(` localhost/me/<skill> — local-only skill (host/owner/repo aligned)`)
187
187
  console.error(``)
188
188
  console.error(` Note: FQ locators look like URLs but map to cold pool paths:`)
189
189
  console.error(` github.com/o/r/skills/s → ~/.agents/skill-repos/github.com/o/r/skills/s/SKILL.md`)
package/src/link.ts CHANGED
@@ -76,7 +76,7 @@ export function findSource(name: string, coldPool: string, _projectDir: string):
76
76
  if (!locator) {
77
77
  return {
78
78
  path: null,
79
- error: `Locator "${name}" is not FQ. Expected: host.tld/owner/repo[/skill] or localhost/<name>. Bare names rejected per ADR-20260502012643244.`,
79
+ error: `Locator "${name}" is not FQ. Expected: host.tld/owner/repo[/skill] or localhost/me/<skill>. Bare names rejected per ADR-20260502012643244.`,
80
80
  };
81
81
  }
82
82
 
@@ -188,6 +188,7 @@ interface DeclaredSkill {
188
188
  alias: string; // working-set flat symlink name
189
189
  type: "innate" | "tool" | "combo" | "transient";
190
190
  sourcePath: string;
191
+ mode?: 'symlink' | 'snapshot';
191
192
  expires?: string;
192
193
  }
193
194
 
@@ -234,7 +235,8 @@ for (const entry of parsedEntries) {
234
235
  continue
235
236
  }
236
237
  }
237
- declared.push({ name: entry.path, alias: entry.alias, type: entry.type, sourcePath: result.path });
238
+ const entryMode = (entry as any).mode as 'symlink' | 'snapshot' | undefined;
239
+ declared.push({ name: entry.path, alias: entry.alias, type: entry.type, sourcePath: result.path, mode: entryMode });
238
240
  }
239
241
 
240
242
  // transient: sub-tables with path field (kept backward-compat; future ADR may unify)
@@ -427,7 +429,8 @@ for (const item of declared) {
427
429
 
428
430
  try {
429
431
  mkdirSync(dirname(dest), { recursive: true });
430
- if (MODE === 'snapshot') {
432
+ const linkMode = item.mode ?? MODE;
433
+ if (linkMode === 'snapshot') {
431
434
  cpSync(item.sourcePath, dest, { recursive: true });
432
435
  } else {
433
436
  symlinkSync(item.sourcePath, dest);
@@ -463,7 +466,7 @@ for (const item of declared) {
463
466
  type: item.type,
464
467
  source: sourceRel,
465
468
  dest: relative(PROJECT_DIR, dest),
466
- mode: MODE,
469
+ mode: item.mode ?? MODE,
467
470
  content_hash: contentHash,
468
471
  linked_at: new Date().toISOString(),
469
472
  ...(item.expires ? { expires: item.expires } : {}),
@@ -135,6 +135,25 @@ describe('buildRefreshPlan', () => {
135
135
  expect(plan.workdir).toBe('/custom/work')
136
136
  expect(plan.coldPool).toBe('/custom/pool')
137
137
  })
138
+ test('plan-mode: all declared skills appear in plan structure', () => {
139
+ const plan = buildRefreshPlan(deckAliasDict, { coldPool: '/pool' })
140
+ expect(plan.allDeclared).toHaveLength(2)
141
+ expect(plan.targets.length).toBeGreaterThanOrEqual(0)
142
+ // Plan structure is correct — path/alias mapping verified.
143
+ // Type detection (git/localhost/missing) depends on filesystem;
144
+ // those cases are covered by detectGitRoot tests above.
145
+ })
146
+
147
+ test('plan-mode: plan carries correct config paths through', () => {
148
+ const plan = buildRefreshPlan(deckAliasDict, {
149
+ deckPath: '/custom/deck.toml',
150
+ workdir: '/custom/work',
151
+ coldPool: '/custom/pool',
152
+ })
153
+ expect(plan.deckPath).toBe('/custom/deck.toml')
154
+ expect(plan.workdir).toBe('/custom/work')
155
+ expect(plan.coldPool).toBe('/custom/pool')
156
+ })
138
157
  })
139
158
 
140
159
  // ── executeRefreshPlan (IO-injected plan execution) ────────────────