Source code for analysis.paths

"""Locating the monorepo root and the cached-artefact paths.

Each pipeline stage writes its outputs and a manifest under
``<root>/artefacts/<stage>/<run-hash>/``, where the run hash is a content hash over the
inputs that determine the output (dataset version, feature list, hyperparameters, seed,
stratum definition, and the package commit). The directory is gitignored, because it
holds participant-derived intermediates that the SFARI consent does not allow into the
committed history.
"""

from __future__ import annotations

import os
from pathlib import Path


[docs] def find_repo_root(start: Path | None = None) -> Path: """Walk up from ``start`` (or the working directory) to the monorepo root. Honours ``ANALYSIS_ROOT`` if set. Otherwise the root is the nearest ancestor that holds a ``data/`` directory or a ``pyproject.toml`` declaring a uv workspace. Parameters ---------- start : Path, optional Directory to start the search from. Defaults to the working directory. Returns ------- Path The resolved monorepo root. """ env = os.environ.get("ANALYSIS_ROOT") if env: return Path(env).expanduser().resolve() start = (start or Path.cwd()).resolve() for d in (start, *start.parents): if (d / "data").is_dir(): return d pp = d / "pyproject.toml" if pp.is_file(): try: if "[tool.uv.workspace]" in pp.read_text(encoding="utf-8"): return d except OSError: pass return start
[docs] def artefacts_dir(root: Path) -> Path: """Return the cached-artefacts directory, ``<root>/artefacts``.""" return root / "artefacts"
[docs] def stage_dir(root: Path, stage: str) -> Path: """Return the directory holding every run of one stage, ``<root>/artefacts/<stage>``.""" return artefacts_dir(root) / stage
[docs] def run_dir(root: Path, stage: str, run_hash: str) -> Path: """Return one run's directory, ``<root>/artefacts/<stage>/<run-hash>``.""" return stage_dir(root, stage) / run_hash
[docs] def manifest_path(run_dir: Path) -> Path: """Return the manifest path for a run, ``<run-dir>/manifest.json``.""" return run_dir / "manifest.json"