## TL;DR
`failed to execute 'fetch' on 'window': illegal invocation` (Chrome capitalises it as `Failed to execute 'fetch' on 'Window': Illegal invocation`) means fetch was called with the wrong receiver: the function was detached from `window` and invoked unbound, and fetch refuses to run without its Window. In your own code, call `window.fetch(...)` directly or bind it first with `window.fetch.bind(window)`. If the error comes from a library bundle such as `airtable.browser.js`, the bundle detached fetch internally: update to the latest build of that library, where the maintainers merged the fix.

```text
TypeError: Failed to execute 'fetch' on 'Window': Illegal invocation
```

Firefox words the same failure as: 'fetch' called on an object that does not implement interface Window.

## Use this when
- The error appears the moment any fetch-based call runs, before any network activity
- You stored fetch in a variable, passed it as a callback, or destructured it off window
- A browser bundle (the reported case is airtable.browser.js with select().eachPage()) throws it on every call
- The same code works when the request is made with a direct fetch call in the console

## Not for this skill when
- The error is a CORS rejection (the console names Access-Control-Allow-Origin; different fix, see related skills)
- The error says Failed to fetch with a network or DNS cause (server down, mixed content, offline)
- You are in Node.js, where there is no window at all (the fix there is upgrading Node or your fetch polyfill, not binding)

## Steps

1. Confirm detachment with a minimal test in the page console:

```js
const detached = window.fetch;
detached('https://example.com'); // throws Illegal invocation
window.fetch('https://example.com'); // works
```

Expected: the detached call throws the exact TypeError and the direct call does not. That split confirms the binding is the problem, not the URL or the server.

2. Fix your own code: never call a stored fetch unbound. Either call it as a method of window, or bind it at the point you store it:

```js
const boundFetch = window.fetch.bind(window);
boundFetch('https://example.com');
```

Expected: the stored reference now runs. The same rule applies to code that destructures fetch off window, wraps it in a logger, or passes it as a callback argument.

3. If a library throws it (the verified case is airtable.browser.js): the bundle captured fetch detached from window, so every call through the library fails the same way. Update to the latest airtable.js release and re-download the browser build; users verified a patched build fixes it and the maintainers merged that fix into the published bundle.

Expected: `new Airtable(...)` followed by `select().eachPage()` completes without the TypeError. If you are pinned to the old bundle and cannot update yet, the community-fixed build was the workaround people used, but updating is the clean fix.

4. Check your bundler and wrappers last: some bundler configs and analytics wrappers replace or re-export fetch. If a fresh direct call works but the app still throws, search the bundle for where fetch is assigned to a variable and apply step 2 there, or upgrade the wrapper.

Expected: the first network call from the app succeeds with no Illegal invocation in the console.

## Variant phrasings

### 'fetch' called on an object that does not implement interface Window
Firefox's wording for the same detached-fetch failure. Same cause, same bind-or-update fix.

### airtable.browser.js fails with this error on every call
That is the library case in step 3: a real bug in the old browser bundle, fixed in the current build. Updating replaces the detached internal fetch call.

### Illegal invocation after storing fetch for retries or logging
Your own wrapper detached it. Bind at storage time (step 2) rather than at every call site.

## Why it happens
fetch is specified as a method of the Window object and the browser checks the receiver on every call: the internal slots it needs live on window, so an unbound call has nothing to read and the browser throws Illegal invocation. Most native-looking global functions tolerate detachment; fetch (and a few others, like alert in some engines) do not. Libraries written against Node-style fetch, where detachment is harmless, ship this bug into browser bundles until they bind fetch internally.

## Edge cases
- iframes: fetch belongs to the frame's window it came from. Calling one frame's fetch from another frame's context can throw the same error; use the fetch of the window that owns the code.
- Test runners and jsdom-style environments implement fetch differently; if the error only appears in tests, check the environment's fetch implementation before binding production code.

## Tool compatibility
Chrome and Firefox (wording differs, above), any page or browser bundle that calls the native fetch. The airtable.js fix is in the current published browser build; older pinned bundles still throw it.

## Related skills
- 1Password passkey causes Illegal Invocation error: https://vectle.com/skills/skl_UATszmGCJs3fg3x2A_GFuw
- No 'Access-Control-Allow-Origin' header is present on the requested resource: https://vectle.com/skills/skl_cbb_ym-EVf2I9eFCL6eA9A

## Provenance
Resolved from the public thread on the airtable.browser.js case: every call failed with this TypeError in Chrome, and a patched browser build fixed it.
