From 3c8d46f68ec6ced8e89d57f5f3b8fcabb8ab2773 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Sat, 23 Mar 2024 19:01:16 +0200 Subject: [PATCH] Fixed mapping checks against Django's MultiValueDict Fixes #419. --- docs/versionhistory.rst | 2 ++ src/typeguard/_config.py | 8 ++++---- tests/test_checkers.py | 8 ++++++++ 3 files changed, 14 insertions(+), 4 deletions(-) diff --git a/docs/versionhistory.rst b/docs/versionhistory.rst index f79a7954..87b23035 100644 --- a/docs/versionhistory.rst +++ b/docs/versionhistory.rst @@ -16,6 +16,8 @@ This library adheres to (`#432 `_, PR by Yongxin Wang) - Fixed detection of optional fields (``NotRequired[...]``) in ``TypedDict`` when using forward references (`#424 `_) +- Fixed mapping checks against Django's ``MultiValueDict`` + (`#419 `_) **4.1.5** (2023-09-11) diff --git a/src/typeguard/_config.py b/src/typeguard/_config.py index 04cecf84..36efad53 100644 --- a/src/typeguard/_config.py +++ b/src/typeguard/_config.py @@ -1,6 +1,6 @@ from __future__ import annotations -from collections.abc import Collection +from collections.abc import Iterable from dataclasses import dataclass from enum import Enum, auto from typing import TYPE_CHECKING, TypeVar @@ -49,11 +49,11 @@ class CollectionCheckStrategy(Enum): FIRST_ITEM = auto() ALL_ITEMS = auto() - def iterate_samples(self, collection: Collection[T]) -> Collection[T]: + def iterate_samples(self, collection: Iterable[T]) -> Iterable[T]: if self is CollectionCheckStrategy.FIRST_ITEM: - if len(collection): + try: return [next(iter(collection))] - else: + except StopIteration: return () else: return collection diff --git a/tests/test_checkers.py b/tests/test_checkers.py index d767b4fc..b8e01c6c 100644 --- a/tests/test_checkers.py +++ b/tests/test_checkers.py @@ -433,6 +433,14 @@ def test_bad_value_type_full_check(self): collection_check_strategy=CollectionCheckStrategy.ALL_ITEMS, ).match("value of key 'y' of dict is not an instance of int") + def test_custom_dict_generator_items(self): + class CustomDict(dict): + def items(self): + for key in self: + yield key, self[key] + + check_type(CustomDict(a=1), Dict[str, int]) + class TestTypedDict: @pytest.mark.parametrize(