> ## Documentation Index
> Fetch the complete documentation index at: https://docs.gloo.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Choosing, Pinning and Updating Models

> Best practices for picking a Gloo AI model from the catalog, pinning its ID, noticing deprecations and redirects, and moving to a new model on your own timeline.

Models change underneath every AI application: providers release better ones and retire old ones, sometimes at a different price. This page is for developers running Gloo AI in production who want to choose a model deliberately, keep it fixed, and move to the next one when they are ready rather than when a provider decides.

> [!TIP]
>
> New to choosing models? [Choosing a Model](https://docs.gloo.com/ai-learning-center/gloo-ai-104/cost-and-speed.md#choosing-a-model) in the AI Learning Center explains the trade-offs, and [Model Lifecycle](https://docs.gloo.com/api-guides/model-lifecycle.md) is the policy this page builds on.

This page covers how to:

* pick a model from the catalog by what your task needs
* pin the model ID so it doesn't change between calls
* notice deprecations early, from the catalog and from response headers
* move to a new model after testing it, on your own timeline

## Pick from the catalog by what the task needs

The [model catalog](https://docs.gloo.com/api-guides/supported-models.md), [`GET /platform/v2/models`](https://docs.gloo.com/api-reference/get-models/v2), is public and needs no [API key](https://docs.gloo.com/studio/manage-api-credentials.md). Each entry describes what the model can do, so you can rule models in or out before you try them:

| You need | Catalog field |
| :- | :- |
| The model to call your functions | `supports_tools: true` |
| The model to read images | `supports_vision: true`, and `"image"` in `input_modalities` |
| Answers as they're written | `supports_streaming: true` |
| Control over thinking | `reasoning`: `effort_levels`, `thinks_by_default`, `can_disable` ([Reasoning](https://docs.gloo.com/api-guides/supported-models.md#reasoning)) |
| Room for long inputs | `context_window` and `max_input_tokens` |
| Long answers | `max_output_tokens`, the most it can produce, reasoning and answer together |
| A price that fits | `pricing.input`, `pricing.output`, and `cache_read` / `cache_write` where the model caches |
| A rough sense of speed and quality | `speed` (1 slowest to 5 fastest) and `reasoning_level` (an overall quality rating from 0 to 5) |

Filter the catalog in code rather than copying IDs by hand. This picks every current chat model that calls tools and reads images, cheapest output first:

```python Python theme={null}
import requests

catalog = requests.get("https://platform.ai.gloo.com/platform/v2/models", timeout=30).json()["data"]

candidates = sorted(
    (
        m for m in catalog
        if not m.get("is_deprecated")
        and "text" in m.get("output_modalities", [])
        and m.get("supports_tools")
        and m.get("supports_vision")
    ),
    key=lambda m: float(m["pricing"]["output"]["rate_per_1m_tokens"]),
)

for m in candidates[:5]:
    print(m["id"], m["context_window"], m["pricing"]["output"]["rate_per_1m_tokens"])
```

```typescript TypeScript theme={null}
const res = await fetch("https://platform.ai.gloo.com/platform/v2/models");
const catalog: any[] = (await res.json()).data;

const candidates = catalog
  .filter(
    (m) =>
      !m.is_deprecated &&
      (m.output_modalities ?? []).includes("text") &&
      m.supports_tools &&
      m.supports_vision,
  )
  .sort(
    (a, b) =>
      Number(a.pricing.output.rate_per_1m_tokens) - Number(b.pricing.output.rate_per_1m_tokens),
  );

for (const m of candidates.slice(0, 5)) {
  console.log(m.id, m.context_window, m.pricing.output.rate_per_1m_tokens);
}
```

```bash cURL theme={null}
curl -s https://platform.ai.gloo.com/platform/v2/models \
  | jq -r '[.data[] | select((.is_deprecated | not) and ((.output_modalities // []) | index("text")) and .supports_tools and .supports_vision)]
           | sort_by(.pricing.output.rate_per_1m_tokens | tonumber) | .[:5][]
           | "\(.id)\t\(.context_window)\t\(.pricing.output.rate_per_1m_tokens)"'
```

Then try two or three candidates on real examples from your app. The [Chat Playground](https://docs.gloo.com/studio/playground-chat.md) is a quick first look; for a decision you can repeat, run a small test set as described in [Testing, Evaluation and Observability](https://docs.gloo.com/best-practices/testing-and-observability.md).

A few rules of thumb:

* **Match the model to the step, not the app.** A classification or a short extraction rarely needs the largest model. Use a smaller, faster one there and keep the large model for the steps that need it. See [Controlling Cost](https://docs.gloo.com/best-practices/cost-control.md).
* **Check reasoning behaviour, not just quality.** A model with `thinks_by_default: true` reasons, and bills that reasoning as output, even when you send no reasoning setting. If you want short, fast answers, pick a model with `can_disable: true`. See [Reasoning Models in Production](https://docs.gloo.com/best-practices/reasoning-models.md).
* **Leave headroom in the [context window](https://docs.gloo.com/ai-learning-center/gloo-ai-101/prompting-and-generation.md#context-window).** Size for your longest real conversation plus the documents you add to it, not your average one. See [Conversations and Context Windows](https://docs.gloo.com/best-practices/conversations-and-context.md).

## Pin the model ID

Send the exact `id` from the catalog as `model` on every request, and keep it in configuration rather than scattered through your code, so changing models is a one-line change you can test and roll back.

A pinned ID gives you the same model on every call, so behaviour, cost and latency stay predictable. The Responses endpoints run the model you name (or its replacement, once that model is deprecated). On guarded [Completions](https://docs.gloo.com/api-guides/completions-v2.md#choose-how-the-model-is-selected), you can instead let Gloo choose: [`model_family`](https://docs.gloo.com/getting-started/glossary#model-family) picks a model from a provider's family, and opt-in [auto-routing](https://docs.gloo.com/getting-started/glossary.md#auto-routing) picks one per request. Both can change the model from one call to the next, so use them where that suits the task, and pin a `model` for [tool calling](https://docs.gloo.com/ai-learning-center/gloo-ai-104/tools-and-mcp.md), [structured output](https://docs.gloo.com/ai-learning-center/gloo-ai-104/structured-output.md), anything you test against, and anything you need to reproduce.

Take IDs from the catalog's `id` field. The `gloo-<provider>-<model>` pattern is a convention, not a guarantee, so don't build IDs from parts.

## Notice deprecations early

A deprecated model doesn't stop working on the day it's flagged. For a generation model with a `replacement_model`, requests for its ID are served by the replacement, so your app keeps running while you migrate. The replacement can behave differently and can cost more: a replacement's price is normally capped at 1.3 times the old rate on input or output, and any exception is stated in `deprecation_note`. See [How a replacement is chosen](https://docs.gloo.com/api-guides/model-lifecycle.md#how-a-replacement-is-chosen).

Two signals tell you a model you use is on its way out. Watch both. To see what's coming across the whole catalog, [Model Updates](https://docs.gloo.com/model-updates.md) lists every deprecation, retirement and redirect with its date and replacement model.

### Check the catalog on a schedule

Run a check daily, or in CI before each deploy, against the model IDs your app uses. Fail loudly when one is deprecated or missing:

```python Python theme={null}
import sys

import requests

MY_MODELS = {"gloo-anthropic-claude-sonnet-5.5", "gloo-openai-gpt-6-luna"}

catalog = requests.get("https://platform.ai.gloo.com/platform/v2/models", timeout=30).json()["data"]
listed = {m["id"]: m for m in catalog}

problems = []
for model_id in sorted(MY_MODELS):
    model = listed.get(model_id)
    if model is None:
        problems.append(f"{model_id}: no longer listed. Move to a listed model.")
    elif model.get("is_deprecated"):
        replacement = model.get("replacement_model") or "none: choose one yourself"
        problems.append(f"{model_id}: deprecated. Replacement: {replacement}. {model.get('deprecation_note') or ''}")

print("\n".join(problems) or "All models current.")
sys.exit(1 if problems else 0)
```

```typescript TypeScript theme={null}
const MY_MODELS = ["gloo-anthropic-claude-sonnet-5.5", "gloo-openai-gpt-6-luna"];

const res = await fetch("https://platform.ai.gloo.com/platform/v2/models");
const listed = new Map<string, any>((await res.json()).data.map((m: any) => [m.id, m]));

const problems: string[] = [];
for (const id of [...MY_MODELS].sort()) {
  const model = listed.get(id);
  if (!model) {
    problems.push(`${id}: no longer listed. Move to a listed model.`);
  } else if (model.is_deprecated) {
    const replacement = model.replacement_model ?? "none: choose one yourself";
    problems.push(`${id}: deprecated. Replacement: ${replacement}. ${model.deprecation_note ?? ""}`);
  }
}

console.log(problems.length ? problems.join("\n") : "All models current.");
process.exit(problems.length ? 1 : 0);
```

Read `deprecation_note` when a model is flagged: it says when the model retires, what replaces it and whether the price changes. When `replacement_model` is empty, nothing will serve the old ID after its retirement date, and choosing the next model is up to you.

### Watch the response headers

A successful response served by a replacement carries `X-Gloo-Model-Redirected-From` with the ID you asked for, `Deprecation: true`, and `Sunset` with the retirement date when one is set. The response's `model` names the model that actually answered. Log these on every response and alert when they appear:

```python Python theme={null}
import logging

log = logging.getLogger("gloo")


def check_model_headers(response, requested_model: str) -> None:
    redirected_from = response.headers.get("X-Gloo-Model-Redirected-From")
    sunset = response.headers.get("Sunset")
    if redirected_from:
        log.warning("Model %s was served by a replacement; retires %s", redirected_from, sunset or "(no date)")
    elif sunset:
        log.error("Model %s retires on %s with no replacement: migrate now", requested_model, sunset)
```

```typescript TypeScript theme={null}
function checkModelHeaders(response: Response, requestedModel: string): void {
  const redirectedFrom = response.headers.get("X-Gloo-Model-Redirected-From");
  const sunset = response.headers.get("Sunset");
  if (redirectedFrom) {
    console.warn(`Model ${redirectedFrom} was served by a replacement; retires ${sunset ?? "(no date)"}`);
  } else if (sunset) {
    console.error(`Model ${requestedModel} retires on ${sunset} with no replacement: migrate now`);
  }
}
```

Treat `Sunset` without `X-Gloo-Model-Redirected-From` as urgent. It means nothing replaces the model: from 00:00 UTC on that date, requests are refused with `410` and the code `model_retired`, which isn't retryable. On [Anthropic Messages](https://docs.gloo.com/api-guides/anthropic-messages.md#errors), a retired Claude model returns `404` with `model_retired` instead of being served by its replacement. See [When nothing replaces a model](https://docs.gloo.com/api-guides/model-lifecycle.md#when-nothing-replaces-a-model).

## Move to a new model on your own timeline

Automatic routing to a replacement is there so a retirement doesn't break your app. It isn't a substitute for testing: the replacement may answer differently, reason differently or cost more. Move deliberately, whether a model was deprecated or a better one has arrived:

1. **Read the note and the catalog entry.** Compare the new model's price, `context_window`, `max_output_tokens`, capability flags and `reasoning` object with the old one. A replacement with a smaller context window is called out in `deprecation_note`.
2. **Run your test set on both.** Compare quality on your own examples, the `usage` each request reports, and response times. Check structured output and tool calls especially, since small changes in format break code that reads them.
3. **Revisit your settings.** Reasoning efforts and output limits that suited one model may not suit the next: check `effort_levels` and resize `max_output_tokens` from the new model's `usage`.
4. **Switch the configured ID and watch.** Roll out to a share of traffic first if you can, and compare error rates, cut-off answers and cost before moving everything.
5. **Keep the old ID only as long as it's listed.** An ID you can still see in the catalog is supported; once its entry is removed, continued routing is a courtesy, not something to build on. See [Notice before removal](https://docs.gloo.com/api-guides/model-lifecycle.md#notice-before-removal).

You don't have to migrate the moment a generation model is flagged, but don't wait for the retirement date either.

## Embeddings don't follow replacements

Don't assume a deprecated [embedding](https://docs.gloo.com/ai-learning-center/gloo-ai-103/embeddings.md) model's requests go to a replacement. Vectors from different models aren't comparable, so changing an embedding model means re-embedding everything you've stored before you query it with the new model.

* Store the embedding model ID, and the `dimensions` you asked for, alongside every vector.
* When the catalog flags your embedding model, plan a re-embedding job, build the new index alongside the old one, and switch queries over only when it's complete.
* Embedding requests are not failed over to another provider. See [Provider Failover](https://docs.gloo.com/api-guides/provider-failover.md).

## Summary

* Choose from the catalog by capability flags, context window, reasoning behaviour and price, then test candidates on your own examples.
* Pin the exact catalog `id` in configuration; use `model_family` or auto-routing only where a changing model is fine.
* Check `is_deprecated` on a schedule, and log `X-Gloo-Model-Redirected-From`, `Deprecation` and `Sunset` on every response.
* Treat `Sunset` without a redirect header as urgent: `410 model_retired` follows on that date.
* Test a new model on your own examples before you switch, and re-embed stored content when an embedding model changes.

## Next steps

> [card] [Model Lifecycle](https://docs.gloo.com/api-guides/model-lifecycle.md)
>
> How deprecations are announced, how replacements are chosen and how much notice you get.

> [card] [Model Updates](https://docs.gloo.com/model-updates.md)
>
> Every model added, deprecated, retired or redirected, with dates and replacements.

> [card] [Supported Models](https://docs.gloo.com/api-guides/supported-models.md)
>
> The live catalog with capabilities and rates.

> [card] [Production-Ready](https://docs.gloo.com/ai-learning-center/gloo-ai-104/production-ready.md#models-come-and-go)
>
> The lesson on routing, failover and models that come and go.

> [card] [Testing, Evaluation and Observability](https://docs.gloo.com/best-practices/testing-and-observability.md)
>
> Compare models on your own examples before you switch.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.