gm-skill 2.0.1544 → 2.0.1546
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/AGENTS.md +1 -5
- package/bin/bootstrap.js +3 -2
- package/bin/plugkit.version +1 -1
- package/bin/plugkit.wasm.sha256 +1 -1
- package/gm-plugkit/bootstrap.js +3 -2
- package/gm-plugkit/package.json +1 -1
- package/gm-plugkit/plugkit-wasm-wrapper.js +13 -2
- package/gm.json +2 -2
- package/lib/skill-bootstrap.js +3 -2
- package/package.json +1 -1
- package/skills/gm-skill/SKILL.md +1 -1
package/AGENTS.md
CHANGED
|
@@ -158,11 +158,7 @@ Three npm packages publish from this repo: `gm-skill` (the skill harness), `gm-p
|
|
|
158
158
|
|
|
159
159
|
## Spool-dispatch architecture replaces hooks
|
|
160
160
|
|
|
161
|
-
Orchestration state is tracked via
|
|
162
|
-
|
|
163
|
-
**Marker files**: `.gm/{prd.yml, mutables.yml, needs-gm, gm-fired-<sessionId>, residual-check-fired}` gate Write/Edit/git via `checkDispatchGates`. Per-marker semantics in rs-learn (`recall: spool dispatch gates marker files`).
|
|
164
|
-
|
|
165
|
-
**Gate enforcement**: the CLI layer calls `checkDispatchGates()` before tool execution; marker-driven dispatch replaces the hook event pump entirely. Detail in rs-learn (`recall: gate enforcement layer`).
|
|
161
|
+
Orchestration state is tracked via `.gm/` marker files, not hook events; the CLI layer calls `checkDispatchGates()` before tool execution to gate Write/Edit/git. Marker set (`prd.yml, mutables.yml, needs-gm, gm-fired-<sessionId>, residual-check-fired`), per-marker semantics, and the SpoolDispatcher CLI mechanism live in rs-learn (`recall: gate enforcement layer`, `recall: spool dispatch gates marker files`).
|
|
166
162
|
|
|
167
163
|
**gm-skill tool-use sequencing**: Invoking `Skill(skill="gm-skill")` writes `.gm/gm-fired-<sessionId>` to clear the needs-gm gate. The marker is cleared at turn start to reset the gate. There is one shipped skill; no subagent variant exists.
|
|
168
164
|
|
package/bin/bootstrap.js
CHANGED
|
@@ -27,7 +27,8 @@ function ensureSkillMdCurrent(wrapperDir) {
|
|
|
27
27
|
const bundledPath = candidates.find(p => { try { return fs.existsSync(p); } catch (_) { return false; } });
|
|
28
28
|
if (!bundledPath) return { skipped: 'bundled-not-found' };
|
|
29
29
|
const bundled = fs.readFileSync(bundledPath, 'utf8');
|
|
30
|
-
const
|
|
30
|
+
const _norm = s => s.replace(/\r\n/g, '\n');
|
|
31
|
+
const bundledHash = crypto.createHash('sha256').update(_norm(bundled)).digest('hex');
|
|
31
32
|
const home = os.homedir();
|
|
32
33
|
const targets = [
|
|
33
34
|
path.join(home, '.agents', 'skills', 'gm-skill', 'SKILL.md'),
|
|
@@ -39,7 +40,7 @@ function ensureSkillMdCurrent(wrapperDir) {
|
|
|
39
40
|
let needsWrite = true;
|
|
40
41
|
if (fs.existsSync(target)) {
|
|
41
42
|
const existing = fs.readFileSync(target, 'utf8');
|
|
42
|
-
const existingHash = crypto.createHash('sha256').update(existing).digest('hex');
|
|
43
|
+
const existingHash = crypto.createHash('sha256').update(_norm(existing)).digest('hex');
|
|
43
44
|
if (existingHash === bundledHash) needsWrite = false;
|
|
44
45
|
}
|
|
45
46
|
if (needsWrite) {
|
package/bin/plugkit.version
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
0.1.
|
|
1
|
+
0.1.642
|
package/bin/plugkit.wasm.sha256
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
a6532f8efc7b865cc2a4ce2ed714169e7f6110255b01cd709f94a51ca4b70e48 plugkit.wasm
|
package/gm-plugkit/bootstrap.js
CHANGED
|
@@ -716,7 +716,8 @@ function ensureSkillMdFresh() {
|
|
|
716
716
|
}
|
|
717
717
|
const bundled = fs.readFileSync(bundledPath, 'utf-8');
|
|
718
718
|
const crypto = require('crypto');
|
|
719
|
-
const
|
|
719
|
+
const _norm = s => s.replace(/\r\n/g, '\n');
|
|
720
|
+
const bundledHash = crypto.createHash('sha256').update(_norm(bundled)).digest('hex');
|
|
720
721
|
const home = process.env.HOME || process.env.USERPROFILE || require('os').homedir();
|
|
721
722
|
const targets = [
|
|
722
723
|
path.join(home, '.agents', 'skills', 'gm-skill', 'SKILL.md'),
|
|
@@ -728,7 +729,7 @@ function ensureSkillMdFresh() {
|
|
|
728
729
|
let needsWrite = true;
|
|
729
730
|
if (fs.existsSync(target)) {
|
|
730
731
|
const existing = fs.readFileSync(target, 'utf-8');
|
|
731
|
-
const existingHash = crypto.createHash('sha256').update(existing).digest('hex');
|
|
732
|
+
const existingHash = crypto.createHash('sha256').update(_norm(existing)).digest('hex');
|
|
732
733
|
if (existingHash === bundledHash) needsWrite = false;
|
|
733
734
|
}
|
|
734
735
|
if (needsWrite) {
|
package/gm-plugkit/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "gm-plugkit",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.1546",
|
|
4
4
|
"description": "Bootstrap and daemon-spawn tool for gm plugkit binary. Downloads the correct platform binary, verifies SHA256, and starts the spool watcher daemon. Includes plugkit-wasm-wrapper for WASM-based spool watching.",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"bin": {
|
|
@@ -2560,6 +2560,17 @@ async function runSpoolWatcher(instance, spoolDir) {
|
|
|
2560
2560
|
setTimeout(probeGmPlugkitSelfStale, 5000);
|
|
2561
2561
|
setInterval(probeGmPlugkitSelfStale, 300_000);
|
|
2562
2562
|
|
|
2563
|
+
// A supervised watcher self-exits on drift assuming the supervisor respawns it. If the
|
|
2564
|
+
// supervisor has died, that bare exit leaves the spool dead (worse than staying up). Treat a
|
|
2565
|
+
// dead/absent supervisor as unsupervised so the drift loops take the self-respawn-and-wait path
|
|
2566
|
+
// (spawn replacement, wait for its heartbeat, then exit) instead. False-negative is self-correcting:
|
|
2567
|
+
// if both the supervisor and this watcher respawn, the single-instance lock admits exactly one.
|
|
2568
|
+
function _supervisorIsDead() {
|
|
2569
|
+
try {
|
|
2570
|
+
const sp = parseInt(fs.readFileSync(path.join(spoolDir, '.supervisor.pid'), 'utf8').trim(), 10);
|
|
2571
|
+
return !(Number.isFinite(sp) && isProcessAliveSync(sp));
|
|
2572
|
+
} catch (_) { return true; }
|
|
2573
|
+
}
|
|
2563
2574
|
const _instanceVersionAtBoot = readInstanceVersion(instance);
|
|
2564
2575
|
let _driftLoggedOnce = false;
|
|
2565
2576
|
setInterval(() => {
|
|
@@ -2568,7 +2579,7 @@ async function runSpoolWatcher(instance, spoolDir) {
|
|
|
2568
2579
|
const instV = _instanceVersionAtBoot;
|
|
2569
2580
|
if (!fileV || !instV || fileV === instV) return;
|
|
2570
2581
|
const bootReason = process.env.PLUGKIT_BOOT_REASON || 'unknown';
|
|
2571
|
-
const unsupervised = bootReason === 'direct-no-supervisor';
|
|
2582
|
+
const unsupervised = bootReason === 'direct-no-supervisor' || _supervisorIsDead();
|
|
2572
2583
|
if (unsupervised) {
|
|
2573
2584
|
if (_driftLoggedOnce) return;
|
|
2574
2585
|
_driftLoggedOnce = true;
|
|
@@ -2665,7 +2676,7 @@ async function runSpoolWatcher(instance, spoolDir) {
|
|
|
2665
2676
|
const cur = crypto.createHash('sha256').update(fs.readFileSync(_wrapperPathInstalled)).digest('hex');
|
|
2666
2677
|
if (cur === _wrapperShaAtBoot) return;
|
|
2667
2678
|
const bootReason = process.env.PLUGKIT_BOOT_REASON || 'unknown';
|
|
2668
|
-
const unsupervised = bootReason === 'direct-no-supervisor';
|
|
2679
|
+
const unsupervised = bootReason === 'direct-no-supervisor' || _supervisorIsDead();
|
|
2669
2680
|
if (unsupervised) {
|
|
2670
2681
|
if (_wrapperDriftLoggedOnce) return;
|
|
2671
2682
|
_wrapperDriftLoggedOnce = true;
|
package/gm.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "gm",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.1546",
|
|
4
4
|
"description": "Spool-dispatch orchestration engine with unified state machine, skills, and automated git enforcement",
|
|
5
5
|
"author": "AnEntrypoint",
|
|
6
6
|
"license": "MIT",
|
|
@@ -17,5 +17,5 @@
|
|
|
17
17
|
"publishConfig": {
|
|
18
18
|
"access": "public"
|
|
19
19
|
},
|
|
20
|
-
"plugkitVersion": "0.1.
|
|
20
|
+
"plugkitVersion": "0.1.642"
|
|
21
21
|
}
|
package/lib/skill-bootstrap.js
CHANGED
|
@@ -300,7 +300,8 @@ function ensureSkillMdCurrent() {
|
|
|
300
300
|
return { refreshed: [], skipped: true };
|
|
301
301
|
}
|
|
302
302
|
const bundled = fs.readFileSync(bundledPath, 'utf8');
|
|
303
|
-
const
|
|
303
|
+
const _norm = s => s.replace(/\r\n/g, '\n');
|
|
304
|
+
const bundledHash = crypto.createHash('sha256').update(_norm(bundled)).digest('hex');
|
|
304
305
|
const targets = [
|
|
305
306
|
path.join(os.homedir(), '.agents', 'skills', 'gm-skill', 'SKILL.md'),
|
|
306
307
|
path.join(os.homedir(), '.claude', 'skills', 'gm-skill', 'SKILL.md'),
|
|
@@ -311,7 +312,7 @@ function ensureSkillMdCurrent() {
|
|
|
311
312
|
let needsWrite = true;
|
|
312
313
|
if (fs.existsSync(target)) {
|
|
313
314
|
const existing = fs.readFileSync(target, 'utf8');
|
|
314
|
-
const existingHash = crypto.createHash('sha256').update(existing).digest('hex');
|
|
315
|
+
const existingHash = crypto.createHash('sha256').update(_norm(existing)).digest('hex');
|
|
315
316
|
if (existingHash === bundledHash) needsWrite = false;
|
|
316
317
|
}
|
|
317
318
|
if (needsWrite) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "gm-skill",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.1546",
|
|
4
4
|
"description": "Canonical universal harness — AI-native software engineering via skill-driven orchestration; bootstraps plugkit for task execution and session isolation. Install in any AI coding agent host.",
|
|
5
5
|
"author": "AnEntrypoint",
|
|
6
6
|
"license": "MIT",
|
package/skills/gm-skill/SKILL.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: gm-skill
|
|
3
|
-
description: Plugkit-served instruction stream. Three-layer admission (
|
|
3
|
+
description: Plugkit-served instruction stream. Three-layer admission (witness, single-writer, direction) over every possible mutation; effort unbounded, never gated on cost. Closure on first emit; partial = non-monotonic.
|
|
4
4
|
allowed-tools: Skill, Read, Write, Bash(bun *), Bash(npx *)
|
|
5
5
|
---
|
|
6
6
|
|