affaan-m/ECC · error · FileNotFoundError
Trace file not found: {path}
Error message
Trace file not found: {path} What it means
Raised by parse_trace() in skill-comply when the supplied path does not point to an existing regular file. The function reads a JSONL observation trace from disk and guards immediately with path.is_file(), so any miss — wrong directory, typo, unexpanded '~', or a path that is actually a directory — surfaces here before any parsing begins.
Source
Thrown at skills/skill-comply/scripts/parser.py:50
description: str
required: bool
detector: Detector
@dataclass(frozen=True)
class ComplianceSpec:
id: str
name: str
source_rule: str
version: str
steps: tuple[Step, ...]
threshold_promote_to_hook: float
def parse_trace(path: Path) -> list[ObservationEvent]:
"""Parse a JSONL observation trace file into sorted events."""
if not path.is_file():
raise FileNotFoundError(f"Trace file not found: {path}")
text = path.read_text().strip()
if not text:
return []
events: list[ObservationEvent] = []
for i, line in enumerate(text.splitlines(), 1):
try:
raw = json.loads(line)
except json.JSONDecodeError as e:
raise ValueError(f"Invalid JSON at line {i}: {e}") from e
try:
events.append(ObservationEvent(
timestamp=raw["timestamp"],
event=raw["event"],
tool=raw["tool"],
session=raw["session"],
input=raw.get("input", ""),View on GitHub (pinned to 01e15490f0)
Solutions
- Print path.resolve() at the call site to confirm the absolute location actually being checked.
- Expand user paths explicitly: Path(p).expanduser() or Path.home() / 'traces' / 'x.jsonl'.
- Use absolute paths derived from a known project root instead of relative paths.
- If the file was never produced, run the generation step first (runner.run_scenario) so the trace exists before parsing.
Example fix
# before
from pathlib import Path
from scripts.parser import parse_trace
events = parse_trace(Path('~/skill-comply/trace.jsonl'))
# after
from pathlib import Path
from scripts.parser import parse_trace
trace_path = Path('~/skill-comply/trace.jsonl').expanduser()
if not trace_path.is_file():
raise SystemExit(f'trace not found: {trace_path}')
events = parse_trace(trace_path) Defensive patterns
Strategy: validation
Validate before calling
from pathlib import Path
def safe_parse_trace(path: Path):
resolved = Path(path).expanduser().resolve()
if not resolved.is_file():
raise SystemExit(f'trace not found: {resolved}')
from scripts.parser import parse_trace
return parse_trace(resolved) Try / catch
from scripts.parser import parse_trace
try:
events = parse_trace(path)
except FileNotFoundError as e:
log.warning('trace missing: %s', e)
events = [] Prevention
- Always call .expanduser().resolve() on Path inputs before passing them to parser functions.
- Derive trace paths from a known project root or __file__ rather than relative strings.
- In CI, assert the trace file exists as a separate step before invoking the parser.
When it happens
Trigger: Calling parse_trace(Path('missing.jsonl')); passing a directory path; constructing the Path in Python from a literal that contains an unexpanded '~' (e.g. Path('~/traces/x.jsonl')); passing a relative path while the process CWD differs from the caller's expectation.
Common situations: Running the compliance checker before generating traces; CI passing a relative path under a different working directory; downstream code reusing a path after the trace file was cleaned up by /tmp eviction.
Related errors
- Invalid JSON at line {i}: {e}
- Missing required field {e} at line {i}
- Spec file not found: {path}
- Missing 'scoring' section in compliance spec
- Unknown model: {model!r}. Allowed: {ALLOWED_MODELS}
AI-assisted analysis of affaan-m/ECC@01e15490f0 (2026-08-13).
Data as JSON: /api/errors/1c170254634e4ca1.
Report an issue: GitHub.