"""Canonical FDS build version, shared by Cargo, images and package builders.""" from pathlib import Path import re import subprocess ROOT = Path(__file__).resolve().parents[1] RELEASE = re.compile(r'v?([0-9]+(?:\.[0-9]+){1,2})\Z') VALID = re.compile(r'[0-9][A-Za-z0-9.]{0,31}\Z') def validate(value): if not isinstance(value, str) or not VALID.fullmatch(value): raise ValueError(f'Invalid FDS version: {value!r}') return value def git(root, *args): return subprocess.check_output(['git', '-C', str(root), *args], text=True, stderr=subprocess.DEVNULL).strip() def version(root=ROOT): root = Path(root).resolve() # Source exports carry the value resolved when the export was created. # Never accidentally describe a containing repository during offline builds. if not (root / '.git').exists(): return validate((root / 'FDS_VERSION').read_text().strip()) revision = git(root, 'rev-parse', '--short=12', 'HEAD') tags = [tag for tag in git(root, 'tag', '--merged', 'HEAD').splitlines() if RELEASE.fullmatch(tag)] if tags: description = git(root, 'describe', '--tags', '--long', '--abbrev=12', *[f'--match={tag}' for tag in tags], 'HEAD') tag, distance, commit = description.rsplit('-', 2) value = RELEASE.fullmatch(tag)[1] if int(distance): value += f'.r{distance}.{commit}' else: value = f'0.dev.g{revision}' if git(root, 'status', '--porcelain', '--untracked-files=no'): value += '.dirty' return validate(value) def cargo(root=ROOT): print(f'cargo:rustc-env=FDS_BUILD_VERSION={version(root)}') for path in [root / 'tools/fds_version.py', root / 'tools/version', root / 'tools/version-build.rs']: print(f'cargo:rerun-if-changed={path}') if not (root / '.git').exists(): print(f'cargo:rerun-if-changed={root / "FDS_VERSION"}') return # Tag creation, ref changes, staging and edits must invalidate cached binaries. for name in ['HEAD', 'index', 'packed-refs', 'refs']: path = git(root, 'rev-parse', '--path-format=absolute', '--git-path', name) print(f'cargo:rerun-if-changed={path}') head = subprocess.run(['git', '-C', str(root), 'symbolic-ref', '-q', 'HEAD'], capture_output=True, text=True) if head.returncode == 0: print('cargo:rerun-if-changed=' + git(root, 'rev-parse', '--path-format=absolute', '--git-path', head.stdout.strip())) paths = git(root, 'ls-files', '--cached', '--others', '--exclude-standard').splitlines() for name in paths: if name != 'vendor/void-packages': print(f'cargo:rerun-if-changed={root / name}')