better typing

This commit is contained in:
John Lancaster
2026-06-21 15:41:22 -05:00
parent 57347077a9
commit 4f05f13e45
3 changed files with 62 additions and 0 deletions
+15
View File
@@ -73,6 +73,20 @@ Use these defaults unless a hard compatibility constraint prevents them:
5. Use `typing.Literal` when a finite value set is the real contract.
6. Remove legacy typing aliases and module-level `TypeVar` declarations when PEP 695 can replace them.
7. Keep runtime behavior unchanged unless the task explicitly requests behavior refactors.
8. Treat `typing.cast(...)` as a last resort, not a default fix for type-checker complaints.
9. Before adding a cast, prefer real narrowing (`isinstance`, `TypeIs`/`TypeGuard`), explicit control-flow checks, or small annotation refactors that preserve behavior.
10. Reject casts whose only purpose is to silence the checker without a clear runtime invariant.
11. For closed variant sets (`Literal`/`Enum`/tagged unions), prefer structural pattern matching with exhaustiveness checks (`assert_never`) for deterministic narrowing.
## Cast Discipline
Use this policy whenever a modernization pass encounters a potential cast:
1. Confirm whether the checker can be satisfied with stronger narrowing first (for example `isinstance` or assertion-based narrowing).
2. If a cast is still necessary, keep it narrowly scoped to the exact expression rather than widening an entire variable flow.
3. Document the invariant that makes the cast valid in human terms, not just "type checker requires this".
4. Prefer fixing imprecise annotations at the source over stacking repeated casts downstream.
5. If multiple casts appear in one code path, treat that as a design smell and propose a structural typing fix.
## Completion Checks
@@ -81,6 +95,7 @@ Use these defaults unless a hard compatibility constraint prevents them:
3. Public APIs are unchanged unless explicitly requested.
4. Feature-level recommendations include source links.
5. Any deferral is backed by a specific hard constraint (for example Python version floor).
6. New casts, if any, are minimal, justified by an explicit invariant, and not used as checker-silencing shortcuts.
## Output Contract