def _write_json(path: Path, manifest: Dict[str, Any]) -> None:
    path.write_text(json.dumps(manifest, indent=2, sort_keys=True), encoding="utf-8")


def _write_markdown(path: Path, manifest: Dict[str, Any]) -> None:
    s = manifest.get("summary", {}) or {}
    env = s.get("environment", {})
    deps = s.get("dependencies", {})
    gaps = s.get("gaps", {})
    exps = s.get("experiments", {})
    gate = s.get("local_gate", {})

    lines: List[str] = []
    lines.append("# `_codex_` Reproducibility Manifest\n")
    lines.append(f"- Generated at: `{manifest.get('generated_at', '')}`")
    lines.append(f"- Repo root   : `{manifest.get('repo_root', '.')}`\n")

    lines.append("## 1. Environment\n")
    if not env.get("available"):
        lines.append("- Environment snapshot: **not available**\n")
    else:
        lines.append(f"- Python version: `{env.get('python_version')}`")
        lines.append(
            f"- OS: `{env.get('os_platform')}` / `{env.get('os_release')}`"
        )
        keys = env.get("codex_env_var_keys") or []
        if keys:
            lines.append(f"- CODEX_* env vars: {', '.join(keys)}")
        else:
            lines.append("- CODEX_* env vars: (none recorded)")
        lines.append("")

    lines.append("## 2. Dependencies\n")
    if not deps.get("available"):
        lines.append("- Dependency report: **not available**\n")
    else:
        lines.append(f"- Total packages      : {deps.get('total_packages')}")
        lines.append(f"- Direct dependencies : {deps.get('direct_dependencies')}")
        lines.append("")

    lines.append("## 3. Gaps (Gap Registry)\n")
    if not gaps.get("available"):
        lines.append("- Gap registry: **not available**\n")
    else:
        lines.append(f"- Total gaps: **{gaps.get('total_gaps', 0)}**")
        by_status = gaps.get("by_status") or {}
        if by_status:
            lines.append("- By status:")
            for status, count in sorted(by_status.items()):
                lines.append(f"  - **{status}**: {count}")
        by_risk = gaps.get("by_risk_level") or {}
        if by_risk:
            lines.append("- By risk level:")
            for level, count in sorted(by_risk.items()):
                lines.append(f"  - **{level}**: {count}")
        lines.append("")

    lines.append("## 4. Experiments\n")
    if not exps.get("available"):
        lines.append("- Experiment index: **not available**\n")
    else:
        lines.append(f"- Total runs: **{exps.get('total_runs', 0)}**")
        by_mode = exps.get("runs_by_mode") or {}
        if by_mode:
            lines.append("- Runs by mode:")
            for mode, count in sorted(by_mode.items()):
                lines.append(f"  - **{mode}**: {count}")
        cfgs = exps.get("unique_config_paths") or []
        if cfgs:
            lines.append("- Unique config paths:")
            for c in cfgs:
                lines.append(f"  - `{c}`")
        lines.append("")

    lines.append("## 5. Local Gate\n")
    if not gate.get("available"):
        lines.append("- Local gate report: **not available**\n")
    else:
        lines.append(
            f"- Overall return code: **{gate.get('overall_returncode', 0)}**"
        )
        lines.append(f"- Total commands     : {gate.get('total_commands', 0)}")
        failed = gate.get("failed_commands") or []
        if failed:
            lines.append("- Failed commands:")
            for name in failed:
                lines.append(f"  - `{name}`")
        else:
            lines.append("- Failed commands: (none)")

    path.write_text("\n".join(lines) + "\n", encoding="utf-8")


