pub struct ProviderRule {Show 73 fields
pub model_match: String,
pub version_min: Option<Vec<u32>>,
pub native_tools: Option<bool>,
pub message_wire_format: Option<String>,
pub native_tool_wire_format: Option<String>,
pub defer_loading: Option<bool>,
pub tool_search: Option<Vec<String>>,
pub responses_api: Option<bool>,
pub hosted_tools: Option<Vec<String>>,
pub remote_mcp: Option<bool>,
pub conversation_state: Option<bool>,
pub compaction: Option<bool>,
pub background_mode: Option<bool>,
pub tool_approval_policy: Option<String>,
pub max_tools: Option<u32>,
pub prompt_caching: Option<bool>,
pub cache_breakpoint_style: Option<String>,
pub vision: Option<bool>,
pub audio: Option<bool>,
pub pdf: Option<bool>,
pub video: Option<bool>,
pub files_api_supported: Option<bool>,
pub file_upload_wire_format: Option<String>,
pub structured_output: Option<String>,
pub json_schema: Option<String>,
pub prefers_xml_scaffolding: Option<bool>,
pub reserved_tool_call_token: Option<bool>,
pub prefers_markdown_scaffolding: Option<bool>,
pub structured_output_mode: Option<String>,
pub supports_assistant_prefill: Option<bool>,
pub prefers_role_developer: Option<bool>,
pub prefers_xml_tools: Option<bool>,
pub thinking_block_style: Option<String>,
pub thinking_modes: Option<Vec<String>>,
pub interleaved_thinking_supported: Option<bool>,
pub anthropic_beta_features: Option<Vec<String>>,
pub thinking: Option<bool>,
pub vision_supported: Option<bool>,
pub image_url_input_supported: Option<bool>,
pub preserve_thinking: Option<bool>,
pub server_parser: Option<String>,
pub honors_chat_template_kwargs: Option<bool>,
pub chat_template_options_field: Option<String>,
pub requires_completion_tokens: Option<bool>,
pub requires_streaming: Option<bool>,
pub reasoning_effort_supported: Option<bool>,
pub reasoning_effort_levels: Option<Vec<String>>,
pub reasoning_none_supported: Option<bool>,
pub max_thinking_budget: Option<i64>,
pub reasoning_disable_supported: Option<bool>,
pub reasoning_required_for_tools: Option<bool>,
pub reasoning_text_promotable: Option<bool>,
pub reasoning_wire_format: Option<String>,
pub seed_supported: Option<bool>,
pub top_k_supported: Option<bool>,
pub temperature_supported: Option<bool>,
pub top_p_supported: Option<bool>,
pub frequency_penalty_supported: Option<bool>,
pub presence_penalty_supported: Option<bool>,
pub allowed_tool_choice_modes: Option<Vec<String>>,
pub requires_tool_result_adjacency: Option<bool>,
pub supports_parallel_tool_calls: Option<bool>,
pub tools_exclude_response_format: Option<bool>,
pub recommended_endpoint: Option<String>,
pub text_tool_wire_format_supported: Option<bool>,
pub preferred_tool_format: Option<String>,
pub tool_mode_parity: Option<String>,
pub tool_mode_parity_notes: Option<String>,
pub thinking_disable_directive: Option<String>,
pub auto_reasoning_overrides: Option<BTreeMap<String, String>>,
pub provider_route_denylist: Option<Vec<String>>,
pub openrouter_provider_order: Option<Vec<String>>,
pub serving_precision: Option<String>,
}Expand description
One row of the capability matrix.
Fields§
§model_match: StringGlob pattern (supports leading / trailing * and a single mid-*).
Matched case-insensitively against the model ID.
version_min: Option<Vec<u32>>Optional [major, minor] lower bound. When set, the model ID
must parse via the provider’s version extractor AND compare ≥
this tuple. Rules with an unparseable version_min for the
given model are skipped, not merged.
native_tools: Option<bool>§message_wire_format: Option<String>Message/request/response wire format used by shared helpers.
Known values are openai, anthropic, gemini, and ollama.
native_tool_wire_format: Option<String>Native tool definition wire shape. Known values are openai
and anthropic.
defer_loading: Option<bool>§tool_search: Option<Vec<String>>§responses_api: Option<bool>Whether Harn supports this route through the provider’s native Responses-style API instead of generic chat completions.
hosted_tools: Option<Vec<String>>Provider-hosted tools Harn can pass through without local execution.
remote_mcp: Option<bool>Whether provider-hosted remote MCP connectors can be mediated by the provider for this route.
conversation_state: Option<bool>Whether provider-managed previous-response conversation state is available.
compaction: Option<bool>Whether provider-side truncation/compaction controls are available.
background_mode: Option<bool>Whether provider-side background Responses jobs are available.
tool_approval_policy: Option<String>Approval policy modes available when provider-hosted tools execute.
max_tools: Option<u32>§prompt_caching: Option<bool>§cache_breakpoint_style: Option<String>Request-side cache breakpoint strategy for routes that require
cache_control to opt into provider prompt caching. Known values are
none, top_level, and last_block.
vision: Option<bool>Whether this provider/model route accepts image or other visual input blocks through Harn’s LLM message path.
audio: Option<bool>Whether this provider/model route accepts audio input blocks through Harn’s LLM message path.
pdf: Option<bool>Whether this provider/model route accepts PDF/document input blocks through Harn’s LLM message path.
video: Option<bool>Whether this provider/model route accepts video input blocks through Harn’s LLM message path.
files_api_supported: Option<bool>Whether uploaded file references can be reused in message content.
file_upload_wire_format: Option<String>File-upload transport used by std/files.upload. Known values
are anthropic and gemini.
structured_output: Option<String>Structured-output transport strategy. Known values are:
native, tool_use, format_kw, and none.
json_schema: Option<String>Legacy name retained for project overrides written before
structured_output became the canonical capability.
prefers_xml_scaffolding: Option<bool>Whether prompt sections should prefer XML-style tags such as
<task> / <examples> over Markdown headings.
reserved_tool_call_token: Option<bool>Whether this model’s tokenizer reserves <tool_call> / </tool_call>
as single special tokens (the native Hermes tool-call markers). When
true, harn remaps those delimiters to a non-special bracket form on the
wire to avoid degenerate opener repetition; see [crate::llm::tool_delimiter].
prefers_markdown_scaffolding: Option<bool>Whether prompt sections should prefer Markdown headings such as
## Task / ## Examples.
structured_output_mode: Option<String>Preferred logical structured-output prompt shape. This is separate
from the transport-level structured_output strategy above.
Known values are native_json, delimited, and xml_tagged.
supports_assistant_prefill: Option<bool>Whether the route accepts an assistant-role prefill message.
prefers_role_developer: Option<bool>Whether durable instructions should use OpenAI’s developer role
instead of system.
prefers_xml_tools: Option<bool>Whether text-rendered tool specifications should use XML wrappers instead of JSON-schema prose.
thinking_block_style: Option<String>Preferred representation for model thinking/reasoning blocks in
transcript-like prompt context. Known values are none,
thinking_blocks, reasoning_summary, and inline.
thinking_modes: Option<Vec<String>>Supported thinking/reasoning modes for this rule. Values are
script-facing mode names: enabled, adaptive, and effort.
interleaved_thinking_supported: Option<bool>Whether Anthropic interleaved thinking is supported for this provider/model route.
anthropic_beta_features: Option<Vec<String>>Anthropic beta features that should be requested for this route.
thinking: Option<bool>Legacy override compatibility. New built-in rules should use
thinking_modes so the capability matrix preserves mode detail.
vision_supported: Option<bool>Whether the model accepts image inputs in chat content.
image_url_input_supported: Option<bool>Whether image content blocks may reference remote URLs.
preserve_thinking: Option<bool>Carry <think>...</think> blocks in assistant history across turns.
Qwen3.6 exposes this as chat_template_kwargs.preserve_thinking;
Alibaba recommends enabling it for long-horizon agent loops so the
model doesn’t re-derive context it already worked out in prior turns.
Anthropic’s adaptive-thinking signature contract is stricter but plays
the same role there.
server_parser: Option<String>Name of any server-side response parser that can transform model
bytes before Harn sees them. none means the provider returns the
model text/tool channel without an implicit parser.
honors_chat_template_kwargs: Option<bool>Whether provider-specific chat-template options are honored. Most
OpenAI-compatible servers call this chat_template_kwargs; Baseten’s
Model APIs spell the same concept chat_template_args.
chat_template_options_field: Option<String>Request body field for provider-specific chat-template options when it
differs from the default chat_template_kwargs.
requires_completion_tokens: Option<bool>Whether this route requires OpenAI’s max_completion_tokens
request field instead of legacy max_tokens.
requires_streaming: Option<bool>Whether this route rejects non-streaming chat-completion requests.
Harn forces streaming for such routes so callers can keep provider-
neutral stream preferences.
reasoning_effort_supported: Option<bool>Whether this route accepts Harn’s provider-neutral reasoning effort
control. Providers project this to their native field (for example
OpenAI reasoning_effort or Anthropic output_config.effort).
reasoning_effort_levels: Option<Vec<String>>Accepted effort values for routes that expose a narrower subset than Harn’s provider-neutral enum. Empty means “unknown/all”.
reasoning_none_supported: Option<bool>Whether this route accepts effort “none” as a true reasoning-off
setting. Older GPT-5 variants support effort but only floor at
minimal.
max_thinking_budget: Option<i64>Maximum thinking-budget tokens this model accepts for its high/xhigh/max
reasoning levels, when the provider takes an explicit token budget rather
than an effort enum. The canonical case is the native Gemini API
generationConfig.thinkingConfig.thinkingBudget field, whose ceiling
differs by model (Gemini 2.5 Flash caps at 24576, Pro at 32768).
Declared alongside the model’s other wire capabilities instead of a
hard-coded model.contains("flash") branch in the provider.
reasoning_disable_supported: Option<bool>Whether this route accepts an explicit disabled/off reasoning switch. Some routes require reasoning and reject the provider’s disabled shape.
reasoning_required_for_tools: Option<bool>Whether this model performs tool calls inside its reasoning channel,
so disabling reasoning silently breaks tool calling. The canonical case
is the OpenAI gpt-oss (Harmony) family: with reasoning disabled it emits
0 tool_calls and a tiny billed-noncommittal completion; with reasoning
enabled (even low) it emits clean native tool calls. This is the
opposite of the Qwen3 quirk (Qwen narrates tool intent in the
reasoning trace and emits zero tool_calls, so Qwen needs reasoning
OFF for tools). When set, reasoning_policy refuses to downgrade the
auto reasoning level to off for tool-bearing tasks (agent/code/verify)
— flooring instead to the lowest supported effort — so no future
auto-policy default or session pin can re-introduce the
billed-noncommittal failure at the data layer.
reasoning_text_promotable: Option<bool>Whether reasoning-only clean stops may be promoted into visible text.
Disable this for providers whose reasoning field is always private
trace, even when content is empty.
reasoning_wire_format: Option<String>Provider-specific reasoning request shape for OpenAI-compatible
transports. Known values are openrouter, enabled, and minimax.
seed_supported: Option<bool>§top_k_supported: Option<bool>§temperature_supported: Option<bool>§top_p_supported: Option<bool>§frequency_penalty_supported: Option<bool>§presence_penalty_supported: Option<bool>§allowed_tool_choice_modes: Option<Vec<String>>Accepted provider-native tool_choice modes. Empty means unrestricted
or unknown. Use this for routes whose native tools work, but whose API
rejects forced/specified tool choices.
requires_tool_result_adjacency: Option<bool>Whether an assistant tool_calls message must be followed immediately
by role=tool messages for every emitted tool_call_id.
supports_parallel_tool_calls: Option<bool>Whether a single assistant message may contain multiple tool calls.
Some OpenAI-compatible providers reject replayed history with more than
one tool_calls[] entry even when the calls were parsed from Harn’s text
tool protocol, so the request builder must serialize history as
one-call assistant turns for those routes.
tools_exclude_response_format: Option<bool>Whether the route rejects response_format when native tools are
present. Strict OpenAI-compatible servers such as Cerebras accept each
feature alone but reject the pair together.
recommended_endpoint: Option<String>Preferred endpoint family for this provider/model route. Values
are descriptive labels consumed by providers, e.g.
/api/generate-raw for Ollama raw prompt bypass.
text_tool_wire_format_supported: Option<bool>Whether Harn’s text-tool protocol (<tool_call>name({...})) can
survive the provider route and return in the visible response body.
preferred_tool_format: Option<String>Preferred tool-calling mode for this provider/model route when
callers do not explicitly choose tool_format. This lets the
capability matrix route around known provider-native regressions
without making presets branch on model names.
tool_mode_parity: Option<String>Empirical native/text interchangeability status for this route.
Known values are descriptive, not gates: interchangeable,
native_unreliable, text_unreliable, native_only,
text_only, and unknown.
tool_mode_parity_notes: Option<String>Short human-readable note explaining tool_mode_parity.
thinking_disable_directive: Option<String>In-prompt directive that disables this model’s “thinking” mode when
the API doesn’t expose a first-class field (or exposes it
inconsistently across templates / quantizations). For Qwen3 family
chat templates this is /no_think. When thinking: false is
requested and this is set, Harn auto-prepends the directive to the
system message so script authors don’t need to know it exists.
auto_reasoning_overrides: Option<BTreeMap<String, String>>Per-task auto-policy reasoning-level overrides for this route.
Keys are task labels (agent, verify, chat, summarize,
code); values are reasoning levels (off, minimal, low,
medium, high, xhigh, max). Consulted by reasoning_policy only
when policy resolves to auto — explicit policies always win.
Use this to declare known per-model regressions that should
flip the auto-policy default, instead of hard-coding the model/
provider pattern in resolver code. The canonical example is the
Qwen3 tool-call regression — { agent = "off" } disables
reasoning whenever a script registers tools with that route,
matching Qwen’s own published guidance.
provider_route_denylist: Option<Vec<String>>OpenRouter upstream provider names that must be excluded from routing
for this (provider, model) row. Materialized into the request body’s
provider.ignore array (see
[crate::llm::providers::openai_compat::apply_openrouter_route_denylist]).
This is a data-driven route-around for upstreams that serve a route
incorrectly while still advertising the model — the canonical case is
OpenRouter’s Ambient upstream billing reasoning tokens for
qwen/qwen3.6-35b-a3b and then finishing with empty tool_calls,
while Parasail / AtlasCloud / AkashML serve the identical request
natively. Only consulted for the openrouter provider.
openrouter_provider_order: Option<Vec<String>>OpenRouter upstream provider names this (provider, model) row is
PINNED to, in preference order. Materialized into the request body’s
provider.order array with allow_fallbacks = false (see
[crate::llm::providers::openai_compat::apply_openrouter_provider_order]),
so OpenRouter only ever routes the model to these known-clean upstreams
and never silently falls back to a sketchier one. This is the
allowlist counterpart to Self::provider_route_denylist: prefer it
when the bad upstreams are intermittent / hard to enumerate but the
clean ones are few and stable. The canonical case is OpenRouter’s
openai/gpt-oss-* route, which fans out across ~17 upstreams in a
sub-provider lottery; some mis-serialize the Harmony tool call even with
reasoning ON (billed-noncommittal: 0 tool_calls), while Cerebras and
Groq serve it cleanly. Only consulted for the openrouter provider. An
empty / unset list means “no pin” (free OpenRouter routing). When both a
pin and a denylist are present the pin wins (a closed allowlist already
excludes everything not on it). Validated by the footgun gate in
crate::llm::capability_audit.
serving_precision: Option<String>Serving-quality / precision trust verdict for this (provider, model)
route. A provider can be live and fast yet still serve a model at
DEGRADED quality (e.g. an undocumented quantization) or reject otherwise
valid requests, silently contaminating any eval/meter that trusts its
numbers. This is the data-driven sibling of Self::provider_route_denylist
/ Self::openrouter_provider_order: instead of routing around a bad
upstream, it labels the route’s measured precision so tooling (the
meter precision canary) can refuse to trust a degraded route and flag a
throttled one. Known values are trusted (full-precision verified
against a reference), degraded (proven to serve at reduced quality),
throttled (full-precision but rate-limited to unusable timing), and
unverified (no verdict — treated the same as unset). Unset means
unverified.
Trait Implementations§
Source§impl Clone for ProviderRule
impl Clone for ProviderRule
Source§fn clone(&self) -> ProviderRule
fn clone(&self) -> ProviderRule
1.0.0 (const: unstable) · Source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
source. Read moreSource§impl Debug for ProviderRule
impl Debug for ProviderRule
Source§impl<'de> Deserialize<'de> for ProviderRule
impl<'de> Deserialize<'de> for ProviderRule
Source§fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>where
__D: Deserializer<'de>,
fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>where
__D: Deserializer<'de>,
Auto Trait Implementations§
impl Freeze for ProviderRule
impl RefUnwindSafe for ProviderRule
impl Send for ProviderRule
impl Sync for ProviderRule
impl Unpin for ProviderRule
impl UnsafeUnpin for ProviderRule
impl UnwindSafe for ProviderRule
Blanket Implementations§
Source§impl<'a, T, E> AsTaggedExplicit<'a, E> for Twhere
T: 'a,
impl<'a, T, E> AsTaggedExplicit<'a, E> for Twhere
T: 'a,
Source§impl<'a, T, E> AsTaggedImplicit<'a, E> for Twhere
T: 'a,
impl<'a, T, E> AsTaggedImplicit<'a, E> for Twhere
T: 'a,
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> DeserializeOwned for Twhere
T: for<'de> Deserialize<'de>,
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
Source§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§impl<T> Paint for Twhere
T: ?Sized,
impl<T> Paint for Twhere
T: ?Sized,
Source§fn fg(&self, value: Color) -> Painted<&T>
fn fg(&self, value: Color) -> Painted<&T>
Returns a styled value derived from self with the foreground set to
value.
This method should be used rarely. Instead, prefer to use color-specific
builder methods like red() and
green(), which have the same functionality but are
pithier.
§Example
Set foreground color to white using fg():
use yansi::{Paint, Color};
painted.fg(Color::White);Set foreground color to white using white().
use yansi::Paint;
painted.white();Source§fn bright_black(&self) -> Painted<&T>
fn bright_black(&self) -> Painted<&T>
Source§fn bright_red(&self) -> Painted<&T>
fn bright_red(&self) -> Painted<&T>
Source§fn bright_green(&self) -> Painted<&T>
fn bright_green(&self) -> Painted<&T>
Source§fn bright_yellow(&self) -> Painted<&T>
fn bright_yellow(&self) -> Painted<&T>
Source§fn bright_blue(&self) -> Painted<&T>
fn bright_blue(&self) -> Painted<&T>
Source§fn bright_magenta(&self) -> Painted<&T>
fn bright_magenta(&self) -> Painted<&T>
Source§fn bright_cyan(&self) -> Painted<&T>
fn bright_cyan(&self) -> Painted<&T>
Source§fn bright_white(&self) -> Painted<&T>
fn bright_white(&self) -> Painted<&T>
Source§fn bg(&self, value: Color) -> Painted<&T>
fn bg(&self, value: Color) -> Painted<&T>
Returns a styled value derived from self with the background set to
value.
This method should be used rarely. Instead, prefer to use color-specific
builder methods like on_red() and
on_green(), which have the same functionality but
are pithier.
§Example
Set background color to red using fg():
use yansi::{Paint, Color};
painted.bg(Color::Red);Set background color to red using on_red().
use yansi::Paint;
painted.on_red();Source§fn on_primary(&self) -> Painted<&T>
fn on_primary(&self) -> Painted<&T>
Source§fn on_magenta(&self) -> Painted<&T>
fn on_magenta(&self) -> Painted<&T>
Source§fn on_bright_black(&self) -> Painted<&T>
fn on_bright_black(&self) -> Painted<&T>
Source§fn on_bright_red(&self) -> Painted<&T>
fn on_bright_red(&self) -> Painted<&T>
Source§fn on_bright_green(&self) -> Painted<&T>
fn on_bright_green(&self) -> Painted<&T>
Source§fn on_bright_yellow(&self) -> Painted<&T>
fn on_bright_yellow(&self) -> Painted<&T>
Source§fn on_bright_blue(&self) -> Painted<&T>
fn on_bright_blue(&self) -> Painted<&T>
Source§fn on_bright_magenta(&self) -> Painted<&T>
fn on_bright_magenta(&self) -> Painted<&T>
Source§fn on_bright_cyan(&self) -> Painted<&T>
fn on_bright_cyan(&self) -> Painted<&T>
Source§fn on_bright_white(&self) -> Painted<&T>
fn on_bright_white(&self) -> Painted<&T>
Source§fn attr(&self, value: Attribute) -> Painted<&T>
fn attr(&self, value: Attribute) -> Painted<&T>
Enables the styling Attribute value.
This method should be used rarely. Instead, prefer to use
attribute-specific builder methods like bold() and
underline(), which have the same functionality
but are pithier.
§Example
Make text bold using attr():
use yansi::{Paint, Attribute};
painted.attr(Attribute::Bold);Make text bold using using bold().
use yansi::Paint;
painted.bold();Source§fn rapid_blink(&self) -> Painted<&T>
fn rapid_blink(&self) -> Painted<&T>
Source§fn quirk(&self, value: Quirk) -> Painted<&T>
fn quirk(&self, value: Quirk) -> Painted<&T>
Enables the yansi Quirk value.
This method should be used rarely. Instead, prefer to use quirk-specific
builder methods like mask() and
wrap(), which have the same functionality but are
pithier.
§Example
Enable wrapping using .quirk():
use yansi::{Paint, Quirk};
painted.quirk(Quirk::Wrap);Enable wrapping using wrap().
use yansi::Paint;
painted.wrap();Source§fn clear(&self) -> Painted<&T>
👎Deprecated since 1.0.1: renamed to resetting() due to conflicts with Vec::clear().
The clear() method will be removed in a future release.
fn clear(&self) -> Painted<&T>
renamed to resetting() due to conflicts with Vec::clear().
The clear() method will be removed in a future release.
Source§fn whenever(&self, value: Condition) -> Painted<&T>
fn whenever(&self, value: Condition) -> Painted<&T>
Conditionally enable styling based on whether the Condition value
applies. Replaces any previous condition.
See the crate level docs for more details.
§Example
Enable styling painted only when both stdout and stderr are TTYs:
use yansi::{Paint, Condition};
painted.red().on_yellow().whenever(Condition::STDOUTERR_ARE_TTY);