A price entered by hand on an endpoint whose provider gives none (Z.ai,
say): provider_settings["pricing"] — %{"model" => id, "input" => "0.60", "output" => "2.2"}, US dollars per 1M input and output tokens as decimal
strings (a JSON number would read back as a float), both required, for the
model it names. The
endpoint's changeset stamps the model when none is given and drops the
price when the endpoint's model changes (like a capability declaration).
A call whose provider reports no usage.cost and whose model no catalogue
prices gets its cost from it (cost/3), and its
usage row says cost_source: "manual" (PhoenixKitAI.CallCost keeps the
order of the sources). Money limits and the daily budget then count the
call like any other. That is chat, embeddings and the vision verbs
(describe_image/3, extract_text/3, compare_images/4), for a call
sent to the price's model. Making or editing images (generate_image/3,
edit_image/4, process_image/4) is priced per image or per call, not
per token, so a manual price does not apply there: those calls keep only
the provider's own cost.
A price whose halves are integers is in the shape the released versions
stored (millionths of a dollar); legacy?/1 says so, the module's migration
chain converts it, and a call on such an endpoint is refused until it has.
Summary
Functions
What a call costs at a price per 1M tokens, in dollars, not rounded:
(input_tokens × input + output_tokens × output) / 1_000_000. nil when a
price the tokens need is missing (no price at all, or an output price for a
call with output).
Whether the endpoint's stored price is in the released versions' shape: integer millionths of a dollar per 1M tokens.
The highest price per 1M tokens, in dollars ($10 000).
Checks a stored price: "input" and "output" both, dollar strings from 0
to max/0, and an optional "model" (the model it prices). :ok or
:error.
Types
Functions
@spec cost(t() | nil, non_neg_integer(), non_neg_integer()) :: Decimal.t() | nil
What a call costs at a price per 1M tokens, in dollars, not rounded:
(input_tokens × input + output_tokens × output) / 1_000_000. nil when a
price the tokens need is missing (no price at all, or an output price for a
call with output).
@spec get(PhoenixKitAI.Endpoint.t() | map() | nil) :: t() | nil
The endpoint's manual price for its own model, %{"input" => dollars, "output" => dollars} per 1M tokens as Decimals, or nil — when it has none,
the stored price names another model, lacks a half, or is in the legacy shape
(legacy?/1).
@spec legacy?(PhoenixKitAI.Endpoint.t() | map() | nil) :: boolean()
Whether the endpoint's stored price is in the released versions' shape: integer millionths of a dollar per 1M tokens.
@spec max() :: Decimal.t()
The highest price per 1M tokens, in dollars ($10 000).
@spec validate(term()) :: :ok | :error
Checks a stored price: "input" and "output" both, dollar strings from 0
to max/0, and an optional "model" (the model it prices). :ok or
:error.