#!/bin/bash # Branch archiving — archives previous run artifacts when the branch changes. # Preserves prd.json, progress.md, and contracts from the previous feature. # # Design: At the end of each run, snapshot_for_archive saves current artifacts # to .archive-staging/. On the next run, if the branch changed, check_archive # moves the snapshot to archive/ and cleans up. This avoids archiving the # WRONG artifacts (the new feature's) when prd.json has already been overwritten. LAST_BRANCH_FILE="$LOOP_DIR/.last-branch" STAGING_DIR="$LOOP_DIR/.archive-staging" # Snapshot current artifacts so they can be archived later if the branch changes. # Call this at the END of a successful run or before exit. snapshot_for_archive() { rm -rf "$STAGING_DIR" mkdir -p "$STAGING_DIR" [ -f "$LOOP_DIR/prd.json" ] && cp "$LOOP_DIR/prd.json" "$STAGING_DIR/" [ -f "$LOOP_DIR/progress.md" ] && cp "$LOOP_DIR/progress.md" "$STAGING_DIR/" [ -d "$LOOP_DIR/contracts" ] && cp -r "$LOOP_DIR/contracts" "$STAGING_DIR/" } # Check if we need to archive and do so if branch changed. # Reads the NEW branch from live prd.json and the OLD branch from the staging # snapshot (which was saved at the end of the previous run). This avoids the # bug where both branches read from the same (already-overwritten) prd.json. check_archive() { local current_branch current_branch=$(prd_branch_name 2>/dev/null) [ -z "$current_branch" ] && return # Determine the previous branch from the staging snapshot (most reliable) # or fall back to .last-branch file local last_branch="" if [ -f "$STAGING_DIR/prd.json" ]; then if command -v jq &>/dev/null; then last_branch=$(jq -r '.branchName // empty' "$STAGING_DIR/prd.json" 2>/dev/null) else last_branch=$(LOOP_PRD="$STAGING_DIR/prd.json" python3 -c " import json, os print(json.load(open(os.environ['LOOP_PRD'])).get('branchName', ''), end='') " 2>/dev/null) fi fi [ -z "$last_branch" ] && [ -f "$LAST_BRANCH_FILE" ] && last_branch=$(cat "$LAST_BRANCH_FILE") if [ -n "$last_branch" ] && [ "$last_branch" != "$current_branch" ]; then archive_run "$last_branch" fi echo "$current_branch" > "$LAST_BRANCH_FILE" } # Archive the previous run's staged artifacts (NOT current prd.json) archive_run() { local branch_name="$1" local feature_name feature_name=$(echo "$branch_name" | sed 's|.*/||') local archive_dir="$LOOP_DIR/archive/$(date +%Y-%m-%d)-${feature_name}" mkdir -p "$archive_dir" if [ -d "$STAGING_DIR" ]; then # Use the staged snapshot (correct artifacts from the previous run) cp -r "$STAGING_DIR"/* "$archive_dir/" 2>/dev/null || true rm -rf "$STAGING_DIR" else # Fallback: no snapshot exists (first run or upgrade from old version). # Current artifacts may belong to the new feature — archive what we have # but warn the user. log "WARNING: No archive snapshot found. Archiving current artifacts (may be from new feature)." [ -f "$LOOP_DIR/prd.json" ] && cp "$LOOP_DIR/prd.json" "$archive_dir/" [ -f "$LOOP_DIR/progress.md" ] && cp "$LOOP_DIR/progress.md" "$archive_dir/" [ -d "$LOOP_DIR/contracts" ] && cp -r "$LOOP_DIR/contracts" "$archive_dir/" fi # Clean up old run's artifacts (progress.md, contracts — NOT prd.json which belongs to new feature) rm -f "$LOOP_DIR/progress.md" rm -rf "$LOOP_DIR/contracts" log "Archived previous run to $archive_dir" }