82def render_request(provider: ProviderPlugin, plan:
"ProviderRequestPlan") ->
"RenderedRequest":
83 """Render a provider-neutral :class:`ProviderRequestPlan` to the wire shape.
85 Default = OpenAI-Chat-compatible (plan 135 §3.4): recompose the chat
86 ``messages`` list (``messages[0]`` reproduced byte-for-byte from
87 ``policy_prompt + tool_reference``), narrow the tool catalog to
88 ``allowed_tools``, and leave ``system`` as ``None`` (the system prompt
89 lives in ``messages[0]`` for chat providers; ``effort``/``extra_body``
90 keep their caller-side ownership). DeepSeek/ollama/example inherit this;
91 the future Anthropic bundle (plan 137) supplies its own ``render_request``
92 method, which this function delegates to when present.
94 Relocated out of the ``ProviderPlugin`` ABC by plan 154 because the pure
95 contract leaf must not import ``oc_chat.core.request_plan``.
97 override = getattr(type(provider),
"render_request",
None)
98 if callable(override):
99 return override(provider, plan)
103 compose_chat_messages,
104 filtered_tool_catalog,
108 messages=compose_chat_messages(plan),
109 tools=filtered_tool_catalog(plan),
111 max_tokens=plan.output_max_tokens,
116def endpoints(provider: ProviderPlugin) -> dict[str, ProviderEndpoint]:
117 """Return the named base-URL targets *provider* can serve (Phase O2).
119 Default implementation synthesises exactly one entry named ``"default"``
120 whose ``base_url`` is read from ``os.environ[provider.base_url_env_var]``
121 when set, else :attr:`ProviderPlugin.default_base_url`. LAN policy is
122 classified by ``oc_chat.core.endpoint_registry.classify_lan_policy``.
124 A provider can expose multiple curated endpoints by defining its own
125 ``endpoints`` method, which this function delegates to when present; the
126 registry layer (env var + ``~/.oc_chat/endpoints.toml``) merges on top.
128 Relocated out of the ``ProviderPlugin`` ABC by plan 154 because the pure
129 contract leaf must not import ``oc_chat.core.endpoint_registry``.
131 override = getattr(type(provider),
"endpoints",
None)
132 if callable(override):
133 return override(provider)
138 if provider.base_url_env_var:
139 base_url = os.environ.get(provider.base_url_env_var, provider.default_base_url)
141 base_url = provider.default_base_url
144 policy = classify_lan_policy(base_url)
145 return {
"default": ProviderEndpoint(name=
"default", base_url=base_url, lan_policy_status=policy)}