|
5 | 5 | import urllib.request |
6 | 6 | import sys |
7 | 7 |
|
8 | | -ROOT_DIRNAME = path.dirname(path.dirname(path.abspath(__file__))) |
9 | | -REQUIREMENTS_PATH = path.join(ROOT_DIRNAME, "requirements.txt") |
10 | | -PYTHONFILES_PATH = path.join(ROOT_DIRNAME, "pythonFiles", "lib", "python") |
| 8 | +ROOT = path.dirname(path.dirname(path.abspath(__file__))) |
| 9 | +REQUIREMENTS = path.join(ROOT, "requirements.txt") |
| 10 | +PYTHONFILES = path.join(ROOT, "pythonFiles", "lib", "python") |
11 | 11 | PYPI_PTVSD_URL = "https://pypi.org/pypi/ptvsd/json" |
12 | 12 |
|
13 | 13 |
|
14 | 14 | def install_ptvsd(): |
15 | | - # If we are in CI use the packaging module installed in PYTHONFILES_PATH. |
| 15 | + # If we are in CI use the packaging module installed in PYTHONFILES. |
16 | 16 | if len(sys.argv) == 2 and sys.argv[1] == "--ci": |
17 | | - sys.path.insert(0, PYTHONFILES_PATH) |
| 17 | + sys.path.insert(0, PYTHONFILES) |
18 | 18 | from packaging.requirements import Requirement |
19 | 19 |
|
20 | | - with open(REQUIREMENTS_PATH, "r", encoding="utf-8") as requirements: |
21 | | - for line in requirements: |
22 | | - package_requirement = Requirement(line) |
23 | | - if package_requirement.name != "ptvsd": |
24 | | - continue |
25 | | - requirement_specifier = package_requirement.specifier |
26 | | - ptvsd_version = next(requirement_specifier.__iter__()).version |
| 20 | + with open(REQUIREMENTS, "r", encoding="utf-8") as reqsfile: |
| 21 | + for line in reqsfile: |
| 22 | + pkgreq = Requirement(line) |
| 23 | + if pkgreq.name == "ptvsd": |
| 24 | + specs = pkgreq.specifier |
| 25 | + version = next(iter(specs)).version |
| 26 | + break |
| 27 | + |
| 28 | + try: |
| 29 | + version |
| 30 | + except NameError: |
| 31 | + raise Exception("ptvsd requirement not found.") |
27 | 32 |
|
28 | 33 | # Response format: https://warehouse.readthedocs.io/api-reference/json/#project |
29 | 34 | with urllib.request.urlopen(PYPI_PTVSD_URL) as response: |
30 | 35 | json_response = json.loads(response.read()) |
31 | 36 | releases = json_response["releases"] |
32 | 37 |
|
33 | 38 | # Release metadata format: https://github.com/pypa/interoperability-peps/blob/master/pep-0426-core-metadata.rst |
34 | | - for wheel_info in releases[ptvsd_version]: |
| 39 | + for wheel_info in releases[version]: |
35 | 40 | # Download only if it's a 3.7 wheel. |
36 | 41 | if not wheel_info["python_version"].endswith(("37", "3.7")): |
37 | 42 | continue |
38 | 43 | filename = wheel_info["filename"].rpartition(".")[0] # Trim the file extension. |
39 | | - ptvsd_path = path.join(PYTHONFILES_PATH, filename) |
| 44 | + ptvsd_path = path.join(PYTHONFILES, filename) |
40 | 45 |
|
41 | 46 | with urllib.request.urlopen(wheel_info["url"]) as wheel_response: |
42 | 47 | wheel_file = BytesIO(wheel_response.read()) |
43 | | - # Extract only the contents of the ptvsd subfolder. |
44 | | - prefix = path.join(f"ptvsd-{ptvsd_version}.data", "purelib", "ptvsd") |
| 48 | + # Extract only the contents of the purelib subfolder (parent folder of ptvsd), |
| 49 | + # since ptvsd files rely on the presence of a 'ptvsd' folder. |
| 50 | + prefix = path.join(f"ptvsd-{version}.data", "purelib") |
45 | 51 |
|
46 | 52 | with ZipFile(wheel_file, "r") as wheel: |
47 | 53 | for zip_info in wheel.infolist(): |
48 | | - if not zip_info.filename.startswith(prefix): |
49 | | - continue |
| 54 | + # Normalize path for Windows, the wheel folder structure uses forward slashes. |
| 55 | + normalized = path.normpath(zip_info.filename) |
50 | 56 | # Flatten the folder structure. |
51 | | - zip_info.filename = zip_info.filename.split(prefix)[-1] |
| 57 | + zip_info.filename = normalized.split(prefix)[-1] |
52 | 58 | wheel.extract(zip_info, ptvsd_path) |
53 | 59 |
|
54 | 60 |
|
|
0 commit comments