withfig/autocomplete · warning · Error

Script not found: '${token}'

Error message

Script not found: '${token}'

What it means

After loading `${npmPrefix}/package.json`, the generator reads `scripts[token]` to resolve the requested npm script. If the parsed JSON has no `scripts` object or no entry matching the typed token, the spec throws this Error because completion cannot resolve the script's command.

Source

Thrown at src/yarn.ts:20

export const yarnScriptParserDirectives: Fig.Arg["parserDirectives"] = {
  alias: async (token, executeShellCommand) => {
    const npmPrefix = await executeShellCommand({
      command: "npm",
      // eslint-disable-next-line @withfig/fig-linter/no-useless-arrays
      args: ["prefix"],
    });
    if (npmPrefix.status !== 0) {
      throw new Error("npm prefix command failed");
    }
    const packageJson = await executeShellCommand({
      command: "cat",
      // eslint-disable-next-line @withfig/fig-linter/no-useless-arrays
      args: [`${npmPrefix.stdout.trim()}/package.json`],
    });
    const script: string = JSON.parse(packageJson.stdout).scripts?.[token];
    if (!script) {
      throw new Error(`Script not found: '${token}'`);
    }
    return script;
  },
};

export const nodeClis = new Set([
  "vue",
  "vite",
  "nuxt",
  "react-native",
  "degit",
  "expo",
  "jest",
  "next",
  "electron",
  "prisma",
  "eslint",
  "prettier",

View on GitHub (pinned to aef52acff8)

Solutions

  1. Run `npm run` (or `yarn run`) with no arguments to list available scripts and confirm the exact name
  2. Check that the script exists in the package.json file the generator reads (`cat $(npm prefix)/package.json`) — note it is the global prefix, not your project, so scripts defined in a local project will not be found here
  3. Fix the typo or add the missing script to the scripts field
  4. If your scripts live in a local package.json, verify the spec's prefix resolution matches your project layout

Example fix

// before
const script: string = JSON.parse(packageJson.stdout).scripts?.[token];
// after (fall back to the local project's package.json)
const parsed = JSON.parse(packageJson.stdout);
const script: string =
  parsed.scripts?.[token] ??
  JSON.parse((await executeShellCommand({ command: "cat", args: ["package.json"] })).stdout).scripts?.[token];
Defensive patterns

Strategy: validation

Validate before calling

import { readFileSync } from "fs";
export function scriptExists(prefix: string, token: string): boolean {
  const pkg = JSON.parse(readFileSync(`${prefix}/package.json`, "utf8"));
  return Boolean(pkg.scripts && token in pkg.scripts);
}
// call before resolving: if (!scriptExists(npmPrefix, token)) return [];

Type guard

function hasScript(pkg: unknown, token: string): pkg is { scripts: Record<string, string> } & Record<string, unknown> {
  return typeof pkg === "object" && pkg !== null &&
    "scripts" in pkg && typeof (pkg as any).scripts === "object" &&
    token in (pkg as any).scripts && typeof (pkg as any).scripts[token] === "string";
}

Try / catch

try {
  const script = await resolveScript(token);
} catch (err) {
  if (err instanceof Error && err.message.startsWith("Script not found:")) {
    // unknown token: return the list of available scripts instead of throwing
    return listAvailableScripts();
  }
  throw err;
}

Prevention

When it happens

Trigger: The typed token is not a key of the `scripts` field in package.json at the npm prefix directory, or package.json has no `scripts` field at all (`undefined` fails the `if (!script)` check).

Common situations: User typed a script that exists in the local project but not in the global-prefix package.json the generator reads; typo in script name; scripts removed/renamed in a package.json version bump; monorepo scripts defined only in workspace packages.

Related errors


AI-assisted analysis of withfig/autocomplete@aef52acff8 (2026-08-31). Data as JSON: /api/errors/ff527a7305e68c04. Report an issue: GitHub.