jestjs/jest · error · Error

${EXPECTED_COLOR('expected')} value must be a non-negative i

Error message

${EXPECTED_COLOR('expected')} value must be a non-negative integer

What it means

Thrown by ensureExpectedIsNonNegativeInteger in jest-matcher-utils. It guards matchers that take a positional index/count argument — notably haveBeenNthCalledWith and haveNthReturnedWith — requiring the expected argument to be a non-negative safe integer (no floats, no negatives, no strings).

Source

Thrown at packages/jest-matcher-utils/src/index.ts:242

  options?: MatcherHintOptions,
): void => {
  ensureActualIsNumber(actual, matcherName, options);
  ensureExpectedIsNumber(expected, matcherName, options);
};

export const ensureExpectedIsNonNegativeInteger = (
  expected: unknown,
  matcherName: string,
  options?: MatcherHintOptions,
): void => {
  if (
    typeof expected !== 'number' ||
    !Number.isSafeInteger(expected) ||
    expected < 0
  ) {
    // Prepend maybe not only for backward compatibility.
    const matcherString = (options ? '' : '[.not]') + matcherName;
    throw new Error(
      matcherErrorMessage(
        matcherHint(matcherString, undefined, undefined, options),
        `${EXPECTED_COLOR('expected')} value must be a non-negative integer`,
        printWithType('Expected', expected, printExpected),
      ),
    );
  }
};

// Given array of diffs, return concatenated string:
// * include common substrings
// * exclude change substrings which have opposite op
// * include change substrings which have argument op
//   with inverse highlight only if there is a common substring
const getCommonAndChangedSubstrings = (
  diffs: Array<Diff>,
  op: number,
  hasCommonDiff: boolean,

View on GitHub (pinned to 8e6d128e4a)

Solutions

  1. Pass a non-negative integer (>=1 for nth-style matchers) literal or verified variable.
  2. If the index is computed, guard it with Number.isInteger(n) && n >= 0 before the assertion.
  3. Round or floor floats and parseInt string sources before passing.

Example fix

// before
expect(fn).toHaveBeenNthCalledWith(i, payload);
// after
expect(Number.isInteger(i) && i >= 1).toBe(true);
expect(fn).toHaveBeenNthCalledWith(i, payload);
Defensive patterns

Strategy: validation

Validate before calling

if (!Number.isSafeInteger(nth) || nth < 0) {
  throw new TypeError(`nth must be a non-negative integer, got ${nth}`);
}
expect(fn).toHaveBeenNthCalledWith(nth, ...args);

Type guard

const isNonNegInt = (x: unknown): x is number =>
  typeof x === 'number' && Number.isSafeInteger(x) && x >= 0;

Prevention

When it happens

Trigger: expect(fn).toHaveBeenNthCalledWith(-1, x); expect(fn).toHaveBeenNthCalledWith(1.5, x); expect(fn).toHaveNthReturnedWith('2', x); expect(fn).toHaveBeenNthCalledWith(NaN, x).

Common situations: Off-by-one in loop-driven assertions; passing a computed float index; reading an index from a string source; using 0 for nth when the matcher is 1-indexed (0 itself passes the guard but may misbehave in the matcher).

Related errors


AI-assisted analysis of jestjs/jest@8e6d128e4a (2026-08-10). Data as JSON: /api/errors/f7876b9eaa0eab9a. Report an issue: GitHub.