karatelabs/karate · error · RuntimeException

cache() requires (key, fn)

Error message

cache() requires (key, fn)

What it means

HttpRequest.cache() is a memoization helper exposed to scripts: it takes a cache key and a function, returning the cached value on a hit or invoking the function and caching the result. Called with fewer than two arguments it throws this RuntimeException because it cannot perform either the key lookup or the lazy evaluation.

Solutions

  1. Supply both arguments: request.cache('key', () => expensiveCall())
  2. If you only meant to read a cached value, guard the read yourself or use the cache store API directly
  3. Ensure the second argument is actually a function (a plain value will trigger the companion 'second argument must be a function' error)
  4. Check for script minification/refactor tooling that dropped trailing lambda arguments

Example fix

// before
request.cache("token"); // throws
// after
request.cache("token", () => karate.callSingle("classpath:auth.feature"));
Defensive patterns

Strategy: validation

Validate before calling

if (arguments.length < 2) throw new Error('cache() requires (key, fn)');
request.cache(key, fn);

Type guard

function cacheArgsOk(key, fn) { return key != null && typeof fn === 'function'; }

Prevention

When it happens

Trigger: Calling cache() with 0 or 1 argument, e.g. request.cache('mykey') without the value-producing function, or cache() entirely bare — usually a dropped argument in a chained script expression or a partial refactor.

Common situations: Caching expensive setup calls (tokens, fixtures) in HTTP scripts where the closure argument was accidentally deleted; users confusing this cache() with Karate's karate.cache-style helpers with different signatures.

Understand the failure class

Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.

Related errors


AI-assisted analysis of karatelabs/karate@a22eb90246 (2026-09-12). Data as JSON: /api/errors/ab0294e6a8f57835. Report an issue: GitHub.

Appendix: source

Thrown at karate-core/src/main/java/io/karatelabs/http/HttpRequest.java:755

            return proceed(targetUrl);
        };
    }

    /**
     * Per-request memoization. {@code request.cache('key', () => compute())}
     * invokes the function on the first call with that key, stores the result
     * on this request, and returns the same value on subsequent calls. The
     * store dies with the request — never crosses request boundaries.
     * <p>
     * The two-argument form is the only supported shape. If the key is
     * missing, the second argument must be a function (otherwise a runtime
     * error is raised). A cached {@code null} or {@code undefined} return
     * value is still a cache hit and does not re-invoke the function.
     */
    private JavaCallable cache() {
        return (context, args) -> {
            if (args.length < 2) {
                throw new RuntimeException("cache() requires (key, fn)");
            }
            String key = args[0] + "";
            if (cacheStore != null && cacheStore.containsKey(key)) {
                return cacheStore.get(key);
            }
            if (!(args[1] instanceof JavaCallable fn)) {
                throw new RuntimeException("cache() second argument must be a function: " + key);
            }
            Object value = fn.call(context);
            if (cacheStore == null) {
                cacheStore = new HashMap<>();
            }
            cacheStore.put(key, value);
            return value;
        };
    }

    @Override

View on GitHub (pinned to a22eb90246)