mirror of
https://github.com/NixOS/nixos-hardware.git
synced 2025-11-05 17:38:41 +08:00
100 lines
3.1 KiB
Python
Executable File
100 lines
3.1 KiB
Python
Executable File
#!/usr/bin/env nix-shell
|
|
#!nix-shell -i python -p nix -p "python3.withPackages (p: [p.requests])"
|
|
|
|
import argparse
|
|
import json
|
|
import re
|
|
import subprocess
|
|
import sys
|
|
from tempfile import NamedTemporaryFile
|
|
from concurrent.futures import ThreadPoolExecutor, as_completed
|
|
|
|
import requests
|
|
|
|
API_BASE = "https://api.github.com"
|
|
PATCH_PATTERN = re.compile(r"^\d{4}-.*\.patch$")
|
|
|
|
parser = argparse.ArgumentParser(
|
|
description="Update linux-t2 patches from a GitHub repository."
|
|
)
|
|
parser.add_argument("filename", help="the output filename")
|
|
parser.add_argument(
|
|
"--repository",
|
|
help="the source github repository",
|
|
default="t2linux/linux-t2-patches",
|
|
nargs="?",
|
|
)
|
|
ref_group = parser.add_mutually_exclusive_group()
|
|
ref_group.add_argument(
|
|
"--reference", help="the git reference for the patches", default=None, nargs="?"
|
|
)
|
|
ref_group.add_argument(
|
|
"--branch", help="the git branch to fetch", default=None, nargs="?"
|
|
)
|
|
|
|
|
|
def get_api(endpoint, *args, **kwargs):
|
|
kwargs["headers"] = {"X-GitHub-Api-Version": "2022-11-28"}
|
|
response = requests.get(API_BASE + endpoint, *args, **kwargs)
|
|
response.raise_for_status()
|
|
return response.json()
|
|
|
|
|
|
def get_sri_hash(data: bytes):
|
|
with NamedTemporaryFile() as tmpfile:
|
|
tmpfile.write(data)
|
|
tmpfile.flush()
|
|
proc = subprocess.run(
|
|
["nix-hash", "--sri", "--flat", "--type", "sha256", tmpfile.name],
|
|
check=True,
|
|
capture_output=True,
|
|
)
|
|
return proc.stdout.decode("utf8").strip()
|
|
|
|
def download_task(patch: dict):
|
|
patch_content = requests.get(patch["download_url"])
|
|
patch_hash = get_sri_hash(patch_content.content)
|
|
print(f"{patch['name']}: {patch_hash}")
|
|
return {"name": patch["name"], "hash": patch_hash}
|
|
|
|
def main():
|
|
args = parser.parse_args()
|
|
reference = args.reference
|
|
branch = args.branch
|
|
|
|
if reference is None:
|
|
if branch is None:
|
|
print("Branch and reference not provided, fetching default branch")
|
|
branch = get_api(f"/repos/{args.repository}")["default_branch"]
|
|
|
|
print(f"Reference not provided, fetching from branch {branch}")
|
|
branch_data = get_api(f"/repos/{args.repository}/branches/{branch}")
|
|
reference = branch_data["commit"]["sha"]
|
|
|
|
print(f"Repository: {args.repository}")
|
|
print(f" Reference: {reference}")
|
|
|
|
base_url = f"https://raw.githubusercontent.com/{args.repository}/{reference}/"
|
|
contents = get_api(f"/repos/{args.repository}/contents", {"ref": reference})
|
|
patches = filter(lambda e: PATCH_PATTERN.match(e.get("name")), contents)
|
|
|
|
patches_with_hash = []
|
|
with ThreadPoolExecutor() as executor:
|
|
futures = {executor.submit(download_task, patch) for patch in patches}
|
|
|
|
for future in as_completed(futures):
|
|
patches_with_hash.append(future.result())
|
|
|
|
result = {"base_url": base_url, "patches": sorted(patches_with_hash, key=lambda p: p["name"])}
|
|
|
|
with open(args.filename, "w+") as f:
|
|
json.dump(result, f, indent=2)
|
|
f.write("\n") # write final newline
|
|
print(f"Wrote to {args.filename}")
|
|
|
|
return 0
|
|
|
|
|
|
if __name__ == "__main__":
|
|
sys.exit(main())
|