"""GitHub Models provider — OpenAI-compatible, via ``GITHUB_MODEL_API_TOKEN``. GitHub Models exposes an OpenAI-compatible endpoint backed by a GitHub Copilot subscription. It needs a fine-grained PAT with the ``models:read`` permission. """ from environs import Env from langchain_core.language_models import BaseChatModel from langchain_openai import ChatOpenAI from pydantic import SecretStr from skill_eval_runner.providers import Provider, register GITHUB_MODELS_BASE_URL = "https://models.github.ai/inference" _env = Env() _env.read_env() def make_model(model_name: str) -> BaseChatModel: """Build a ``ChatOpenAI`` model pointed at GitHub Models' inference endpoint.""" token = _env.str("GITHUB_MODEL_API_TOKEN", None) if not token: raise SystemExit( "GITHUB_MODEL_API_TOKEN is not set.\n\n" "Create a fine-grained PAT with Models -> Read-only permission:\n" " github.com -> Settings -> Developer settings -> Fine-grained tokens\n\n" "Then add it to a .env file or export GITHUB_MODEL_API_TOKEN=github_pat_..." ) # ChatOpenAI's pydantic field aliases aren't visible to mypy without the pydantic # plugin; the kwargs are valid at runtime. model: BaseChatModel = ChatOpenAI( # type: ignore[call-arg] model=model_name, base_url=GITHUB_MODELS_BASE_URL, api_key=SecretStr(token), max_tokens=8192, ) return model register( Provider( name="github-models", default_model="openai/gpt-4.1", small_model="openai/gpt-4.1-mini", large_model="openai/gpt-4.1", make_model=make_model, ) )