-
Notifications
You must be signed in to change notification settings - Fork 278
/
Copy pathtest_garbage_collection.py
112 lines (82 loc) · 3.19 KB
/
test_garbage_collection.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
import platform
from collections.abc import Iterable
from typing import Any
from weakref import WeakValueDictionary
import pytest
from pydantic_core import SchemaSerializer, SchemaValidator, core_schema
from .conftest import assert_gc, is_free_threaded
GC_TEST_SCHEMA_INNER = core_schema.definitions_schema(
core_schema.definition_reference_schema(schema_ref='model'),
[
core_schema.typed_dict_schema(
{'x': core_schema.typed_dict_field(core_schema.definition_reference_schema(schema_ref='model'))},
ref='model',
)
],
)
@pytest.mark.xfail(is_free_threaded, reason='GC leaks on free-threaded')
@pytest.mark.xfail(
condition=platform.python_implementation() == 'PyPy', reason='https://foss.heptapod.net/pypy/pypy/-/issues/3899'
)
def test_gc_schema_serializer() -> None:
# test for https://github.com/pydantic/pydantic/issues/5136
class BaseModel:
__schema__: SchemaSerializer
def __init_subclass__(cls) -> None:
cls.__schema__ = SchemaSerializer(
core_schema.model_schema(cls, GC_TEST_SCHEMA_INNER), config={'ser_json_timedelta': 'float'}
)
cache: WeakValueDictionary[int, Any] = WeakValueDictionary()
for _ in range(10_000):
class MyModel(BaseModel):
pass
cache[id(MyModel)] = MyModel
del MyModel
assert_gc(lambda: len(cache) == 0)
@pytest.mark.xfail(is_free_threaded, reason='GC leaks on free-threaded')
@pytest.mark.xfail(
condition=platform.python_implementation() == 'PyPy', reason='https://foss.heptapod.net/pypy/pypy/-/issues/3899'
)
def test_gc_schema_validator() -> None:
# test for https://github.com/pydantic/pydantic/issues/5136
class BaseModel:
__validator__: SchemaValidator
def __init_subclass__(cls) -> None:
cls.__validator__ = SchemaValidator(
schema=core_schema.model_schema(cls, GC_TEST_SCHEMA_INNER),
config=core_schema.CoreConfig(extra_fields_behavior='allow'),
)
cache: WeakValueDictionary[int, Any] = WeakValueDictionary()
for _ in range(10_000):
class MyModel(BaseModel):
pass
cache[id(MyModel)] = MyModel
del MyModel
assert_gc(lambda: len(cache) == 0)
@pytest.mark.xfail(
condition=platform.python_implementation() == 'PyPy', reason='https://foss.heptapod.net/pypy/pypy/-/issues/3899'
)
def test_gc_validator_iterator() -> None:
# test for https://github.com/pydantic/pydantic/issues/9243
class MyModel:
iter: Iterable[int]
v = SchemaValidator(
core_schema.model_schema(
MyModel,
core_schema.model_fields_schema(
{'iter': core_schema.model_field(core_schema.generator_schema(core_schema.int_schema()))}
),
)
)
class MyIterable:
def __iter__(self):
return self
def __next__(self):
raise StopIteration()
cache: WeakValueDictionary[int, Any] = WeakValueDictionary()
for _ in range(10_000):
iterable = MyIterable()
cache[id(iterable)] = iterable
v.validate_python({'iter': iterable})
del iterable
assert_gc(lambda: len(cache) == 0)