sindresorhus/got · error · Error
Unexpected option: ${key}
Error message
Unexpected option: ${key} What it means
Thrown by `Options.merge()` when the merged options object contains a top-level key that is not a known Options property (and not in the `nonMergeableKeys` set: mutableDefaults, handlers, url, preserveHooks, isStream, __proto__). Got validates keys against its own schema to surface typos and unsupported options early instead of silently ignoring them.
Source
Thrown at source/core/options.ts:1712
}
options = cloneRaw(options);
init(this, options, this);
init(options, options, this);
this.#merging = true;
try {
let push = false;
for (const key of Object.keys(options)) {
if (nonMergeableKeys.has(key)) {
continue;
}
if (!(key in this)) {
throw new Error(`Unexpected option: ${key}`);
}
// @ts-expect-error Type 'unknown' is not assignable to type 'never'.
const value = options[key as keyof Options];
if (value === undefined) {
continue;
}
// @ts-expect-error Type 'unknown' is not assignable to type 'never'.
this[key as keyof Options] = value;
push = true;
}
if (push) {
this.#init.push(options);
}
} finally {View on GitHub (pinned to e3924aa1e5)
Solutions
- Check the error message for the offending `${key}` and compare against the Got options docs (most often it is a rename like `baseUrl`->`prefixUrl`, `searchParameters`->`searchParams`).
- Fix the typo/rename in your options object.
- If you need to pass custom data, store it under the `context` option instead of an unknown top-level key.
Example fix
// before
await got(url, {timout: {request: 5000}});
// after
await got(url, {timeout: {request: 5000}}); Defensive patterns
Strategy: validation
Validate before calling
import got from 'got';
const knownKeys = new Set(Object.getOwnPropertyNames(got.extend({}).defaults?.options ?? {}).concat(['method','headers','timeout','url','prefixUrl']));
function validateOptions(options) {
for (const key of Object.keys(options ?? {})) {
if (!knownKeys.has(key)) throw new Error(`Unknown Got option: ${key}`);
}
} Type guard
// Got ships TypeScript types; rely on the compiler:
import type {OptionsInit} from 'got';
function isOptionsInit(o: unknown): o is OptionsInit {
return typeof o === 'object' && o !== null;
} Try / catch
try { await got(url, opts); }
catch (error) {
if (error instanceof Error && error.message.startsWith('Unexpected option:')) {
const key = error.message.split(': ')[1];
delete opts[key];
return got(url, opts);
}
throw error;
} Prevention
- Keep TypeScript strict so unknown keys are compile errors.
- Centralize all Got option construction in one helper and lint for known keys.
- When migrating from another lib, map option names explicitly rather than spreading.
When it happens
Trigger: Calling `got(url, {timout: 5000})` (typo), `got(url, {baseUrl: '...'})` (the option is named `prefixUrl`), or any call where the options object has a key that is not a real Options setter. Also triggered by `got.extend({...})` with the same kind of unknown key.
Common situations: Migrating from `request`/`axios` (`baseURL`, `proxy` object shapes), autocomplete-induced typos, copy-pasting options from another HTTP library, or upgrading Got versions where an option was renamed.
Related errors
- Unexpected hook event: ${knownHookEvent}
- Unexpected retry option: ${key}
- Unexpected agent option: ${key}
- Unexpected timeout option: ${key}
- Missing hook event: ${knownHookEvent}
AI-assisted analysis of sindresorhus/got@e3924aa1e5 (2026-08-03).
Data as JSON: /data/errors/f706b9847a2b4add.json.
Report an issue: GitHub.