---
title: "Advisory memory verdict for one model"
method: POST
path: "/v1/models/fit"
tags: ["Models"]
---

# Advisory memory verdict for one model

`POST /v1/models/fit`

## Request

- Base URL: `http://localhost:9998`
- URL: `http://localhost:9998/v1/models/fit`
- Auth: HTTP bearer

Forecasts the memory one model would occupy on this machine and compares
it with the host budget read at request time. This is the same answer
`model_list fit:true` reads.

Advisory only: nothing is reserved. Model management and GPU admission
recheck at real load time, so a `good` verdict describes the moment the
budget was read and is not a promise about now. Every workload field is
optional; an omitted field takes the product default, and the workload
actually evaluated is echoed in `estimate.workload`.

## Request body

- WireFitVerdictRequest: One model's advisory memory question. Every workload field is optional; an omitted field takes the product default rather than a guess.
  - `modelId` string, required
  - `allocatedTokens` integer, nullable: KV capacity in tokens the backend allocates. Not the tokens a request prepares.
  - `streams` integer, nullable: Concurrent sequences sharing the model. KV scales with this.
  - `keyElementBytes` integer, nullable: Bytes per stored key element (2 for F16, 1 for an 8-bit KV cache).
  - `valueElementBytes` integer, nullable: Bytes per stored value element.
  - `mode` string, nullable: Where the allocation lives: `fullGpu` or `cpuOffload`. Tolerate unknown values.

## Response `200`

Advisory verdict for the model

- WireFitVerdictResult: One model's advisory answer. Nothing here reserves anything; model management and GPU admission recheck at real load time.
  - `modelId` string, required
  - `identity` WireFitEvidenceIdentity, required: What the answer is about, precisely enough that a later answer about a different artifact is recognisable.
    - `modelId` string, required
    - `revision` string, required: Immutable commit the bytes were fetched at; empty when the source recorded none.
    - `quant` string, required: Empty when the artifact declares none.
    - `artifactBytes` integer, nullable, required: Measured bytes of the evaluated file set; null when not on disk.
  - `estimate` WireFitMemoryEstimate, required: A complete memory forecast. `lowerBoundBytes` is always a real floor; `upperBoundBytes` is finite only when no part is unknown.
    - `parts` WireFitMemoryPart[], required
      - `component` string, required: `weights`, `kvCache`, `recurrentState`, `workspace` or `companions`. Tolerate unknown values.
      - `bytes` integer, nullable, required: Bytes; null if and only if `basis` is `unknown`.
      - `basis` string, required: `measuredArtifact`, `derivedLayout`, `parameterProxy`, `notApplicable` or `unknown`. Tolerate unknown values.
      - `sharedKey` string, required: Identity of an allocation shared with other models in the same evaluation; empty when not shared.
      - `note` string, required: Why this basis, in the producer's words.
    - `lowerBoundBytes` integer, required: Sum of every part that carries a number. A floor, never the answer.
    - `upperBoundBytes` integer, nullable, required: Null means the total is unknown.
    - `weakestBasis` string, required: The weakest basis among the parts; the total is no stronger than this. Tolerate unknown values.
    - `missing` string[], required: Components that would have to be observed for `upperBoundBytes` to be finite.
    - `workload` WireFitWorkload, required: The workload actually evaluated, after any documented-default capacity cap.
      - `allocatedTokens` integer, required
      - `contextSource` string, required: `documentedDefault` (the product default, which may be capped to the model limit) or `requested` (a caller named it; over-limit is refused, never truncated). Tolerate unknown values.
      - `streams` integer, required
      - `keyElementBytes` integer, required
      - `valueElementBytes` integer, required
      - `mode` string, required: `fullGpu` or `cpuOffload`. Tolerate unknown values.
      - `preparedTokens` integer, nullable, required: Tokens the request actually prepares; null until an exact prepared count is available. Never derived from capacity.
    - `refusal` string, required: `none`, or why no estimate was produced: `contextExceedsModelLimit`, `nonPositiveContext`, `nonPositiveStreams`, `nonFiniteInput`. Tolerate unknown values.
  - `verdict` string, required: `good` (the ceiling fits with the presentation margin), `tight` (fits below it), `oversize` (the floor already exceeds the budget) or `unknown`. Tolerate unknown values.
  - `budget` WireFitBudget, required: The budget one verdict was taken against, as it was read.
    - `basis` string, required: `hostAvailable` (what a load could claim right now), `hostTotal` (the physical ceiling) or `unknown`. Tolerate unknown values.
    - `bytes` integer, nullable, required: Bytes; null if and only if `basis` is `unknown`.
    - `committedBytes` integer, nullable, required: Bytes already committed to loaded models when the budget was read.
  - `gpuAdmits` boolean, nullable, required: Whether GPU admission would admit the estimate's floor without evicting anything; null when no GPU answer was obtainable. Not a reservation.
  - `limits` string[], required: Evidence the estimator could not use for this answer: `artifactNotOnDisk`, `layoutUnpublished`, `layoutNotUniform`, `historyIdentityInsufficient`, `workspaceUnmeasured`, `preparedCountUnavailable`, `hostTelemetryUnavailable`, `gpuTelemetryUnavailable`. Tolerate unknown values.

## Other responses

- `400`: Invalid request
- `404`: No model on this machine or in the bundled catalog has that id

---

[API](https://skmtc.dev/modelpiper/apis/toolpiper-api.md) · [All operations](https://skmtc.dev/modelpiper/apis/toolpiper-api/llms.txt) · [OpenAPI document](https://skmtc.dev/modelpiper/apis/toolpiper-api/revisions/6722bf56385c?raw)