def main(argv: Optional[List[str]] = None) -> int:
    parser = argparse.ArgumentParser(
        description="Generate `_codex_` reproducibility manifest."
    )
    parser.add_argument(
        "--repo-root",
        type=str,
        default=".",
        help="Repository root (default: current directory).",
    )
    parser.add_argument(
        "--env-snapshot",
        type=str,
        default="codex_env_snapshot.json",
        help="Environment snapshot JSON (default: codex_env_snapshot.json).",
    )
    parser.add_argument(
        "--dep-report",
        type=str,
        default="codex_dependency_report.json",
        help="Dependency report JSON (default: codex_dependency_report.json).",
    )
    parser.add_argument(
        "--gap-registry",
        type=str,
        default="codex_gap_registry.yaml",
        help="Gap registry YAML (default: codex_gap_registry.yaml).",
    )
    parser.add_argument(
        "--experiment-index",
        type=str,
        default="codex_experiment_index.json",
        help="Experiment index JSON (default: codex_experiment_index.json).",
    )
    parser.add_argument(
        "--local-gate",
        type=str,
        default="codex_local_gate_report.json",
        help="Local gate report JSON (default: codex_local_gate_report.json).",
    )
    parser.add_argument(
        "--json-out",
        type=str,
        default="codex_reproducibility_manifest.json",
        help="JSON output path (default: codex_reproducibility_manifest.json).",
    )
    parser.add_argument(
        "--md-out",
        type=str,
        default="codex_reproducibility_manifest.md",
        help="Markdown output path (default: codex_reproducibility_manifest.md).",
    )
    args = parser.parse_args(argv)

    repo_root = Path(args.repo_root).expanduser().resolve()
    manifest = build_manifest(
        repo_root=repo_root,
        env_snapshot_path=Path(args.env_snapshot).expanduser().resolve(),
        dep_report_path=Path(args.dep_report).expanduser().resolve(),
        gap_registry_path=Path(args.gap_registry).expanduser().resolve(),
        exp_index_path=Path(args.experiment_index).expanduser().resolve(),
        local_gate_path=Path(args.local_gate).expanduser().resolve(),
    )

    json_out = Path(args.json_out).expanduser().resolve()
    md_out = Path(args.md_out).expanduser().resolve()
    _write_json(json_out, manifest)
    _write_markdown(md_out, manifest)

    print(f"[codex_repro_manifest] Wrote JSON to {json_out}")
    print(f"[codex_repro_manifest] Wrote Markdown to {md_out}")
    return 0


if __name__ == "__main__":  # pragma: no cover
    raise SystemExit(main())
````

===============================================================================
2) Tests for repro manifest – tests/tools/test_codex_repro_manifest.py
======================================================================

Create/overwrite: tests/tools/test_codex_repro_manifest.py

```python
from pathlib import Path
import json
import yaml

import tools.codex_repro_manifest as repro


def test_build_manifest_handles_missing_inputs(tmp_path: Path):
    repo_root = tmp_path
    env = tmp_path / "codex_env_snapshot.json"
    deps = tmp_path / "codex_dependency_report.json"
    gaps = tmp_path / "codex_gap_registry.yaml"
    exp = tmp_path / "codex_experiment_index.json"
    gate = tmp_path / "codex_local_gate_report.json"

    manifest = repro.build_manifest(
        repo_root=repo_root,
        env_snapshot_path=env,
        dep_report_path=deps,
        gap_registry_path=gaps,
        exp_index_path=exp,
        local_gate_path=gate,
    )
    assert "summary" in manifest
    s = manifest["summary"]
    assert s["environment"]["available"] is False
    assert s["dependencies"]["available"] is False
    assert s["gaps"]["available"] is False
    assert s["experiments"]["available"] is False
    assert s["local_gate"]["available"] is False


def test_build_manifest_with_minimal_inputs(tmp_path: Path):
    repo_root = tmp_path

    # Minimal env snapshot
    env = tmp_path / "codex_env_snapshot.json"
    env.write_text(
        json.dumps(
            {
                "python": {"version": "3.11.0"},
                "os": {"platform": "linux", "release": "5.x"},
                "env": {"CODEX_MODE": "test"},
            }
        ),
        encoding="utf-8",
    )

    # Minimal dependency report
    deps = tmp_path / "codex_dependency_report.json"
    deps.write_text(
        json.dumps(
            {
                "packages": [
                    {"name": "pytest", "version": "8.0.0", "kind": "direct"},
                    {"name": "yaml", "version": "6.0.0", "kind": "transitive"},
                ]
            }
        ),
        encoding="utf-8",
    )

    # Minimal gap registry
    gaps = tmp_path / "codex_gap_registry.yaml"
    gaps.write_text(
        yaml.safe_dump(
            {
                "gaps": [
                    {
                        "id": "GAP-0001",
                        "status": "open",
                        "risk_level": "high",
                    },
                    {
                        "id": "GAP-0002",
                        "status": "closed",
                        "risk_level": "low",
                    },
                ]
            },
            sort_keys=False,
        ),
        encoding="utf-8",
    )

    # Minimal experiment index
    exp = tmp_path / "codex_experiment_index.json"
    exp.write_text(
        json.dumps(
            {
                "runs_dir": str(tmp_path / "runs"),
                "runs": [
                    {
                        "mode": "train",
                        "run_id": "train-run-1",
                        "config_path": "conf/train.yaml",
                    },
                    {
                        "mode": "eval",
                        "run_id": "eval-run-1",
                        "config_path": "conf/eval.yaml",
                    },
                ],
            }
        ),
        encoding="utf-8",
    )

    # Minimal local gate report
    gate = tmp_path / "codex_local_gate_report.json"
    gate.write_text(
        json.dumps(
            {
                "overall_returncode": 1,
                "results": [
                    {"name": "pytest_tools", "returncode": 0},
                    {"name": "pytest_codex_ml", "returncode": 1},
