• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

aio-libs / multidict / 36162962679
87%

Build:
DEFAULT BRANCH: master
Ran 25 Sep 2026 04:48PM UTC
Jobs 1
Files 43
Run time 1min
Badge
Embed ▾
README BADGES
x

If you need to use a raster PNG badge, change the '.svg' to '.png' in the link

Markdown

Textile

RDoc

HTML

Rst

25 Sep 2026 04:47PM UTC coverage: 87.089% (+0.09%) from 87.004%
36162962679

push

github

web-flow
Make istr a final class to prevent identity invariant violations (#1573)

## What does this PR do?

Fixes #1535.

As suggested by maintainer @asvetlov, this PR makes `istr` a final class
to disallow subclassing in both the C extension and pure-Python
implementations, preventing canonical identity invariant violations:
- In debug builds of the C extension (`MULTIDICT_DEBUG_BUILD=1`),
`unicode_hash` hits `assert(PyUnicode_CheckExact(o))` if an `istr`
subclass overrides `lower()` with a non-exact `str`.
- In release builds, casting a non-exact `str` to `PyASCIIObject*` risks
reading incorrect memory layouts.
- Subclassing `istr` is not intended in real-world usage; making `istr`
final simplifies the design and cleanly guarantees the canonical
identity invariant across the board.

### Changes Made:
1. **C Extension (`multidict/_multilib/istr.h`)**:
- Dropped `Py_TPFLAGS_BASETYPE` from `istr_spec` to forbid subclassing
`istr`.
2. **Pure Python (`multidict/_multidict_py.py`)**:
- Added `@final` decorator and `__init_subclass__` check raising
`TypeError: type 'multidict._multidict_py.istr' is not an acceptable
base type`.
- In `_CIMixin._identity()` and `_CSMixin._identity()`, ensure an exact
`str` is returned if a plain `str` subclass returns a non-exact `str`.
3. **Testing (`tests/test_istr.py`)**:
- Updated `test_subclass_ctor` to verify that attempting to subclass
`istr` raises `TypeError`.
- Added tests covering plain `str` subclasses overriding `lower()`
across both C and pure-Python backends.
   - 100% statement and branch coverage with zero CodeQL warnings.
4. **Towncrier Newsfragment**:
   - Updated `CHANGES/1535.bugfix.rst`.

## Verification:
- All tests pass in both C extension and pure-Python implementations
with 100% test coverage on changed files.
- Full test suite, sanitizers (ASan, TSan), CodeQL, and Hypothesis pass
in CI.
- C code formatted with `clang-format`, Python code formatted and linted
with `ruff`.

780 of 1560 branches covered (50.0%)

Branch coverage included in aggregate %.

68 of 68 new or added lines in 3 files covered. (100.0%)

8164 of 8710 relevant lines covered (93.73%)

1.87 hits per line

Jobs
ID Job ID Ran Files Coverage
1 MyPy - 36162962679.1 25 Sep 2026 04:48PM UTC 86
87.09
GitHub Action Run
Source Files on build 36162962679
  • Tree
  • List 43
  • Changed 4
  • Source Changed 3
  • Coverage Changed 4
Coverage ∆ File Lines Relevant Covered Missed Hits/Line Branch Hits Branch Misses
  • Back to Repo
  • Github Actions Build #36162962679
  • 1706f5cd on github
  • Prev Build on master (#36158345628)
  • Next Build on master (#36182074040)
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc