Package pinned native Claude and prove isolated startup
Assistant: codex Assistant-Model: gpt-6-astra Assistant-Session: 01a0726e-5232-73f2-aaca-2c05ceb62efb
This commit is contained in:
parent
cfc79d51af
commit
174dba17b6
7 changed files with 299 additions and 8 deletions
|
|
@ -7,7 +7,9 @@ Run with the sand-boxer Python environment; uv must be available on PATH.
|
|||
from __future__ import annotations
|
||||
|
||||
import argparse
|
||||
import hashlib
|
||||
import json
|
||||
import re
|
||||
import subprocess
|
||||
from pathlib import Path
|
||||
|
||||
|
|
@ -21,7 +23,31 @@ def checked(command: list[str]) -> str:
|
|||
return result.stdout.strip()
|
||||
|
||||
|
||||
def build(output: Path, rein_source: Path, llm_source: Path) -> dict:
|
||||
def install_claude(output: Path, source: Path, sha256: str, version: str) -> dict:
|
||||
"""Copy only an explicitly pinned native executable, never an interactive HOME."""
|
||||
if not re.fullmatch(r"[0-9a-f]{64}", sha256) or not version.strip():
|
||||
raise ValueError("Claude requires an exact SHA-256 and expected version")
|
||||
if source.is_symlink() or not source.is_file():
|
||||
raise ValueError("Claude source must be a regular file, not a symlink")
|
||||
content = source.read_bytes()
|
||||
if hashlib.sha256(content).hexdigest() != sha256:
|
||||
raise ValueError("Claude executable digest mismatch")
|
||||
if not content.startswith(b"\x7fELF"):
|
||||
raise ValueError("Claude executable must be native ELF, not a host wrapper")
|
||||
destination = output / "bin/claude"
|
||||
with destination.open("xb") as stream:
|
||||
stream.write(content)
|
||||
destination.chmod(0o755)
|
||||
return {"path": f"{RUNTIME_MOUNT}/bin/claude", "sha256": sha256,
|
||||
"expected_version": version, "source": str(source)}
|
||||
|
||||
|
||||
def build(output: Path, rein_source: Path, llm_source: Path,
|
||||
claude_binary: Path | None = None, claude_sha256: str | None = None,
|
||||
claude_version: str | None = None) -> dict:
|
||||
supplied = (claude_binary, claude_sha256, claude_version)
|
||||
if any(x is not None for x in supplied) and not all(x is not None for x in supplied):
|
||||
raise ValueError("Claude binary, SHA-256 and expected version must be supplied together")
|
||||
revisions = {}
|
||||
for name, source in (("rein-aharness", rein_source), ("llm-connect", llm_source)):
|
||||
if checked(["git", "-C", str(source), "status", "--porcelain"]):
|
||||
|
|
@ -46,6 +72,8 @@ def build(output: Path, rein_source: Path, llm_source: Path) -> dict:
|
|||
"print(json.dumps({'python':platform.python_version(),'packages':"
|
||||
"{d.metadata['Name']:d.version for d in importlib.metadata.distributions()}}))",
|
||||
]))
|
||||
if claude_binary is not None:
|
||||
metadata["claude"] = install_claude(output, claude_binary, claude_sha256, claude_version)
|
||||
metadata["source_revisions"] = revisions
|
||||
(output / "build-info.json").write_text(json.dumps(metadata, indent=2) + "\n")
|
||||
return {"runtime": {"path": str(output), "sha256": runtime_digest(output)},
|
||||
|
|
@ -57,8 +85,12 @@ def main() -> int:
|
|||
parser.add_argument("--output", type=Path, required=True)
|
||||
parser.add_argument("--rein-source", type=Path, required=True)
|
||||
parser.add_argument("--llm-source", type=Path, required=True)
|
||||
parser.add_argument("--claude-binary", type=Path)
|
||||
parser.add_argument("--claude-sha256")
|
||||
parser.add_argument("--claude-version")
|
||||
args = parser.parse_args()
|
||||
result = build(args.output.resolve(), args.rein_source.resolve(), args.llm_source.resolve())
|
||||
result = build(args.output.resolve(), args.rein_source.resolve(), args.llm_source.resolve(),
|
||||
args.claude_binary, args.claude_sha256, args.claude_version)
|
||||
print(json.dumps(result, indent=2))
|
||||
return 0
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue