finitemonkey 0.1.0-next.7 → 0.1.0-next.8

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.
@@ -4611,6 +4611,7 @@ var LOCK_FILE = ".finitemonkey/lock.json";
4611
4611
  var BACKUPS_DIR = ".finitemonkey/backups";
4612
4612
  var LOCKS_DIR = ".finitemonkey/locks";
4613
4613
  var INSTALL_LOCK = ".finitemonkey/locks/install.lock";
4614
+ var VERIFY_SKILL = ".claude/skills/verify/SKILL.md";
4614
4615
  var LOCAL_BIN = "node_modules/finitemonkey/dist/finitemonkey.mjs";
4615
4616
  var VENDOR_BIN = ".finitemonkey/runtime/dist/finitemonkey.mjs";
4616
4617
  var VENDOR_PACKAGE = ".finitemonkey/runtime/package.json";
@@ -11277,6 +11278,33 @@ var withoutBlock = (text6) => {
11277
11278
  return [...lines3.slice(0, range.start), ...lines3.slice(range.end + 1)].join(eol);
11278
11279
  };
11279
11280
 
11281
+ // src/install/skill-template.ts
11282
+ var gateCommand2 = (runner) => {
11283
+ const args = "gate --fast --json";
11284
+ if (runner.kind === "local") return `node ${LOCAL_BIN} ${args}`;
11285
+ if (runner.kind === "vendored") return `node ${VENDOR_BIN} ${args}`;
11286
+ return isScript(runner.path) ? `node "${runner.path}" ${args}` : `"${runner.path}" ${args}`;
11287
+ };
11288
+ var verifySkillTemplate = (runner) => [
11289
+ "---",
11290
+ "name: verify",
11291
+ "description: >-",
11292
+ " Use before every commit and before telling the person something works. Runs the fast gate through Finite Monkey so the result is recorded as evidence for the current tree instead of being taken on your word.",
11293
+ "when_to_use: >-",
11294
+ " Trigger phrases include commit, run the tests, check it works, roda os testes, confere, verifica, prueba.",
11295
+ "---",
11296
+ "",
11297
+ "# Verify: evidence, not claims",
11298
+ "",
11299
+ `1. From the project root, run \`${gateCommand2(runner)}\`.`,
11300
+ "2. Read `data`; for every failing item, fix the cause, never the check.",
11301
+ "3. Quote the command and its exit code when you report a result. A result from before your last edit no longer counts.",
11302
+ "",
11303
+ `<!-- ${GENERATED_MARKER} -->`,
11304
+ ""
11305
+ ].join("\n");
11306
+ var isOwnSkill = hasMarker;
11307
+
11280
11308
  // src/install/vendor.ts
11281
11309
  var isBundle = (text6) => text6.startsWith("#!/usr/bin/env node") && text6.includes("finitemonkey");
11282
11310
  var isOwnPackage = (text6) => {
@@ -11365,18 +11393,21 @@ var generatedItem = (project, file, previous) => {
11365
11393
  }
11366
11394
  return { ...base, action: actionFor(before, template, "update"), after: template };
11367
11395
  };
11368
- var generatedFiles = (input, vendor) => {
11369
- const config = { path: CONFIG_FILE, template: configTemplate(input.t, input.preset, input.lang), isOurs: hasMarker };
11370
- if (!vendor) return accept([config]);
11396
+ var generatedFiles = (input, runner, vendor) => {
11397
+ const own = [
11398
+ { path: CONFIG_FILE, template: configTemplate(input.t, input.preset, input.lang), isOurs: hasMarker },
11399
+ { path: VERIFY_SKILL, template: verifySkillTemplate(runner), isOurs: isOwnSkill }
11400
+ ];
11401
+ if (!vendor) return accept(own);
11371
11402
  if (input.bundle === void 0) return reject({ kind: "bundle", detail: "the running finitemonkey is not a bundle" });
11372
- return accept([config, ...vendoredFiles(input.bundle, input.version)]);
11403
+ return accept([...own, ...vendoredFiles(input.bundle, input.version)]);
11373
11404
  };
11374
11405
  var entryFor = (lock, path) => lock?.entries.find((entry2) => entry2.path === path);
11375
11406
  var buildPlan = (project, detection, input, previous) => {
11376
11407
  const settings = settingsItem(project, detection, input, entryFor(previous, SETTINGS_FILE));
11377
11408
  if (!settings.ok) return settings;
11378
11409
  const vendor = detection.runner.kind === "vendored" || entryFor(previous, VENDOR_BIN) !== void 0;
11379
- const files = generatedFiles(input, vendor);
11410
+ const files = generatedFiles(input, detection.runner, vendor);
11380
11411
  if (!files.ok) return files;
11381
11412
  const generated = files.value.map((file) => generatedItem(project, file, entryFor(previous, file.path)));
11382
11413
  return accept({
@@ -11433,7 +11464,7 @@ var nextLock = (plan, version, now, backupDir, createdDirs) => ({
11433
11464
  preset: plan.preset,
11434
11465
  installedAt: plan.previous?.installedAt ?? now,
11435
11466
  updatedAt: now,
11436
- createdDirs: plan.previous?.createdDirs ?? createdDirs,
11467
+ createdDirs: [.../* @__PURE__ */ new Set([...plan.previous?.createdDirs ?? [], ...createdDirs])],
11437
11468
  entries: plan.items.filter((item) => item.action !== "skip-foreign").map((item) => entryOf2(plan, item, backupDir))
11438
11469
  });
11439
11470
  var needsBackup = (plan, item) => item.before !== void 0 && plan.previous?.entries.find((entry2) => entry2.path === item.path)?.backup === void 0;
@@ -11449,7 +11480,8 @@ var writeAll = (project, items) => {
11449
11480
  }
11450
11481
  return accept(void 0);
11451
11482
  };
11452
- var createdBy = (project) => [".claude", STATE_DIR].filter((dir) => !project.exists(dir));
11483
+ var OWN_DIRS = [dirname6(dirname6(VERIFY_SKILL)), dirname6(VERIFY_SKILL), ".claude", STATE_DIR];
11484
+ var createdBy = (project) => OWN_DIRS.filter((dir) => !project.exists(dir));
11453
11485
  var commit = (project, plan, version, createdDirs) => {
11454
11486
  const now = project.runtime.now();
11455
11487
  const changing = plan.items.filter((item) => CHANGING.includes(item.action));
@@ -12539,7 +12571,7 @@ var removalFor = (project, entry2, options) => {
12539
12571
  var planRemoval = (project, lock, options) => ({
12540
12572
  items: lock.entries.map((entry2) => removalFor(project, entry2, options)),
12541
12573
  purge: options.purge,
12542
- removeDirs: lock.createdDirs.filter((dir) => dir !== STATE_DIR)
12574
+ removeDirs: lock.createdDirs.filter((dir) => dir !== STATE_DIR).toSorted((a, b) => b.split("/").length - a.split("/").length)
12543
12575
  });
12544
12576
  var applyItem = (project, item) => {
12545
12577
  if (item.action === "delete") {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "finitemonkey",
3
- "version": "0.1.0-next.7",
3
+ "version": "0.1.0-next.8",
4
4
  "description": "Claude Code hooks that stop a coding agent from saying done before the tests pass: a machine-checked definition of done, plus guardrails for secrets, git safety and production. Pre-release.",
5
5
  "type": "module",
6
6
  "license": "Apache-2.0",