2026-07-27

Why did gemini-2.0-flash suddenly start 404ing in production?

Google retired gemini-2.0-flash on 2026-06-01. If your app hardcodes that model ID, it stops working with no warning — here is the fix and why it catches people off guard.

If you woke up to a pile of 500s and a Gemini error that reads something like 404 — This model models/gemini-2.0-flash is no longer available, you are not alone. Google retired gemini-2.0-flash on 2026-06-01, and any code that hardcodes that model string started failing hard — not a deprecation warning, not a graceful fallback, a flat 404 on every call.

This site mostly covers the *other* migration — the silent regression when you move from gemini-3-flash-preview to gemini-3.5-flash and forget to set thinking_level explicitly (see /migrate). But the 2.0-flash retirement is a distinct and arguably worse failure mode: it does not silently degrade output quality, it takes the endpoint down entirely for anyone still pointed at the old model ID.

A real example

A concrete case: a photo-to-ticket pipeline (a small OSS project, TyShaneONeill/movie-tracker) had a background job that called gemini-2.0-flash to classify uploaded images. On 2026-06-05, four days after the retirement, the job started throwing on every invocation. The fix landed as PR #513 — swap the model string to a currently-supported model and re-verify the prompt still behaves the same way (it usually does not, exactly — see the note on thinking_level below).

The pattern here is common: a model ID gets pinned once during initial development, ships, and nobody revisits it until Google retires the model. If your CI does not make a live API call against the real endpoint, a retirement like this will not show up until it hits production.

The fix

Three steps, in order of urgency:

1. Grep your codebase for gemini-2.0-flash (and any other model string you might have hardcoded) and confirm none of them are still live-called.

2. Move to a currently-supported model. If you were already planning to move to gemini-3.5-flash, do it now rather than picking another soon-to-be-retired stopgap — but read /migrate first, because the model swap alone is not enough. The thinking_level default changed too, and skipping that step means your pipeline will run again but produce measurably worse output with zero errors to tell you.

3. Add a scheduled smoke test that makes one real call to your production model ID and asserts on the HTTP status, not just a mocked response. This is the only way to catch a retirement before your users do.

Why this keeps happening

Google's Gemini model lineup moves fast, and retirements are typically announced with a lead time — but "announced" and "seen by the engineer who wrote the original integration eight months ago" are two different things. If nobody owns your AI model versions the way you'd own a dependency in package.json, a retirement announcement in a changelog nobody reads becomes a production outage.

If you landed here because of a 404 and not a silent quality regression, welcome — you have the easier problem. Swap the model ID, read /migrate for the config changes that go with it, and set up that smoke test before the next retirement catches you again.