Skip to content

fix(http-client-python): generate valid Python type annotations in types.py - #11627

Closed
Libba Lawrence (l0lawrence) wants to merge 1 commit into
microsoft:mainfrom
l0lawrence:l0lawrence-fix-python-emitter-invalid-types
Closed

fix(http-client-python): generate valid Python type annotations in types.py#11627
Libba Lawrence (l0lawrence) wants to merge 1 commit into
microsoft:mainfrom
l0lawrence:l0lawrence-fix-python-emitter-invalid-types

Conversation

@l0lawrence

Copy link
Copy Markdown
Member

The Python client emitter generated types.py files with invalid type annotations for azure-search-documents, producing 4 MyPy errors across three generated files. This fixes the three distinct codegen bugs behind them.

What was wrong and how it's fixed

1. Internal enum annotation/import mismatch. An internal enum used as a TypedDict field was annotated as _enums.Name while _enums was never imported (and the enum is not re-exported from the public models package), yielding Name '_enums' is not defined and Module has no attribute errors. The enum is now imported as a bare symbol from its private _enums submodule, and the TYPES_FILE annotation drops the undefined _enums. prefix. Enums stay private (no change to the public __all__).

2. Duplicate enum import. The same symbol could be imported once at runtime and again under if TYPE_CHECKING: (from different modules), triggering mypy no-redef. Added a dedup pass that drops a TYPE_CHECKING submodule import when its bound name is already imported at runtime; the runtime import is sufficient for the annotations.

3. TypedDict requiredness override via inheritance. A child TypedDict that redeclared an inherited field with different requiredness produced Overwriting TypedDict field ... while extending, which PEP 589 forbids. Such models are now emitted as a flat, non-inheriting TypedDict that lists every field (inherited plus own) directly, so requiredness is expressed without subclassing.

Notes for reviewers

  • The internal-enum import intentionally imports the bare symbol from _enums rather than the _enums module, which also avoids name collisions when internal enums come from several sibling namespaces.
  • Regression tests were added to tests/unit/test_typeddict.py covering all three cases.

Validation

  • test_typeddict.py + test_enums.py: 50 passed (42 existing + 8 new).
  • pylint 10.00/10 on the changed files; black clean under the project config; mypy introduces no new errors (the pre-existing errors are unchanged on the baseline).

Fixes: #11626

…pes.py

Fixes three codegen bugs producing invalid annotations in generated types.py:

- Internal enums used as TypedDict fields are imported as a bare symbol from
  their private _enums submodule, and the annotation no longer emits an
  undefined _enums. prefix.
- Deduplicate runtime and TYPE_CHECKING imports of the same symbol to avoid
  mypy no-redef errors.
- Emit a flat (non-inheriting) TypedDict when a child overrides an inherited
  field's requiredness, satisfying PEP 589.

Adds regression tests for all three cases.

Fixes: microsoft#11626

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>

Copilot-Session: 1a8cce88-1663-4cc6-a634-2e83e35d04b7
@microsoft-github-policy-service microsoft-github-policy-service Bot added the emitter:client:python Issue for the Python client emitter: @typespec/http-client-python label Aug 11, 2026
@pkg-pr-new

pkg-pr-new Bot commented Aug 11, 2026

Copy link
Copy Markdown

Open in StackBlitz

npm i https://pkg.pr.new/@typespec/http-client-python@11627

commit: 708a666

@github-actions

Copy link
Copy Markdown
Contributor

All changed packages have been documented.

  • @typespec/http-client-python
Show changes

@typespec/http-client-python - fix ✏️

Fix invalid Python type annotations generated in types.py files. Internal enums used as TypedDict fields are now imported (as a bare symbol) from their private _enums submodule so the annotation resolves; duplicate runtime + TYPE_CHECKING imports of the same symbol are deduplicated to avoid no-redef; and TypedDicts that change an inherited field's requiredness are emitted as a flat (non-inheriting) TypedDict to satisfy PEP 589.

@azure-sdk-automation

Copy link
Copy Markdown

You can try these changes here

🛝 Playground 🌐 Website 🛝 VSCode Extension

@l0lawrence

Copy link
Copy Markdown
Member Author

Reopening as a same-repo PR (branch pushed to microsoft/typespec) so the emitter-diff CI check runs.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

emitter:client:python Issue for the Python client emitter: @typespec/http-client-python

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug]: Python emitter generates invalid type annotations for Azure AI Search

1 participant