5
5
import os .path
6
6
import re
7
7
import shutil
8
+ import zipfile
8
9
10
+ from pip ._vendor .packaging .utils import canonicalize_name , canonicalize_version
11
+ from pip ._vendor .packaging .version import InvalidVersion , Version
12
+ from pip ._vendor .pkg_resources import Distribution
13
+
14
+ from pip ._internal .exceptions import InvalidWheelFilename , UnsupportedWheel
9
15
from pip ._internal .models .link import Link
16
+ from pip ._internal .models .wheel import Wheel
10
17
from pip ._internal .operations .build .wheel import build_wheel_pep517
11
18
from pip ._internal .operations .build .wheel_legacy import build_wheel_legacy
12
19
from pip ._internal .utils .logging import indent_log
16
23
from pip ._internal .utils .temp_dir import TempDirectory
17
24
from pip ._internal .utils .typing import MYPY_CHECK_RUNNING
18
25
from pip ._internal .utils .urls import path_to_url
26
+ from pip ._internal .utils .wheel import pkg_resources_distribution_for_wheel
19
27
from pip ._internal .vcs import vcs
20
28
21
29
if MYPY_CHECK_RUNNING :
@@ -160,9 +168,49 @@ def _always_true(_):
160
168
return True
161
169
162
170
171
+ def _get_metadata_version (dist ):
172
+ # type: (Distribution) -> Optional[Version]
173
+ for line in dist .get_metadata_lines (dist .PKG_INFO ):
174
+ if line .lower ().startswith ("metadata-version:" ):
175
+ value = line .split (":" , 1 )[- 1 ].strip ()
176
+ try :
177
+ return Version (value )
178
+ except InvalidVersion :
179
+ msg = "Invalid Metadata-Version: {}" .format (value )
180
+ raise UnsupportedWheel (msg )
181
+ raise UnsupportedWheel ("Missing Metadata-Version" )
182
+
183
+
184
+ def _verify_one (req , wheel_path ):
185
+ # type: (InstallRequirement, str) -> None
186
+ canonical_name = canonicalize_name (req .name )
187
+ w = Wheel (os .path .basename (wheel_path ))
188
+ if w .name != canonical_name :
189
+ raise InvalidWheelFilename (
190
+ "Wheel has unexpected file name: expected {!r}, "
191
+ "got {!r}" .format (canonical_name , w .name ),
192
+ )
193
+ with zipfile .ZipFile (wheel_path , allowZip64 = True ) as zf :
194
+ dist = pkg_resources_distribution_for_wheel (
195
+ zf , canonical_name , wheel_path ,
196
+ )
197
+ if canonicalize_version (dist .version ) != canonicalize_version (w .version ):
198
+ raise InvalidWheelFilename (
199
+ "Wheel has unexpected file name: expected {!r}, "
200
+ "got {!r}" .format (dist .version , w .version ),
201
+ )
202
+ if (_get_metadata_version (dist ) >= Version ("1.2" )
203
+ and not isinstance (dist .parsed_version , Version )):
204
+ raise UnsupportedWheel (
205
+ "Metadata 1.2 mandates PEP 440 version, "
206
+ "but {!r} is not" .format (dist .version )
207
+ )
208
+
209
+
163
210
def _build_one (
164
211
req , # type: InstallRequirement
165
212
output_dir , # type: str
213
+ verify , # type: bool
166
214
build_options , # type: List[str]
167
215
global_options , # type: List[str]
168
216
):
@@ -182,9 +230,16 @@ def _build_one(
182
230
183
231
# Install build deps into temporary directory (PEP 518)
184
232
with req .build_env :
185
- return _build_one_inside_env (
233
+ wheel_path = _build_one_inside_env (
186
234
req , output_dir , build_options , global_options
187
235
)
236
+ if wheel_path and verify :
237
+ try :
238
+ _verify_one (req , wheel_path )
239
+ except (InvalidWheelFilename , UnsupportedWheel ) as e :
240
+ logger .warning ("Built wheel for %s is invalid: %s" , req .name , e )
241
+ return None
242
+ return wheel_path
188
243
189
244
190
245
def _build_one_inside_env (
@@ -257,6 +312,7 @@ def _clean_one_legacy(req, global_options):
257
312
def build (
258
313
requirements , # type: Iterable[InstallRequirement]
259
314
wheel_cache , # type: WheelCache
315
+ verify , # type: bool
260
316
build_options , # type: List[str]
261
317
global_options , # type: List[str]
262
318
):
@@ -280,7 +336,7 @@ def build(
280
336
for req in requirements :
281
337
cache_dir = _get_cache_dir (req , wheel_cache )
282
338
wheel_file = _build_one (
283
- req , cache_dir , build_options , global_options
339
+ req , cache_dir , verify , build_options , global_options
284
340
)
285
341
if wheel_file :
286
342
# Update the link for this.
0 commit comments