denoland/deno · error · AssertionError

Missing snapshot

Error message

Missing snapshot: ${name}

What it means

assertSnapshot identifies each entry by `<full test name> <counter>` (or an explicit options.name plus counter). If the snapshot file exists but contains no entry for that key, check mode throws AssertionError `Missing snapshot: <name>` (cli/js/40_test_snapshot.js). The file being present but the entry absent points at drift between the tests and the recorded snapshots rather than a missing file.

Solutions

  1. Run `deno test --update` to record the missing entry, review the diff, and commit the updated snapshot file.
  2. If tests were renamed or reordered intentionally, --update is the correct fix; if not, revert the test-name change.
  3. Give critical snapshots explicit stable names (`{ name: "output" }`) so they do not depend on test names and call ordering.
  4. Ensure each assertSnapshot call site is stable — adding/removing one mid-test shifts the counters of all following entries.

Example fix

// before
Deno.test("renders widget", async (t) => {
  await t.assertSnapshot(render()); // depends on full test name + order
});

// after
Deno.test("renders widget", async (t) => {
  await t.assertSnapshot(render(), { name: "widget-render" }); // stable key
});
Defensive patterns

Strategy: validation

Validate before calling

// Give critical snapshots explicit, stable keys so entries survive test renames:
await t.assertSnapshot(value, { name: "widget-render" });

Try / catch

try {
  await t.assertSnapshot(value);
} catch (err) {
  if (String(err.message).startsWith("Missing snapshot:")) {
    // stale snapshot store — regenerate intentionally:
    // deno test --update
  }
  throw err;
}

Prevention

When it happens

Trigger: Renaming a test (the full nested name changes, so old entries no longer match); adding a new assertSnapshot call to an existing test (counters of later assertions shift); deleting or reordering earlier assertions in the same test; using a new options.name; running only a filtered subset of tests that share a snapshot file for the first time after edits.

Common situations: Test renamed during a refactor while snapshots stayed stale; an assertion added mid-test shifting every subsequent count; teammates regenerating snapshots on different test versions; explicit names that were changed.

Related errors


AI-assisted analysis of denoland/deno@9ad36f7a2c (2026-08-20). Data as JSON: /api/errors/328f2f149de69f08. Report an issue: GitHub.

Appendix: source

Thrown at cli/js/40_test_snapshot.js:358

  const expectedSnapshot = MapPrototypeGet(context.currentValues, name);

  if (getIsUpdateMode()) {
    if (actualSnapshot !== expectedSnapshot) {
      MapPrototypeSet(context.updatedValues, name, actualSnapshot);
      if (!ArrayPrototypeIncludes(context.updatedNames, name)) {
        ArrayPrototypePush(context.updatedNames, name);
      }
    }
    return;
  }

  if (!context.fileExists) {
    throw new AssertionError(
      getErrorMessage("Missing snapshot file.", options),
    );
  }
  if (expectedSnapshot === undefined) {
    throw new AssertionError(
      getErrorMessage(`Missing snapshot: ${name}`, options),
    );
  }
  if (actualSnapshot === expectedSnapshot) {
    return;
  }
  throw new AssertionError(
    getErrorMessage(
      getSnapshotNotMatchMessage(actualSnapshot, expectedSnapshot),
      options,
    ),
  );
}

function buildSnapshotFileContent(names, getValue) {
  const buf = ["export const snapshot = {};"];
  for (const name of new SafeArrayIterator(names)) {
    const value = getValue(name);

View on GitHub (pinned to 9ad36f7a2c)