54 lines
1.7 KiB
Python
54 lines
1.7 KiB
Python
|
import argparse
|
||
|
import json
|
||
|
import os
|
||
|
import subprocess
|
||
|
|
||
|
GET_INPUTS_CMD = [
|
||
|
"nix-instantiate",
|
||
|
"--eval",
|
||
|
"--json", # This parser is stupid, better provide it with pre-eaten stuff
|
||
|
"--expr",
|
||
|
"builtins.fromJSON (builtins.toJSON (import ./flake.nix).inputs)",
|
||
|
]
|
||
|
|
||
|
|
||
|
def process_flake(flake: str) -> None:
|
||
|
# get full path
|
||
|
if not os.path.isfile(flake):
|
||
|
raise FileNotFoundError(f"Flake not found: {flake}")
|
||
|
dir = os.path.dirname(flake)
|
||
|
# import dependencies
|
||
|
p = subprocess.run(GET_INPUTS_CMD, cwd=dir, stdout=subprocess.PIPE)
|
||
|
deps = json.loads(p.stdout)
|
||
|
p.check_returncode()
|
||
|
# for each dependency
|
||
|
for dep_name, dep in deps.items():
|
||
|
dep_url = dep["url"]
|
||
|
# if not local path, continue
|
||
|
if not (
|
||
|
dep_url.startswith("path:") or dep_url.startswith("git+file:")
|
||
|
):
|
||
|
continue
|
||
|
if dep.get("flake", True):
|
||
|
# get flake file corresponding
|
||
|
dep_path = dep_url.split(":")[1]
|
||
|
if not dep_path.startswith("/"):
|
||
|
dep_path = os.path.join(dir, dep_path)
|
||
|
dep_path = os.path.normpath(dep_path)
|
||
|
dep_flake = os.path.join(dep_path, "flake.nix")
|
||
|
# call this function with the flake file
|
||
|
process_flake(dep_flake)
|
||
|
# update lockfile
|
||
|
cmd = ["nix", "flake", "lock", "--update-input", dep_name]
|
||
|
subprocess.run(cmd, cwd=dir)
|
||
|
|
||
|
|
||
|
if __name__ == "__main__":
|
||
|
parser = argparse.ArgumentParser(
|
||
|
description="Recursively update lockfiles "
|
||
|
"of flakes located on the system"
|
||
|
)
|
||
|
parser.add_argument("flake", help="Starting flake", default="flake.nix")
|
||
|
args = parser.parse_args()
|
||
|
process_flake(args.flake)
|