-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathflatpak-pypi-checker.py
105 lines (79 loc) · 3.22 KB
/
flatpak-pypi-checker.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
import argparse
import json
import re
import urllib.request
from dataclasses import dataclass
class RequirementsUpdater:
""""""
@dataclass(frozen=True)
class Requirement:
name: str
version: str
filters: list[str] # filter1:filter2:filter3
data: list = None
_requirements: dict[str, Requirement] = {} # name mapped to object
@property
def requirements(self) -> dict[str, Requirement]:
return dict(self._requirements)
def configure_for(self, dependencies: list[str]) -> None:
for dependency in dependencies:
name, filters = dependency.split("::")
filters = [f.strip() for f in filters.split(":")]
if "==" in name:
name, _, version = re.split("(>=|==|<=)", name)
elif "<=" in name:
raise ValueError("Version requirement '<=' currently not supported")
else:
version = "latest"
self._requirements[name] = self.Requirement(name, version, filters)
def resolve(self) -> None:
for requirement in self._requirements.values():
name = requirement.name
with urllib.request.urlopen(f"https://pypi.org/pypi/{name}/json", timeout=5) as connection:
data = json.loads(connection.read().decode("utf-8").strip())
version = data["info"]["version"] if requirement.version == "latest" else requirement.version
filters = requirement.filters
data = data["releases"][version]
self._requirements[requirement.name] = self.Requirement(name, version, filters, data)
def extract(self) -> list:
""""""
def find_first_filename_matching(files: list, must_contain_substr: list[str]) -> dict:
for file in files:
if all(f in file["filename"] for f in must_contain_substr):
return file
raise StopIteration(
f"Cannot find file containing all required substrings: {", ".join(must_contain_substr)}"
)
dependencies = []
for requirement in self._requirements.values():
filters = requirement.filters
release = find_first_filename_matching(files=requirement.data, must_contain_substr=filters)
value = {
"name": requirement.name,
"version": requirement.version,
"filename": release["filename"],
"sha256": release["digests"]["sha256"],
"url": release["url"],
}
dependencies.append(value)
dependencies.sort(key=lambda x: x["name"])
return dependencies
def main():
parser = argparse.ArgumentParser(description="Prints relevant info for flatpak pypi dependencies")
parser.add_argument(
"--dependency",
type=str,
action="append",
default=[],
help="dependency to consider: dependency::filename-filter1:filename-filter2",
)
run(parser.parse_args())
def run(args):
updater = RequirementsUpdater()
updater.configure_for(args.dependency)
updater.resolve()
dependencies = updater.extract()
data = json.dumps(dependencies)
print(data)
if __name__ == "__main__":
main()