Marco Ricci commited on 2025-08-17 16:01:53
Zeige 2 geänderte Dateien mit 66 Einfügungen und 66 Löschungen.
(This is part 2 of a series of refactorings for the test suite.) For the basic tests, collect all test data in a common class `Strategies` (similar to the `Parametrize` class). Split them into groups for validity testing and validation/data cleaning. For each group, factor out the common test operation... which in both cases, is the whole test content, save for the different input data set they run on. For the heavy-duty tests, there is only one data generation strategy, which needn't artifically be wrapped in a class (yet). There is also only one test, so there is no need for further grouping either. Instead, add some missing commentary on the one explicit example in that test set.
... | ... |
@@ -16,14 +16,19 @@ from tests import data |
16 | 16 |
from tests.machinery import hypothesis as hypothesis_machinery |
17 | 17 |
|
18 | 18 |
|
19 |
+class Strategies: |
|
20 |
+ VALID_VAULT_TEST_CONFIGS = tuple( |
|
21 |
+ conf for conf in data.TEST_CONFIGS if conf.is_valid() |
|
22 |
+ ) |
|
23 |
+ SMUDGABLE_VAULT_TEST_CONFIGS = tuple( |
|
24 |
+ conf for conf in data.TEST_CONFIGS if conf.is_smudgable() |
|
25 |
+ ) |
|
26 |
+ |
|
27 |
+ |
|
19 | 28 |
class Parametrize(types.SimpleNamespace): |
20 | 29 |
VALID_VAULT_TEST_CONFIGS = pytest.mark.parametrize( |
21 | 30 |
"test_config", |
22 |
- [ |
|
23 |
- conf |
|
24 |
- for conf in data.TEST_CONFIGS |
|
25 |
- if conf.validation_settings in {None, (True,)} |
|
26 |
- ], |
|
31 |
+ Strategies.VALID_VAULT_TEST_CONFIGS, |
|
27 | 32 |
ids=data.VaultTestConfig._test_id, |
28 | 33 |
) |
29 | 34 |
VAULT_TEST_CONFIGS = pytest.mark.parametrize( |
... | ... |
@@ -33,8 +38,25 @@ class Parametrize(types.SimpleNamespace): |
33 | 38 |
) |
34 | 39 |
|
35 | 40 |
|
41 |
+class TestVaultConfig: |
|
42 |
+ """Test `vault` configuration detection.""" |
|
43 |
+ |
|
44 |
+ @staticmethod |
|
45 |
+ def _test(test_config: data.VaultTestConfig) -> None: |
|
46 |
+ config, comment, _ = test_config |
|
47 |
+ obj = copy.deepcopy(config) |
|
48 |
+ did_cleanup = _types.clean_up_falsy_vault_config_values(obj) |
|
49 |
+ assert _types.is_vault_config(obj) == (not comment), ( |
|
50 |
+ "failed to complain about: " + comment |
|
51 |
+ if comment |
|
52 |
+ else "failed on valid example" |
|
53 |
+ ) |
|
54 |
+ assert did_cleanup is None or bool(did_cleanup) == (obj != config), ( |
|
55 |
+ "mismatched report on cleanup work" |
|
56 |
+ ) |
|
57 |
+ |
|
36 | 58 |
@Parametrize.VALID_VAULT_TEST_CONFIGS |
37 |
-def test_is_vault_config(test_config: data.VaultTestConfig) -> None: |
|
59 |
+ def test_is_config(self, test_config: data.VaultTestConfig) -> None: |
|
38 | 60 |
"""Is this vault configuration recognized as valid/invalid? |
39 | 61 |
|
40 | 62 |
Check all test configurations that do not need custom validation |
... | ... |
@@ -44,15 +66,7 @@ def test_is_vault_config(test_config: data.VaultTestConfig) -> None: |
44 | 66 |
[`_types.clean_up_falsy_vault_config_values`][] functions. |
45 | 67 |
|
46 | 68 |
""" |
47 |
- obj, comment, _ = test_config |
|
48 |
- obj = copy.deepcopy(obj) |
|
49 |
- _types.clean_up_falsy_vault_config_values(obj) |
|
50 |
- assert _types.is_vault_config(obj) == (not comment), ( |
|
51 |
- "failed to complain about: " + comment |
|
52 |
- if comment |
|
53 |
- else "failed on valid example" |
|
54 |
- ) |
|
55 |
- |
|
69 |
+ self._test(test_config) |
|
56 | 70 |
|
57 | 71 |
@hypothesis.given( |
58 | 72 |
test_config=hypothesis_machinery.smudged_vault_test_config( |
... | ... |
@@ -61,7 +75,8 @@ def test_is_vault_config(test_config: data.VaultTestConfig) -> None: |
61 | 75 |
]) |
62 | 76 |
) |
63 | 77 |
) |
64 |
-def test_is_vault_config_smudged( |
|
78 |
+ def test_is_config_even_if_smudged( |
|
79 |
+ self, |
|
65 | 80 |
test_config: data.VaultTestConfig, |
66 | 81 |
) -> None: |
67 | 82 |
"""Is this vault configuration recognized as valid/invalid? |
... | ... |
@@ -73,36 +88,20 @@ def test_is_vault_config_smudged( |
73 | 88 |
[`_types.clean_up_falsy_vault_config_values`][] functions. |
74 | 89 |
|
75 | 90 |
""" |
76 |
- obj_, comment, _ = test_config |
|
77 |
- obj = copy.deepcopy(obj_) |
|
78 |
- did_cleanup = _types.clean_up_falsy_vault_config_values(obj) |
|
79 |
- assert _types.is_vault_config(obj) == (not comment), ( |
|
80 |
- "failed to complain about: " + comment |
|
81 |
- if comment |
|
82 |
- else "failed on valid example" |
|
83 |
- ) |
|
84 |
- assert did_cleanup is None or bool(did_cleanup) == (obj != obj_), ( |
|
85 |
- "mismatched report on cleanup work" |
|
86 |
- ) |
|
91 |
+ self._test(test_config) |
|
87 | 92 |
|
88 | 93 |
|
89 |
-@Parametrize.VAULT_TEST_CONFIGS |
|
90 |
-def test_validate_vault_config( |
|
94 |
+class TestVaultConfigValidation: |
|
95 |
+ """Test the validation of `vault` configurations.""" |
|
96 |
+ |
|
97 |
+ def _test( |
|
98 |
+ self, |
|
91 | 99 |
test_config: data.VaultTestConfig, |
92 | 100 |
) -> None: |
93 |
- """Validate this vault configuration. |
|
94 |
- |
|
95 |
- Check all test configurations, including those with non-standard |
|
96 |
- validation settings. |
|
97 |
- |
|
98 |
- This primarily tests the [`_types.validate_vault_config`][] and |
|
99 |
- [`_types.clean_up_falsy_vault_config_values`][] functions. |
|
100 |
- |
|
101 |
- """ |
|
102 |
- obj, comment, validation_settings = test_config |
|
101 |
+ config, comment, validation_settings = test_config |
|
103 | 102 |
(allow_unknown_settings,) = validation_settings or (True,) |
104 |
- obj = copy.deepcopy(obj) |
|
105 |
- _types.clean_up_falsy_vault_config_values(obj) |
|
103 |
+ obj = copy.deepcopy(config) |
|
104 |
+ did_cleanup = _types.clean_up_falsy_vault_config_values(obj) |
|
106 | 105 |
if comment: |
107 | 106 |
with pytest.raises((TypeError, ValueError)): |
108 | 107 |
_types.validate_vault_config( |
... | ... |
@@ -115,9 +114,27 @@ def test_validate_vault_config( |
115 | 114 |
obj, |
116 | 115 |
allow_unknown_settings=allow_unknown_settings, |
117 | 116 |
) |
118 |
- except (TypeError, ValueError) as exc: # pragma: no cover |
|
119 |
- assert not exc, "failed to validate valid example" # noqa: PT017 |
|
117 |
+ except (TypeError, ValueError): # pragma: no cover |
|
118 |
+ pytest.fail("failed to validate valid example") |
|
119 |
+ assert did_cleanup is None or bool(did_cleanup) == (obj != config), ( |
|
120 |
+ "mismatched report on cleanup work" |
|
121 |
+ ) |
|
122 |
+ |
|
123 |
+ @Parametrize.VAULT_TEST_CONFIGS |
|
124 |
+ def test_validate_config( |
|
125 |
+ self, |
|
126 |
+ test_config: data.VaultTestConfig, |
|
127 |
+ ) -> None: |
|
128 |
+ """Validate this vault configuration. |
|
129 |
+ |
|
130 |
+ Check all test configurations, including those with non-standard |
|
131 |
+ validation settings. |
|
132 |
+ |
|
133 |
+ This primarily tests the [`_types.validate_vault_config`][] and |
|
134 |
+ [`_types.clean_up_falsy_vault_config_values`][] functions. |
|
120 | 135 |
|
136 |
+ """ |
|
137 |
+ self._test(test_config) |
|
121 | 138 |
|
122 | 139 |
@hypothesis.given( |
123 | 140 |
test_config=hypothesis_machinery.smudged_vault_test_config( |
... | ... |
@@ -126,7 +143,8 @@ def test_validate_vault_config( |
126 | 143 |
]) |
127 | 144 |
) |
128 | 145 |
) |
129 |
-def test_validate_vault_config_smudged( |
|
146 |
+ def test_validate_config_even_if_smudged( |
|
147 |
+ self, |
|
130 | 148 |
test_config: data.VaultTestConfig, |
131 | 149 |
) -> None: |
132 | 150 |
"""Validate this vault configuration. |
... | ... |
@@ -138,24 +156,4 @@ def test_validate_vault_config_smudged( |
138 | 156 |
[`_types.clean_up_falsy_vault_config_values`][] functions. |
139 | 157 |
|
140 | 158 |
""" |
141 |
- obj_, comment, validation_settings = test_config |
|
142 |
- (allow_unknown_settings,) = validation_settings or (True,) |
|
143 |
- obj = copy.deepcopy(obj_) |
|
144 |
- did_cleanup = _types.clean_up_falsy_vault_config_values(obj) |
|
145 |
- if comment: |
|
146 |
- with pytest.raises((TypeError, ValueError)): |
|
147 |
- _types.validate_vault_config( |
|
148 |
- obj, |
|
149 |
- allow_unknown_settings=allow_unknown_settings, |
|
150 |
- ) |
|
151 |
- else: |
|
152 |
- try: |
|
153 |
- _types.validate_vault_config( |
|
154 |
- obj, |
|
155 |
- allow_unknown_settings=allow_unknown_settings, |
|
156 |
- ) |
|
157 |
- except (TypeError, ValueError) as exc: # pragma: no cover |
|
158 |
- assert not exc, "failed to validate valid example" # noqa: PT017 |
|
159 |
- assert did_cleanup is None or bool(did_cleanup) == (obj != obj_), ( |
|
160 |
- "mismatched report on cleanup work" |
|
161 |
- ) |
|
159 |
+ self._test(test_config) |
... | ... |
@@ -68,7 +68,9 @@ def js_nested_strategy(draw: strategies.DrawFn) -> Any: |
68 | 68 |
|
69 | 69 |
|
70 | 70 |
@hypothesis.given(value=js_nested_strategy()) |
71 |
-@hypothesis.example(float("nan")) |
|
71 |
+@hypothesis.example(float("nan")).via( |
|
72 |
+ "for branch coverage in the implementation" |
|
73 |
+) |
|
72 | 74 |
def test_js_truthiness(value: Any) -> None: |
73 | 75 |
"""Determine the truthiness of a value according to JavaScript. |
74 | 76 |
|
75 | 77 |