@agentworkforce/persona-kit 0.19.0 → 2.1.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.
- package/dist/interactive-spec.d.ts +1 -1
- package/dist/interactive-spec.js +2 -2
- package/dist/interactive-spec.js.map +1 -1
- package/dist/mount.test.d.ts +2 -0
- package/dist/mount.test.d.ts.map +1 -0
- package/dist/mount.test.js +32 -0
- package/dist/mount.test.js.map +1 -0
- package/dist/parse.test.d.ts +2 -0
- package/dist/parse.test.d.ts.map +1 -0
- package/dist/parse.test.js +157 -0
- package/dist/parse.test.js.map +1 -0
- package/dist/sidecars.test.d.ts +2 -0
- package/dist/sidecars.test.d.ts.map +1 -0
- package/dist/sidecars.test.js +105 -0
- package/dist/sidecars.test.js.map +1 -0
- package/dist/skills.test.d.ts +2 -0
- package/dist/skills.test.d.ts.map +1 -0
- package/dist/skills.test.js +116 -0
- package/dist/skills.test.js.map +1 -0
- package/package.json +1 -1
|
@@ -56,7 +56,7 @@ export interface BuildInteractiveSpecInput {
|
|
|
56
56
|
* Absolute paths of directories to load as Claude Code plugins for this
|
|
57
57
|
* session (`--plugin-dir <path>` per entry). Used to wire in out-of-repo
|
|
58
58
|
* skill stages produced by
|
|
59
|
-
* {@link
|
|
59
|
+
* {@link SkillMaterializationOptions.installRoot}.
|
|
60
60
|
* Claude-only: other harnesses emit a warning and ignore the field.
|
|
61
61
|
*/
|
|
62
62
|
pluginDirs?: readonly string[];
|
package/dist/interactive-spec.js
CHANGED
|
@@ -152,8 +152,8 @@ export function buildInteractiveSpec(input) {
|
|
|
152
152
|
// of autosync, and callers who want a read-only persona (e.g. a code
|
|
153
153
|
// reviewer) can override this in a follow-up PR that threads a
|
|
154
154
|
// richer permission spec through the persona config — the current
|
|
155
|
-
//
|
|
156
|
-
//
|
|
155
|
+
// PersonaPermissions shape is claude-specific and already warned about
|
|
156
|
+
// for opencode.
|
|
157
157
|
//
|
|
158
158
|
// The bare-string form `permission: 'allow'` was valid in older
|
|
159
159
|
// opencode versions but is rejected by 1.14.x: the agent decoder
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"interactive-spec.js","sourceRoot":"","sources":["../src/interactive-spec.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"interactive-spec.js","sourceRoot":"","sources":["../src/interactive-spec.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mount.test.d.ts","sourceRoot":"","sources":["../src/mount.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import test from 'node:test';
|
|
2
|
+
import assert from 'node:assert/strict';
|
|
3
|
+
import { applyPersonaMount } from './mount.js';
|
|
4
|
+
test('applyPersonaMount: undefined policy returns a no-op handle whose cwd matches options.cwd', async () => {
|
|
5
|
+
const handle = await applyPersonaMount(undefined, { cwd: '/some/where' });
|
|
6
|
+
assert.equal(handle.cwd, '/some/where');
|
|
7
|
+
// Idempotent
|
|
8
|
+
await handle.dispose();
|
|
9
|
+
await handle.dispose();
|
|
10
|
+
});
|
|
11
|
+
test('applyPersonaMount: undefined policy ignores missing mountDir + personaId', async () => {
|
|
12
|
+
// The no-op branch must not require mount-only options. This guards against
|
|
13
|
+
// a regression where mount validation happens before the no-op short-circuit.
|
|
14
|
+
const handle = await applyPersonaMount(undefined, { cwd: '/x' });
|
|
15
|
+
assert.equal(handle.cwd, '/x');
|
|
16
|
+
await handle.dispose();
|
|
17
|
+
});
|
|
18
|
+
test('applyPersonaMount: declared policy without mountDir throws a clear error', async () => {
|
|
19
|
+
const mount = {
|
|
20
|
+
ignoredPatterns: ['secrets/**'],
|
|
21
|
+
readonlyPatterns: []
|
|
22
|
+
};
|
|
23
|
+
await assert.rejects(applyPersonaMount(mount, { cwd: '/x', personaId: 'p' }), /options\.mountDir is required when a mount policy is supplied/);
|
|
24
|
+
});
|
|
25
|
+
test('applyPersonaMount: declared policy without personaId throws a clear error', async () => {
|
|
26
|
+
const mount = {
|
|
27
|
+
ignoredPatterns: [],
|
|
28
|
+
readonlyPatterns: ['vendor/**']
|
|
29
|
+
};
|
|
30
|
+
await assert.rejects(applyPersonaMount(mount, { cwd: '/x', mountDir: '/scratch/mount' }), /options\.personaId is required when a mount policy is supplied/);
|
|
31
|
+
});
|
|
32
|
+
//# sourceMappingURL=mount.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mount.test.js","sourceRoot":"","sources":["../src/mount.test.ts"],"names":[],"mappings":"AAAA,OAAO,IAAI,MAAM,WAAW,CAAC;AAC7B,OAAO,MAAM,MAAM,oBAAoB,CAAC;AACxC,OAAO,EAAE,iBAAiB,EAAE,MAAM,YAAY,CAAC;AAG/C,IAAI,CAAC,0FAA0F,EAAE,KAAK,IAAI,EAAE;IAC1G,MAAM,MAAM,GAAG,MAAM,iBAAiB,CAAC,SAAS,EAAE,EAAE,GAAG,EAAE,aAAa,EAAE,CAAC,CAAC;IAC1E,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,GAAG,EAAE,aAAa,CAAC,CAAC;IACxC,aAAa;IACb,MAAM,MAAM,CAAC,OAAO,EAAE,CAAC;IACvB,MAAM,MAAM,CAAC,OAAO,EAAE,CAAC;AACzB,CAAC,CAAC,CAAC;AAEH,IAAI,CAAC,0EAA0E,EAAE,KAAK,IAAI,EAAE;IAC1F,4EAA4E;IAC5E,8EAA8E;IAC9E,MAAM,MAAM,GAAG,MAAM,iBAAiB,CAAC,SAAS,EAAE,EAAE,GAAG,EAAE,IAAI,EAAE,CAAC,CAAC;IACjE,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,GAAG,EAAE,IAAI,CAAC,CAAC;IAC/B,MAAM,MAAM,CAAC,OAAO,EAAE,CAAC;AACzB,CAAC,CAAC,CAAC;AAEH,IAAI,CAAC,0EAA0E,EAAE,KAAK,IAAI,EAAE;IAC1F,MAAM,KAAK,GAAwB;QACjC,eAAe,EAAE,CAAC,YAAY,CAAC;QAC/B,gBAAgB,EAAE,EAAE;KACrB,CAAC;IACF,MAAM,MAAM,CAAC,OAAO,CAClB,iBAAiB,CAAC,KAAK,EAAE,EAAE,GAAG,EAAE,IAAI,EAAE,SAAS,EAAE,GAAG,EAAE,CAAC,EACvD,+DAA+D,CAChE,CAAC;AACJ,CAAC,CAAC,CAAC;AAEH,IAAI,CAAC,2EAA2E,EAAE,KAAK,IAAI,EAAE;IAC3F,MAAM,KAAK,GAAwB;QACjC,eAAe,EAAE,EAAE;QACnB,gBAAgB,EAAE,CAAC,WAAW,CAAC;KAChC,CAAC;IACF,MAAM,MAAM,CAAC,OAAO,CAClB,iBAAiB,CAAC,KAAK,EAAE,EAAE,GAAG,EAAE,IAAI,EAAE,QAAQ,EAAE,gBAAgB,EAAE,CAAC,EACnE,gEAAgE,CACjE,CAAC;AACJ,CAAC,CAAC,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"parse.test.d.ts","sourceRoot":"","sources":["../src/parse.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,157 @@
|
|
|
1
|
+
import test from 'node:test';
|
|
2
|
+
import assert from 'node:assert/strict';
|
|
3
|
+
import { assertInputName, assertSidecarPath, INPUT_NAME_RE, parseHarnessSettings, parseInputs, parseMcpServers, parseMount, parsePermissions, parsePersonaSpec, parseSkills, parseStringList, parseStringMap, parseTags } from './parse.js';
|
|
4
|
+
const baseRuntime = {
|
|
5
|
+
harness: 'claude',
|
|
6
|
+
model: 'anthropic/claude-3-5-sonnet',
|
|
7
|
+
systemPrompt: 'be helpful',
|
|
8
|
+
harnessSettings: { reasoning: 'medium', timeoutSeconds: 300 }
|
|
9
|
+
};
|
|
10
|
+
function validSpec(over = {}) {
|
|
11
|
+
return {
|
|
12
|
+
id: 'p',
|
|
13
|
+
intent: 'documentation',
|
|
14
|
+
tags: ['documentation'],
|
|
15
|
+
description: 'd',
|
|
16
|
+
tiers: { best: baseRuntime, 'best-value': baseRuntime, minimum: baseRuntime },
|
|
17
|
+
...over
|
|
18
|
+
};
|
|
19
|
+
}
|
|
20
|
+
test('parsePersonaSpec accepts a minimal valid spec across all tiers', () => {
|
|
21
|
+
const spec = parsePersonaSpec(validSpec(), 'documentation');
|
|
22
|
+
assert.equal(spec.id, 'p');
|
|
23
|
+
assert.equal(spec.intent, 'documentation');
|
|
24
|
+
assert.deepEqual(spec.tags, ['documentation']);
|
|
25
|
+
assert.equal(spec.tiers.best.harness, 'claude');
|
|
26
|
+
});
|
|
27
|
+
test('parsePersonaSpec strips unknown top-level fields silently', () => {
|
|
28
|
+
const raw = validSpec({ unknownField: 'should be dropped', extra: { nested: true } });
|
|
29
|
+
const spec = parsePersonaSpec(raw, 'documentation');
|
|
30
|
+
assert.ok(!('unknownField' in spec), 'unknown fields are not preserved on the parsed spec');
|
|
31
|
+
assert.ok(!('extra' in spec));
|
|
32
|
+
});
|
|
33
|
+
test('parsePersonaSpec throws when intent does not match the expected intent', () => {
|
|
34
|
+
assert.throws(() => parsePersonaSpec(validSpec({ intent: 'review' }), 'documentation'), /intent mismatch: got review/);
|
|
35
|
+
});
|
|
36
|
+
test('parsePersonaSpec throws with a precise field path on a malformed tier', () => {
|
|
37
|
+
const raw = validSpec({
|
|
38
|
+
tiers: {
|
|
39
|
+
best: baseRuntime,
|
|
40
|
+
'best-value': { ...baseRuntime, harnessSettings: { reasoning: 'turbo', timeoutSeconds: 1 } },
|
|
41
|
+
minimum: baseRuntime
|
|
42
|
+
}
|
|
43
|
+
});
|
|
44
|
+
assert.throws(() => parsePersonaSpec(raw, 'documentation'), /persona\[documentation\]\.tiers\.best-value\.harnessSettings\.reasoning must be low\|medium\|high/);
|
|
45
|
+
});
|
|
46
|
+
test('parsePersonaSpec defers malformed skills[i].source to plan time (does not throw at parse)', () => {
|
|
47
|
+
// Issue 70 contract: parse only validates shape (string + non-empty); URL/source-kind
|
|
48
|
+
// validation happens in materializeSkills so a typo blows up its own persona, not the dir.
|
|
49
|
+
const spec = parsePersonaSpec(validSpec({
|
|
50
|
+
skills: [
|
|
51
|
+
{ id: 'good', source: 'https://prpm.dev/packages/@scope/x', description: 'fine' },
|
|
52
|
+
{ id: 'odd', source: 'totally-bogus-source', description: 'should still parse' }
|
|
53
|
+
]
|
|
54
|
+
}), 'documentation');
|
|
55
|
+
assert.equal(spec.skills.length, 2);
|
|
56
|
+
assert.equal(spec.skills[1].source, 'totally-bogus-source');
|
|
57
|
+
});
|
|
58
|
+
test('parsePermissions throws on an invalid permission mode', () => {
|
|
59
|
+
assert.throws(() => parsePermissions({ mode: 'oops' }, 'p'), /p\.mode must be one of:/);
|
|
60
|
+
});
|
|
61
|
+
test('parseMount accepts ignoredPatterns + readonlyPatterns; drops empties to undefined', () => {
|
|
62
|
+
assert.equal(parseMount({}, 'mount'), undefined);
|
|
63
|
+
const m = parseMount({ ignoredPatterns: ['secrets/**'], readonlyPatterns: ['vendor/**'] }, 'mount');
|
|
64
|
+
assert.deepEqual(m, {
|
|
65
|
+
ignoredPatterns: ['secrets/**'],
|
|
66
|
+
readonlyPatterns: ['vendor/**']
|
|
67
|
+
});
|
|
68
|
+
});
|
|
69
|
+
test('parseMount throws when patterns are not non-empty strings', () => {
|
|
70
|
+
assert.throws(() => parseMount({ ignoredPatterns: [''] }, 'mount'), /ignoredPatterns\[0\]/);
|
|
71
|
+
assert.throws(() => parseMount({ readonlyPatterns: [42] }, 'mount'), /readonlyPatterns\[0\]/);
|
|
72
|
+
});
|
|
73
|
+
test('INPUT_NAME_RE matches env-var convention', () => {
|
|
74
|
+
for (const ok of ['FOO', 'FOO_BAR', '_FOO', 'A1', 'A_1_B']) {
|
|
75
|
+
assert.match(ok, INPUT_NAME_RE, `expected ${ok} to match`);
|
|
76
|
+
}
|
|
77
|
+
for (const bad of ['foo', '1FOO', 'FOO-BAR', 'FOO BAR', 'foo_bar']) {
|
|
78
|
+
assert.doesNotMatch(bad, INPUT_NAME_RE, `expected ${bad} not to match`);
|
|
79
|
+
}
|
|
80
|
+
});
|
|
81
|
+
test('assertInputName throws on names that violate the env-var convention', () => {
|
|
82
|
+
assert.throws(() => assertInputName('lowercase', 'inputs.lowercase'), /env-style name/);
|
|
83
|
+
assert.throws(() => assertInputName('1LEADING', 'inputs.1LEADING'), /env-style name/);
|
|
84
|
+
});
|
|
85
|
+
test('parseInputs accepts a string default and an object with description+env+default', () => {
|
|
86
|
+
const inputs = parseInputs({
|
|
87
|
+
OUTPUT_PATH: '/tmp/out',
|
|
88
|
+
TARGET: { description: 'where to go', env: 'TARGET_OVERRIDE', default: 'home' }
|
|
89
|
+
}, 'inputs');
|
|
90
|
+
assert.equal(inputs?.OUTPUT_PATH.default, '/tmp/out');
|
|
91
|
+
assert.equal(inputs?.TARGET.env, 'TARGET_OVERRIDE');
|
|
92
|
+
assert.equal(inputs?.TARGET.default, 'home');
|
|
93
|
+
assert.equal(inputs?.TARGET.description, 'where to go');
|
|
94
|
+
});
|
|
95
|
+
test('parseInputs forbids combining optional:true with a default', () => {
|
|
96
|
+
assert.throws(() => parseInputs({ FOO: { optional: true, default: 'x' } }, 'inputs'), /cannot set both 'optional: true' and 'default'/);
|
|
97
|
+
});
|
|
98
|
+
test('parseInputs rejects names that violate the env-var convention', () => {
|
|
99
|
+
assert.throws(() => parseInputs({ foo: 'x' }, 'inputs'), /inputs\.foo must be an env-style name/);
|
|
100
|
+
});
|
|
101
|
+
test('parseHarnessSettings accepts optional codex fields and rejects bad ones', () => {
|
|
102
|
+
const ok = parseHarnessSettings({
|
|
103
|
+
reasoning: 'high',
|
|
104
|
+
timeoutSeconds: 60,
|
|
105
|
+
sandboxMode: 'workspace-write',
|
|
106
|
+
approvalPolicy: 'on-request',
|
|
107
|
+
workspaceWriteNetworkAccess: true,
|
|
108
|
+
webSearch: false
|
|
109
|
+
}, 'rt');
|
|
110
|
+
assert.equal(ok.sandboxMode, 'workspace-write');
|
|
111
|
+
assert.equal(ok.approvalPolicy, 'on-request');
|
|
112
|
+
assert.equal(ok.workspaceWriteNetworkAccess, true);
|
|
113
|
+
assert.equal(ok.webSearch, false);
|
|
114
|
+
assert.throws(() => parseHarnessSettings({ reasoning: 'medium', timeoutSeconds: 0 }, 'rt'), /rt\.timeoutSeconds must be a positive number/);
|
|
115
|
+
assert.throws(() => parseHarnessSettings({ reasoning: 'medium', timeoutSeconds: 1, sandboxMode: 'bogus' }, 'rt'), /rt\.sandboxMode must be one of:/);
|
|
116
|
+
});
|
|
117
|
+
test('parseTags rejects empty arrays and unknown tags', () => {
|
|
118
|
+
assert.throws(() => parseTags([], 'tags'), /must be a non-empty array/);
|
|
119
|
+
assert.throws(() => parseTags(['nonsense-tag'], 'tags'), /tags\[0\] must be one of:/);
|
|
120
|
+
});
|
|
121
|
+
test('parseSkills returns [] for undefined, validates shape per entry', () => {
|
|
122
|
+
assert.deepEqual(parseSkills(undefined, 'skills'), []);
|
|
123
|
+
assert.throws(() => parseSkills([{ id: '', source: 'x', description: 'y' }], 'skills'), /skills\[0\]\.id must be a non-empty string/);
|
|
124
|
+
});
|
|
125
|
+
test('parseStringList drops undefined and rejects empty strings', () => {
|
|
126
|
+
assert.equal(parseStringList(undefined, 'list'), undefined);
|
|
127
|
+
assert.throws(() => parseStringList([''], 'list'), /list\[0\] must be a non-empty string/);
|
|
128
|
+
});
|
|
129
|
+
test('parseStringMap rejects non-string values', () => {
|
|
130
|
+
assert.throws(() => parseStringMap({ FOO: 1 }, 'env'), /env\.FOO must be a string/);
|
|
131
|
+
});
|
|
132
|
+
test('parseMcpServers validates the http/sse/stdio union', () => {
|
|
133
|
+
const ok = parseMcpServers({
|
|
134
|
+
api: { type: 'http', url: 'https://example.com', headers: { Authorization: 'x' } },
|
|
135
|
+
tail: { type: 'sse', url: 'https://example.com/sse' },
|
|
136
|
+
local: { type: 'stdio', command: 'node', args: ['index.js'], env: { NODE_ENV: 'test' } }
|
|
137
|
+
}, 'mcpServers');
|
|
138
|
+
assert.equal(ok?.api.type, 'http');
|
|
139
|
+
assert.equal(ok?.local.type, 'stdio');
|
|
140
|
+
assert.throws(() => parseMcpServers({ bad: { type: 'mystery' } }, 'mcpServers'), /mcpServers\.bad\.type must be one of: http, sse, stdio/);
|
|
141
|
+
assert.throws(() => parseMcpServers({ http: { type: 'http' } }, 'mcpServers'), /mcpServers\.http\.url must be a non-empty string/);
|
|
142
|
+
});
|
|
143
|
+
test('assertSidecarPath rejects absolute paths and ".." traversal', () => {
|
|
144
|
+
assert.throws(() => assertSidecarPath('/abs.md', 'claudeMd'), /must be a relative POSIX path/);
|
|
145
|
+
assert.throws(() => assertSidecarPath('a/../escape.md', 'claudeMd'), /must not contain ".." segments/);
|
|
146
|
+
assert.throws(() => assertSidecarPath('not-md.txt', 'claudeMd'), /must end with .md/);
|
|
147
|
+
});
|
|
148
|
+
test('parsePersonaSpec rejects a non-object spec', () => {
|
|
149
|
+
assert.throws(() => parsePersonaSpec(null, 'documentation'), /must be an object/);
|
|
150
|
+
assert.throws(() => parsePersonaSpec('nope', 'documentation'), /must be an object/);
|
|
151
|
+
});
|
|
152
|
+
test('parsePersonaSpec preserves defaultTier when valid and rejects when invalid', () => {
|
|
153
|
+
const ok = parsePersonaSpec(validSpec({ defaultTier: 'best' }), 'documentation');
|
|
154
|
+
assert.equal(ok.defaultTier, 'best');
|
|
155
|
+
assert.throws(() => parsePersonaSpec(validSpec({ defaultTier: 'turbo' }), 'documentation'), /defaultTier must be one of:/);
|
|
156
|
+
});
|
|
157
|
+
//# sourceMappingURL=parse.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"parse.test.js","sourceRoot":"","sources":["../src/parse.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sidecars.test.d.ts","sourceRoot":"","sources":["../src/sidecars.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
import test from 'node:test';
|
|
2
|
+
import assert from 'node:assert/strict';
|
|
3
|
+
import { mkdtemp, readFile, rm, stat, writeFile } from 'node:fs/promises';
|
|
4
|
+
import { tmpdir } from 'node:os';
|
|
5
|
+
import { join } from 'node:path';
|
|
6
|
+
import { writePersonaSidecars } from './sidecars.js';
|
|
7
|
+
import { buildPersonaSpawnPlan } from './plan.js';
|
|
8
|
+
async function exists(path) {
|
|
9
|
+
try {
|
|
10
|
+
await stat(path);
|
|
11
|
+
return true;
|
|
12
|
+
}
|
|
13
|
+
catch {
|
|
14
|
+
return false;
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
async function withTmpDir(fn) {
|
|
18
|
+
const dir = await mkdtemp(join(tmpdir(), 'persona-kit-sidecars-'));
|
|
19
|
+
try {
|
|
20
|
+
return await fn(dir);
|
|
21
|
+
}
|
|
22
|
+
finally {
|
|
23
|
+
await rm(dir, { recursive: true, force: true });
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
const cleanEnv = Object.freeze({});
|
|
27
|
+
function persona(over = {}) {
|
|
28
|
+
return {
|
|
29
|
+
personaId: 'p',
|
|
30
|
+
tier: 'best-value',
|
|
31
|
+
runtime: {
|
|
32
|
+
harness: 'claude',
|
|
33
|
+
model: 'anthropic/claude-3-5-sonnet',
|
|
34
|
+
systemPrompt: 'be helpful',
|
|
35
|
+
harnessSettings: { reasoning: 'medium', timeoutSeconds: 300 }
|
|
36
|
+
},
|
|
37
|
+
skills: [],
|
|
38
|
+
rationale: 'test',
|
|
39
|
+
...over
|
|
40
|
+
};
|
|
41
|
+
}
|
|
42
|
+
test('writePersonaSidecars: extend mode preserves the original on dispose', async () => {
|
|
43
|
+
await withTmpDir(async (dir) => {
|
|
44
|
+
const target = join(dir, 'CLAUDE.md');
|
|
45
|
+
await writeFile(target, 'pre-existing', 'utf8');
|
|
46
|
+
const handle = await writePersonaSidecars([{ filename: 'CLAUDE.md', contents: 'persona body', mode: 'extend' }], { cwd: dir });
|
|
47
|
+
assert.equal(await readFile(target, 'utf8'), 'pre-existing\n\n---\n\npersona body');
|
|
48
|
+
await handle.dispose();
|
|
49
|
+
assert.equal(await readFile(target, 'utf8'), 'pre-existing');
|
|
50
|
+
});
|
|
51
|
+
});
|
|
52
|
+
test('writePersonaSidecars: overwrite of an existing file restores prior contents on dispose', async () => {
|
|
53
|
+
await withTmpDir(async (dir) => {
|
|
54
|
+
const target = join(dir, 'CLAUDE.md');
|
|
55
|
+
await writeFile(target, 'original', 'utf8');
|
|
56
|
+
const handle = await writePersonaSidecars([{ filename: 'CLAUDE.md', contents: 'replacement', mode: 'overwrite' }], { cwd: dir });
|
|
57
|
+
assert.equal(await readFile(target, 'utf8'), 'replacement');
|
|
58
|
+
await handle.dispose();
|
|
59
|
+
assert.equal(await readFile(target, 'utf8'), 'original');
|
|
60
|
+
});
|
|
61
|
+
});
|
|
62
|
+
test('writePersonaSidecars: extend mode against an empty cwd writes the persona body verbatim', async () => {
|
|
63
|
+
// No prior file → "extend" still writes; on dispose the file is removed.
|
|
64
|
+
await withTmpDir(async (dir) => {
|
|
65
|
+
const handle = await writePersonaSidecars([{ filename: 'AGENTS.md', contents: 'persona body', mode: 'extend' }], { cwd: dir });
|
|
66
|
+
const target = join(dir, 'AGENTS.md');
|
|
67
|
+
assert.equal(await readFile(target, 'utf8'), 'persona body');
|
|
68
|
+
await handle.dispose();
|
|
69
|
+
assert.equal(await exists(target), false);
|
|
70
|
+
});
|
|
71
|
+
});
|
|
72
|
+
test('writePersonaSidecars: rejects sourcePath that is not absolute', async () => {
|
|
73
|
+
await withTmpDir(async (dir) => {
|
|
74
|
+
await assert.rejects(writePersonaSidecars([{ filename: 'CLAUDE.md', sourcePath: 'relative/source.md', mode: 'overwrite' }], { cwd: dir }), /sourcePath must be absolute/);
|
|
75
|
+
});
|
|
76
|
+
});
|
|
77
|
+
test('writePersonaSidecars: dispose runs in LIFO order (later write restored before earlier)', async () => {
|
|
78
|
+
// Two writes to the SAME filename in one call. The second write captures
|
|
79
|
+
// the first's body as its `prior`. Only LIFO dispose ends in the original
|
|
80
|
+
// state — restoring oldest-first would leave the file at "first" content.
|
|
81
|
+
await withTmpDir(async (dir) => {
|
|
82
|
+
const target = join(dir, 'CLAUDE.md');
|
|
83
|
+
await writeFile(target, 'original', 'utf8');
|
|
84
|
+
const handle = await writePersonaSidecars([
|
|
85
|
+
{ filename: 'CLAUDE.md', contents: 'first', mode: 'overwrite' },
|
|
86
|
+
{ filename: 'CLAUDE.md', contents: 'second', mode: 'overwrite' }
|
|
87
|
+
], { cwd: dir });
|
|
88
|
+
assert.equal(await readFile(target, 'utf8'), 'second');
|
|
89
|
+
await handle.dispose();
|
|
90
|
+
assert.equal(await readFile(target, 'utf8'), 'original', 'LIFO dispose must restore back through "first" to the pre-call "original"');
|
|
91
|
+
});
|
|
92
|
+
});
|
|
93
|
+
test('buildPersonaSpawnPlan + writePersonaSidecars round-trip a path-backed sidecar', async () => {
|
|
94
|
+
await withTmpDir(async (dir) => {
|
|
95
|
+
const sourcePath = join(dir, 'persona-source.md');
|
|
96
|
+
await writeFile(sourcePath, '# from disk', 'utf8');
|
|
97
|
+
const plan = buildPersonaSpawnPlan(persona({ claudeMd: sourcePath, claudeMdMode: 'overwrite' }), { processEnv: cleanEnv });
|
|
98
|
+
assert.equal(plan.sidecars[0]?.sourcePath, sourcePath);
|
|
99
|
+
const handle = await writePersonaSidecars(plan.sidecars, { cwd: dir });
|
|
100
|
+
assert.equal(await readFile(join(dir, 'CLAUDE.md'), 'utf8'), '# from disk');
|
|
101
|
+
await handle.dispose();
|
|
102
|
+
assert.equal(await exists(join(dir, 'CLAUDE.md')), false);
|
|
103
|
+
});
|
|
104
|
+
});
|
|
105
|
+
//# sourceMappingURL=sidecars.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sidecars.test.js","sourceRoot":"","sources":["../src/sidecars.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"skills.test.d.ts","sourceRoot":"","sources":["../src/skills.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
import test from 'node:test';
|
|
2
|
+
import assert from 'node:assert/strict';
|
|
3
|
+
import { mkdtemp, mkdir, readFile, rm, stat, writeFile } from 'node:fs/promises';
|
|
4
|
+
import { tmpdir } from 'node:os';
|
|
5
|
+
import { join } from 'node:path';
|
|
6
|
+
import { runSkillInstalls } from './skill-runner.js';
|
|
7
|
+
async function exists(path) {
|
|
8
|
+
try {
|
|
9
|
+
await stat(path);
|
|
10
|
+
return true;
|
|
11
|
+
}
|
|
12
|
+
catch {
|
|
13
|
+
return false;
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
async function withTmpDir(fn) {
|
|
17
|
+
const dir = await mkdtemp(join(tmpdir(), 'persona-kit-skills-'));
|
|
18
|
+
try {
|
|
19
|
+
return await fn(dir);
|
|
20
|
+
}
|
|
21
|
+
finally {
|
|
22
|
+
await rm(dir, { recursive: true, force: true });
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
test('runSkillInstalls: empty plan with no installs and no session root spawns nothing', async () => {
|
|
26
|
+
await withTmpDir(async (dir) => {
|
|
27
|
+
const plan = { harness: 'claude', installs: [] };
|
|
28
|
+
const handle = await runSkillInstalls(plan, { cwd: dir });
|
|
29
|
+
await handle.dispose();
|
|
30
|
+
// Idempotent
|
|
31
|
+
await handle.dispose();
|
|
32
|
+
});
|
|
33
|
+
});
|
|
34
|
+
test('runSkillInstalls: cleanupOnDispose=false leaves cleanupPaths intact', async () => {
|
|
35
|
+
await withTmpDir(async (dir) => {
|
|
36
|
+
// Pre-create the artifact dir so we can verify it survives dispose.
|
|
37
|
+
const artifactDir = '.claude/skills/persisted';
|
|
38
|
+
await mkdir(join(dir, artifactDir), { recursive: true });
|
|
39
|
+
await writeFile(join(dir, artifactDir, 'SKILL.md'), '# survives', 'utf8');
|
|
40
|
+
const plan = {
|
|
41
|
+
harness: 'claude',
|
|
42
|
+
installs: [
|
|
43
|
+
{
|
|
44
|
+
skillId: 'persisted',
|
|
45
|
+
source: 'persisted/persisted',
|
|
46
|
+
sourceKind: 'prpm',
|
|
47
|
+
packageRef: 'persisted/persisted',
|
|
48
|
+
harness: 'claude',
|
|
49
|
+
// no-op subprocess so the spawn path runs without filesystem effects
|
|
50
|
+
installCommand: [process.execPath, '-e', 'process.exit(0)'],
|
|
51
|
+
installedDir: artifactDir,
|
|
52
|
+
installedManifest: `${artifactDir}/SKILL.md`,
|
|
53
|
+
cleanupPaths: [artifactDir]
|
|
54
|
+
}
|
|
55
|
+
]
|
|
56
|
+
};
|
|
57
|
+
const handle = await runSkillInstalls(plan, { cwd: dir, cleanupOnDispose: false });
|
|
58
|
+
await handle.dispose();
|
|
59
|
+
assert.equal(await exists(join(dir, artifactDir)), true);
|
|
60
|
+
assert.equal(await readFile(join(dir, artifactDir, 'SKILL.md'), 'utf8'), '# survives');
|
|
61
|
+
});
|
|
62
|
+
});
|
|
63
|
+
test('runSkillInstalls: cleanupOnDispose=true removes per-install cleanupPaths', async () => {
|
|
64
|
+
await withTmpDir(async (dir) => {
|
|
65
|
+
const artifactDir = '.claude/skills/cleanup-me';
|
|
66
|
+
await mkdir(join(dir, artifactDir), { recursive: true });
|
|
67
|
+
await writeFile(join(dir, artifactDir, 'SKILL.md'), '# transient', 'utf8');
|
|
68
|
+
const plan = {
|
|
69
|
+
harness: 'claude',
|
|
70
|
+
installs: [
|
|
71
|
+
{
|
|
72
|
+
skillId: 'cleanup-me',
|
|
73
|
+
source: 'cleanup-me/cleanup-me',
|
|
74
|
+
sourceKind: 'prpm',
|
|
75
|
+
packageRef: 'cleanup-me/cleanup-me',
|
|
76
|
+
harness: 'claude',
|
|
77
|
+
installCommand: [process.execPath, '-e', 'process.exit(0)'],
|
|
78
|
+
installedDir: artifactDir,
|
|
79
|
+
installedManifest: `${artifactDir}/SKILL.md`,
|
|
80
|
+
cleanupPaths: [artifactDir]
|
|
81
|
+
}
|
|
82
|
+
]
|
|
83
|
+
};
|
|
84
|
+
const handle = await runSkillInstalls(plan, { cwd: dir });
|
|
85
|
+
await handle.dispose();
|
|
86
|
+
assert.equal(await exists(join(dir, artifactDir)), false);
|
|
87
|
+
});
|
|
88
|
+
});
|
|
89
|
+
test('runSkillInstalls: session install root scaffolds plugin.json and dispose removes the root', async () => {
|
|
90
|
+
await withTmpDir(async (dir) => {
|
|
91
|
+
const sessionRoot = join(dir, 'session-root');
|
|
92
|
+
const plan = {
|
|
93
|
+
harness: 'claude',
|
|
94
|
+
installs: [],
|
|
95
|
+
sessionInstallRoot: sessionRoot
|
|
96
|
+
};
|
|
97
|
+
const handle = await runSkillInstalls(plan, { cwd: dir });
|
|
98
|
+
assert.equal(await exists(join(sessionRoot, '.claude-plugin', 'plugin.json')), true);
|
|
99
|
+
await handle.dispose();
|
|
100
|
+
assert.equal(await exists(sessionRoot), false);
|
|
101
|
+
});
|
|
102
|
+
});
|
|
103
|
+
test('runSkillInstalls: session-root cleanupOnDispose=false leaves the root in place', async () => {
|
|
104
|
+
await withTmpDir(async (dir) => {
|
|
105
|
+
const sessionRoot = join(dir, 'sticky-root');
|
|
106
|
+
const plan = {
|
|
107
|
+
harness: 'claude',
|
|
108
|
+
installs: [],
|
|
109
|
+
sessionInstallRoot: sessionRoot
|
|
110
|
+
};
|
|
111
|
+
const handle = await runSkillInstalls(plan, { cwd: dir, cleanupOnDispose: false });
|
|
112
|
+
await handle.dispose();
|
|
113
|
+
assert.equal(await exists(join(sessionRoot, '.claude-plugin', 'plugin.json')), true);
|
|
114
|
+
});
|
|
115
|
+
});
|
|
116
|
+
//# sourceMappingURL=skills.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"skills.test.js","sourceRoot":"","sources":["../src/skills.test.ts"],"names":[],"mappings":"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"}
|