gm-plugkit 2.0.1530 → 2.0.1532

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 (2) hide show
  1. package/package.json +1 -1
  2. package/supervisor.js +29 -0
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "gm-plugkit",
3
- "version": "2.0.1530",
3
+ "version": "2.0.1532",
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": {
package/supervisor.js CHANGED
@@ -298,6 +298,35 @@ function checkWatcherHealth() {
298
298
  if (process.platform === 'win32') {
299
299
  try { spawnSync('taskkill', ['/F', '/T', '/PID', String(currentChildPid)], { stdio: 'ignore', windowsHide: true, timeout: 3000 }); } catch (_) {}
300
300
  }
301
+ return;
302
+ }
303
+ // The watcher reads the wasm's embedded instance_version at load and compares it to the
304
+ // plugkit.version text file (file_version), exposing version_drifted when they disagree.
305
+ // This catches the case where the version text was bumped (e.g. ensureReady's remote-latest
306
+ // override) but the cached plugkit.wasm bytes are a different build -- the text claims 635
307
+ // while the binary embeds 634, so ensureReady's text-only drift check never re-downloads.
308
+ // On that drift, evict the stale cached wasm so the next bootstrap fails isReady() and
309
+ // redownloads the correct build, then recycle the child to load it.
310
+ if (status.version_drifted === true) {
311
+ logEvent('supervisor.version-drift', {
312
+ watcher_pid: currentChildPid,
313
+ instance_version: status.instance_version || null,
314
+ file_version: status.file_version || null,
315
+ severity: 'critical',
316
+ });
317
+ try {
318
+ const home = process.env.USERPROFILE || process.env.HOME || require('os').homedir();
319
+ const gmTools = fs.existsSync(path.join(home, '.gm-tools'))
320
+ ? path.join(home, '.gm-tools')
321
+ : path.join(home, '.claude', 'gm-tools');
322
+ for (const f of ['plugkit.wasm', 'plugkit.version', 'plugkit.wasm.sha256']) {
323
+ try { fs.unlinkSync(path.join(gmTools, f)); } catch (_) {}
324
+ }
325
+ } catch (_) {}
326
+ try { process.kill(currentChildPid, 'SIGTERM'); } catch (_) {}
327
+ if (process.platform === 'win32') {
328
+ try { spawnSync('taskkill', ['/F', '/T', '/PID', String(currentChildPid)], { stdio: 'ignore', windowsHide: true, timeout: 3000 }); } catch (_) {}
329
+ }
301
330
  }
302
331
  }
303
332