From f3ff95e0e9d8ed0eede586b6f7ccc1d27b8568b1 Mon Sep 17 00:00:00 2001 From: Manjunath Janardhan Date: Fri, 4 Sep 2026 11:12:53 +0530 Subject: [PATCH 1/2] Python: give the Anthropic package its own dependency-probe Pyright config The weekly dependency-bounds gate has failed at packages/anthropic on every run since 2026-08-03. The upper-bound step that follows it is gated on that step's outcome, so it has been skipped ever since, leaving every package's dependency bounds unmaintained while the workflow still reports success. agent_framework_anthropic/_vertex_client.py type-checks against google.auth.credentials, but the package declares plain anthropic without the vertex extra and nothing in the repo declares google-auth. A full workspace sync resolves it transitively, so repo-wide Pyright passes and the gap is invisible outside the isolated probe. Add the dependency-pyright escape hatch that packages/core already uses, so the probe can type-check the implementation without requiring the undeclared namespace package. Repo-wide Pyright is unchanged and still covers _vertex_client.py in full. Co-Authored-By: Claude Opus 5 --- python/packages/anthropic/pyproject.toml | 4 +++ .../anthropic/pyrightconfig.dependency.json | 9 +++++++ .../tests/test_dependency_bounds_runtime.py | 26 +++++++++++++++++++ 3 files changed, 39 insertions(+) create mode 100644 python/packages/anthropic/pyrightconfig.dependency.json diff --git a/python/packages/anthropic/pyproject.toml b/python/packages/anthropic/pyproject.toml index 91ff2919101..db2884b00ae 100644 --- a/python/packages/anthropic/pyproject.toml +++ b/python/packages/anthropic/pyproject.toml @@ -85,6 +85,10 @@ exclude_dirs = ["tests"] executor.type = "uv" include = "../../shared_tasks.toml" +[tool.poe.tasks.dependency-pyright] +help = "Run Pyright over Anthropic implementation files for isolated dependency validation." +cmd = "pyright --project pyrightconfig.dependency.json" + [tool.poe.tasks.mypy] help = "Run MyPy for this package." cmd = "mypy --config-file $POE_ROOT/pyproject.toml agent_framework_anthropic" diff --git a/python/packages/anthropic/pyrightconfig.dependency.json b/python/packages/anthropic/pyrightconfig.dependency.json new file mode 100644 index 00000000000..6a3c479a49c --- /dev/null +++ b/python/packages/anthropic/pyrightconfig.dependency.json @@ -0,0 +1,9 @@ +{ + "extends": "../../pyproject.toml", + "include": [ + "agent_framework_anthropic" + ], + "exclude": [ + "agent_framework_anthropic/_vertex_client.py" + ] +} diff --git a/python/scripts/dependencies/tests/test_dependency_bounds_runtime.py b/python/scripts/dependencies/tests/test_dependency_bounds_runtime.py index 12e184057c5..5dc20f246b7 100644 --- a/python/scripts/dependencies/tests/test_dependency_bounds_runtime.py +++ b/python/scripts/dependencies/tests/test_dependency_bounds_runtime.py @@ -1,5 +1,6 @@ # Copyright (c) Microsoft. All rights reserved. +import json from collections.abc import Callable from pathlib import Path @@ -196,3 +197,28 @@ def test_dependency_pyright_reuses_root_test_requirements(tmp_path: Path) -> Non "mcp[ws]", ] assert command[-3:-1] == ["python", "-c"] + + +def test_anthropic_probe_uses_its_own_dependency_pyright_task() -> None: + """Anthropic's Vertex client type-checks against an undeclared namespace package. + + ``_vertex_client.py`` imports ``google.auth.credentials`` under ``TYPE_CHECKING`` while the + package only declares ``anthropic`` without the ``vertex`` extra, so isolated dependency + probes have no ``google-auth`` to resolve. Without the package-defined escape hatch the + ``lowest-direct`` probe fails on ``reportMissingImports`` and blocks the whole bounds gate. + """ + workspace_root = Path(__file__).resolve().parents[3] + + plans = _build_test_plans(workspace_root, "anthropic") + + assert [plan.typing_task for plan in plans] == ["dependency-pyright"] + + +def test_anthropic_dependency_pyright_config_excludes_the_vertex_client() -> None: + workspace_root = Path(__file__).resolve().parents[3] + config_path = workspace_root / "packages/anthropic/pyrightconfig.dependency.json" + + config = json.loads(config_path.read_text()) + + assert config["include"] == ["agent_framework_anthropic"] + assert config["exclude"] == ["agent_framework_anthropic/_vertex_client.py"] From 094f9cadbdd440ae6ace8c5ea46756687615bb16 Mon Sep 17 00:00:00 2001 From: Manjunath Janardhan Date: Fri, 4 Sep 2026 12:10:47 +0530 Subject: [PATCH 2/2] Python: give the OpenAI package its own dependency-probe Pyright config packages/openai is the second package the dependency-bounds gate stops at, for the same reason as packages/anthropic: it type-checks against namespaces it deliberately does not declare. _chat_client.py, _chat_completion_client.py, _embedding_client.py and _shared.py reference azure.core.credentials under TYPE_CHECKING and azure.identity from a lazy import, because Entra ID support is optional -- the docstrings say so ("Credential objects require the optional azure-identity package"). A full workspace sync resolves both transitively, so repo-wide Pyright passes and only the isolated probe sees them missing. Unlike anthropic, no exclusion is needed. The dependency-pyright task reuses the root workspace test dependency group, whose azure-monitor-opentelemetry pulls azure-monitor-opentelemetry-exporter and in turn azure-identity, so the probe resolves the whole package as-is. Excluding files would not have worked here in any case: the azure references span four of seven modules, 97% of the package by line count. Generalize the regression test over both packages rather than duplicating it, and keep the anthropic-specific exclusion assertion separate. Co-Authored-By: Claude Opus 5 --- python/packages/openai/pyproject.toml | 4 ++++ .../openai/pyrightconfig.dependency.json | 6 +++++ .../tests/test_dependency_bounds_runtime.py | 22 ++++++++++++------- 3 files changed, 24 insertions(+), 8 deletions(-) create mode 100644 python/packages/openai/pyrightconfig.dependency.json diff --git a/python/packages/openai/pyproject.toml b/python/packages/openai/pyproject.toml index f1df50c9269..a8d7a9a1c96 100644 --- a/python/packages/openai/pyproject.toml +++ b/python/packages/openai/pyproject.toml @@ -84,6 +84,10 @@ exclude_dirs = ["tests"] executor.type = "uv" include = "../../shared_tasks.toml" +[tool.poe.tasks.dependency-pyright] +help = "Run Pyright over OpenAI implementation files for isolated dependency validation." +cmd = "pyright --project pyrightconfig.dependency.json" + [tool.poe.tasks.mypy] help = "Run MyPy for this package." cmd = "mypy --config-file $POE_ROOT/pyproject.toml agent_framework_openai" diff --git a/python/packages/openai/pyrightconfig.dependency.json b/python/packages/openai/pyrightconfig.dependency.json new file mode 100644 index 00000000000..6298bac03b6 --- /dev/null +++ b/python/packages/openai/pyrightconfig.dependency.json @@ -0,0 +1,6 @@ +{ + "extends": "../../pyproject.toml", + "include": [ + "agent_framework_openai" + ] +} diff --git a/python/scripts/dependencies/tests/test_dependency_bounds_runtime.py b/python/scripts/dependencies/tests/test_dependency_bounds_runtime.py index 5dc20f246b7..3776295e82e 100644 --- a/python/scripts/dependencies/tests/test_dependency_bounds_runtime.py +++ b/python/scripts/dependencies/tests/test_dependency_bounds_runtime.py @@ -199,20 +199,27 @@ def test_dependency_pyright_reuses_root_test_requirements(tmp_path: Path) -> Non assert command[-3:-1] == ["python", "-c"] -def test_anthropic_probe_uses_its_own_dependency_pyright_task() -> None: - """Anthropic's Vertex client type-checks against an undeclared namespace package. +@pytest.mark.parametrize( + ("package", "module"), + [("anthropic", "agent_framework_anthropic"), ("openai", "agent_framework_openai")], +) +def test_optional_namespace_packages_define_their_own_dependency_pyright_task(package: str, module: str) -> None: + """Packages that type-check against deliberately optional namespaces need the probe escape hatch. - ``_vertex_client.py`` imports ``google.auth.credentials`` under ``TYPE_CHECKING`` while the - package only declares ``anthropic`` without the ``vertex`` extra, so isolated dependency - probes have no ``google-auth`` to resolve. Without the package-defined escape hatch the - ``lowest-direct`` probe fails on ``reportMissingImports`` and blocks the whole bounds gate. + ``agent_framework_anthropic`` references ``google.auth`` and ``agent_framework_openai`` references + ``azure.core``/``azure.identity``, in both cases without declaring them, because those surfaces are + optional. A full workspace sync resolves them transitively, so repo-wide Pyright passes; an isolated + dependency probe does not, and the resulting ``reportMissingImports`` aborts the whole bounds gate. """ workspace_root = Path(__file__).resolve().parents[3] - plans = _build_test_plans(workspace_root, "anthropic") + plans = _build_test_plans(workspace_root, package) assert [plan.typing_task for plan in plans] == ["dependency-pyright"] + config = json.loads((workspace_root / f"packages/{package}/pyrightconfig.dependency.json").read_text()) + assert config["include"] == [module] + def test_anthropic_dependency_pyright_config_excludes_the_vertex_client() -> None: workspace_root = Path(__file__).resolve().parents[3] @@ -220,5 +227,4 @@ def test_anthropic_dependency_pyright_config_excludes_the_vertex_client() -> Non config = json.loads(config_path.read_text()) - assert config["include"] == ["agent_framework_anthropic"] assert config["exclude"] == ["agent_framework_anthropic/_vertex_client.py"]