Skip to content

Commit f6cf175

Browse files
committed
pylock: refine and test some validation erros
1 parent 2e433d6 commit f6cf175

File tree

2 files changed

+82
-12
lines changed

2 files changed

+82
-12
lines changed

src/pip/_internal/models/pylock.py

Lines changed: 8 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,8 @@ def _get(d: Dict[str, Any], expected_type: Type[T], key: str) -> Optional[T]:
8585
return None
8686
if not isinstance(value, expected_type):
8787
raise PylockValidationError(
88-
f"{key} has unexpected type {type(value)} (expected {expected_type})"
88+
f"{key!r} has unexpected type {type(value).__name__} "
89+
f"(expected {expected_type.__name__})"
8990
)
9091
return value
9192

@@ -114,7 +115,7 @@ def _get_as(
114115
try:
115116
return target_type(value)
116117
except Exception as e:
117-
raise PylockValidationError(f"Error parsing value of {key!r}: {e}") from e
118+
raise PylockValidationError(f"Error in {key!r}: {e}") from e
118119

119120

120121
def _get_required_as(
@@ -145,15 +146,13 @@ def _get_list_as(
145146
for i, item in enumerate(value):
146147
if not isinstance(item, expected_type):
147148
raise PylockValidationError(
148-
f"Item {i} of {key} has unpexpected type {type(item)} "
149-
f"(expected {expected_type})"
149+
f"Item {i} of {key!r} has unexpected type {type(item).__name__} "
150+
f"(expected {expected_type.__name__})"
150151
)
151152
try:
152153
result.append(target_type(item))
153154
except Exception as e:
154-
raise PylockValidationError(
155-
f"Error parsing item {i} of {key!r}: {e}"
156-
) from e
155+
raise PylockValidationError(f"Error in item {i} of {key!r}: {e}") from e
157156
return result
158157

159158

@@ -167,7 +166,7 @@ def _get_object(
167166
try:
168167
return target_type.from_dict(value)
169168
except Exception as e:
170-
raise PylockValidationError(f"Error parsing value of {key!r}: {e}") from e
169+
raise PylockValidationError(f"Error in {key!r}: {e}") from e
171170

172171

173172
def _get_list_of_objects(
@@ -184,9 +183,7 @@ def _get_list_of_objects(
184183
try:
185184
result.append(target_type.from_dict(item))
186185
except Exception as e:
187-
raise PylockValidationError(
188-
f"Error parsing item {i} of {key!r}: {e}"
189-
) from e
186+
raise PylockValidationError(f"Error in item {i} of {key!r}: {e}") from e
190187
return result
191188

192189

tests/unit/test_pylock.py

Lines changed: 74 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -107,7 +107,7 @@ def test_pylock_packages_without_dist() -> None:
107107
with pytest.raises(PylockValidationError) as exc_info:
108108
Pylock.from_dict(data)
109109
assert str(exc_info.value) == (
110-
"Error parsing item 0 of 'packages': "
110+
"Error in item 0 of 'packages': "
111111
"Exactly one of vcs, directory, archive must be set "
112112
"if sdist and wheels are not set"
113113
)
@@ -139,3 +139,76 @@ def test_pylock_basic_package() -> None:
139139
assert package.marker == Marker('os_name == "posix"')
140140
assert package.requires_python == SpecifierSet(">=3.10, !=3.10.1")
141141
assert pylock.to_dict() == data
142+
143+
144+
def test_pylock_invalid_archive() -> None:
145+
data = {
146+
"lock-version": "1.0",
147+
"created-by": "pip",
148+
"requires-python": ">=3.10",
149+
"environments": ['os_name == "posix"'],
150+
"packages": [
151+
{
152+
"name": "example",
153+
"archive": {
154+
# "path": "example.tar.gz",
155+
"hashes": {"sha256": "f" * 40},
156+
},
157+
}
158+
],
159+
}
160+
with pytest.raises(PylockValidationError) as exc_info:
161+
Pylock.from_dict(data)
162+
assert str(exc_info.value) == (
163+
"Error in item 0 of 'packages': "
164+
"Error in 'archive': "
165+
"No path nor url set for archive package"
166+
)
167+
168+
169+
def test_pylock_invalid_wheel() -> None:
170+
data = {
171+
"lock-version": "1.0",
172+
"created-by": "pip",
173+
"requires-python": ">=3.10",
174+
"environments": ['os_name == "posix"'],
175+
"packages": [
176+
{
177+
"name": "example",
178+
"wheels": [
179+
{
180+
"name": "example-1.0-py3-none-any.whl",
181+
"path": "./example-1.0-py3-none-any.whl",
182+
# "hashes": {"sha256": "f" * 40},
183+
}
184+
],
185+
}
186+
],
187+
}
188+
with pytest.raises(PylockValidationError) as exc_info:
189+
Pylock.from_dict(data)
190+
assert str(exc_info.value) == (
191+
"Error in item 0 of 'packages': "
192+
"Error in item 0 of 'wheels': "
193+
"Missing required key 'hashes'"
194+
)
195+
196+
197+
def test_pylock_invalid_environments() -> None:
198+
data = {
199+
"lock-version": "1.0",
200+
"created-by": "pip",
201+
"environments": [
202+
'os_name == "posix"',
203+
'invalid_marker == "..."',
204+
],
205+
"packages": [],
206+
}
207+
with pytest.raises(PylockValidationError) as exc_info:
208+
Pylock.from_dict(data)
209+
assert str(exc_info.value) == (
210+
"Error in item 1 of 'environments': "
211+
"Expected a marker variable or quoted string\n"
212+
' invalid_marker == "..."\n'
213+
" ^"
214+
)

0 commit comments

Comments
 (0)