Product design skills

scripts/invoke.mjs

A supporting file of the silver-measure skill, shown as source.

#!/usr/bin/env node
// Generated by The Silver Design Framework.
//
// The guarded runtime needs dependencies an installed workspace does not carry,
// so prefer the CLI, which always resolves them:
//
//   .silver/bin/silver invoke --scaffold <skill-id> .
//   .silver/bin/silver invoke <skill-id> <request.json> .
//
// This shim stays for workspaces nested inside a Silver npm installation.
import path from "node:path";
import { fileURLToPath } from "node:url";

const skillDirectory = new URL("..", import.meta.url);
const skillId = path.basename(fileURLToPath(skillDirectory).replace(/[\\/]$/, ""));

let runtime;
let failure;
// The installed package resolves its own bundled dependencies through its
// package name, so the first rung is the one that runs. The second is a genuine
// long shot: `.silver/runtime/` resolves only where ajv and yaml are reachable
// from the workspace, and a plain npm install does not make them reachable —
// Silver bundles them inside its own package, and Node's resolver walks upward
// through ancestor node_modules directories, never into a sibling package's
// private tree. Read the mirror as inspectable, integrity-checked evidence of
// the rules being enforced; the CLI is the engine.
for (const specifier of [
  "silver-design-framework/framework/runtime/invoke-skill.mjs",
  "../../../.silver/runtime/invoke-skill.mjs",
]) {
  try {
    runtime = await import(specifier);
    break;
  } catch (error) {
    failure = error;
  }
}

if (!runtime) {
  const error = failure;
  console.error(
    [
      `Cannot load the Silver runtime from this workspace: ${error.message}`,
      "",
      `Run the skill through the CLI instead, which resolves its dependencies:`,
      `  .silver/bin/silver invoke --scaffold ${skillId} .`,
      `  .silver/bin/silver invoke ${skillId} <request.json> .`,
      "",
      "If .silver/bin/silver is missing or points at a moved installation, run",
      "`silver repair` from your Silver checkout to regenerate it.",
    ].join("\n"),
  );
  process.exit(2);
}

runtime
  .runSkillCli({ skillDirectory, args: process.argv.slice(2) })
  .then((code) => {
    process.exitCode = code;
  });