#!/usr/bin/env bash
set -Eeuo pipefail
umask 077
VERIFY_ONLY=false
if [[ "${1:-}" == --verify-only ]]; then VERIFY_ONLY=true; shift; fi
[[ "$#" -ge 3 && "$#" -le 4 ]] || { echo 'Usage: router-step-bootstrap [--verify-only] ZIP ZIP_SHA256 INSTALLER_SHA256 [TARGET_PACKAGE_SHA256]' >&2; exit 2; }
ZIP="$1"; ZIP_SHA="$2"; INSTALL_SHA="$3"; TARGET_SHA="${4:-}"
BASE="${ROUTER_OPS_BASE:-/opt/router-ops}"
GATE="${ROUTER_BUNDLE_GATE:-$BASE/bin/router-bundle-gate}"
ZIP_TOOL="$BASE/bin/router-zip-contract"
RELEASE_TOOL="$BASE/bin/router-release-contract"
STEP="$(basename "$ZIP" .zip)"
INCOMING="$(dirname "$ZIP")"
WORK="$INCOMING/.unpack-${STEP}-$$"
STEP_STARTED=false
EMERGENCY_HANDLED=false
LATEST_BEFORE="$WORK/.latest-before.txt"
LATEST_AFTER="$WORK/.latest-after.txt"

source_workflow() {
  [[ -r "$BASE/lib/router-step-workflow.sh" ]] || return 1
  # shellcheck disable=SC1090
  source "$BASE/lib/router-step-workflow.sh"
}
snapshot_latest() {
  local out="$1"
  find "$INCOMING" -maxdepth 1 -type f -name 'WG_PAID_MGTS_LATEST_*.zip' -printf '%f\n' 2>/dev/null | LC_ALL=C sort > "$out" || true
}
new_started_latest() {
  snapshot_latest "$LATEST_AFTER"
  comm -13 "$LATEST_BEFORE" "$LATEST_AFTER" | tail -n1
}
retain_started_bundle() {
  local retained actual
  source_workflow || return 1
  if [[ -f "$ZIP" ]]; then
    router_step_retain_bundle "$ZIP" "$ZIP_SHA" "$BASE" "$INCOMING"
    return $?
  fi
  retained="$BASE/state/retained-step-zips/$STEP/${ZIP_SHA}.zip"
  if [[ -f "$retained" ]]; then
    actual="$(sha256sum "$retained" | awk '{print $1}')"
    if [[ "$actual" == "$ZIP_SHA" ]]; then
      echo RESULT=PASS_ROUTER_STEP_RETAIN_BUNDLE_ALREADY_RETAINED
      echo "STEP=$STEP"
      echo "RETAINED_STEP_ZIP=$retained"
      echo "RETAINED_STEP_ZIP_SHA256=$actual"
      echo INCOMING_SOURCE_REMOVED=true
      return 0
    fi
    echo RESULT=STOP_ROUTER_STEP_RETAIN_BUNDLE_RETAINED_SHA_MISMATCH
    echo "STEP=$STEP"
    echo "RETAINED_STEP_ZIP=$retained"
    echo "EXPECTED_SHA256=$ZIP_SHA"
    echo "ACTUAL_SHA256=$actual"
    return 1
  fi
  echo RESULT=STOP_ROUTER_STEP_RETAIN_BUNDLE_MISSING
  echo "BUNDLE=$ZIP"
  return 1
}
archive_current_latest() {
  source_workflow || return 1
  router_step_archive_latest_python "$BASE" "$INCOMING" "$(date -u +%Y%m%d-%H%M%S)"
}
cleanup_old_unpacks() {
  source_workflow || return 0
  router_step_cleanup_stale_unpacks "$BASE" "$INCOMING" "$WORK" || true
}
started_stop() {
  local rc="$1" line="$2" command="$3" newest='' retained=false
  trap - ERR; set +e
  echo RESULT=STOP_ROUTER_STEP_BOOTSTRAP
  echo "STEP=$STEP"
  echo "BOOTSTRAP_STOP_LINE=$line"
  echo "BOOTSTRAP_STOP_RC=$rc"
  printf 'BOOTSTRAP_STOP_COMMAND=%q\n' "$command"
  if retain_started_bundle; then retained=true; else echo STARTED_BUNDLE_RETENTION=FAILED; fi
  newest="$(new_started_latest 2>/dev/null || true)"
  if [[ -n "$newest" && -f "$INCOMING/$newest" ]]; then
    echo STARTED_ATTEMPT_LATEST_PRESENT=true
    echo "STARTED_ATTEMPT_LATEST=$INCOMING/$newest"
    if [[ "$retained" == true ]]; then
      rm -rf "$WORK"
      echo UNPACK_CLEANUP=PASS_SAFE_STOP_CLOSURE
      cleanup_old_unpacks
    else
      echo "RETAINED_UNPACK_DIR=$WORK"
    fi
  else
    echo STARTED_ATTEMPT_LATEST_PRESENT=false
    archive_current_latest || true
    echo "RETAINED_UNPACK_DIR=$WORK"
    echo UNPACK_CLEANUP=SKIPPED_EMERGENCY_EVIDENCE
  fi
  exit "$rc"
}
emergency_stop() {
  local rc="$1" line="$2" command="$3"
  trap - ERR
  [[ "$EMERGENCY_HANDLED" == false ]] || exit "$rc"
  EMERGENCY_HANDLED=true
  if [[ "$STEP_STARTED" == true ]]; then
    started_stop "$rc" "$line" "$command"
  fi
  set +e
  echo RESULT=STOP_ROUTER_STEP_BOOTSTRAP_PRESTART
  echo "STEP=$STEP"
  echo "BOOTSTRAP_STOP_LINE=$line"
  echo "BOOTSTRAP_STOP_RC=$rc"
  printf 'BOOTSTRAP_STOP_COMMAND=%q\n' "$command"
  echo STEP_WAS_NOT_STARTED=true
  echo "RETAINED_UNPACK_DIR=$WORK"
  exit "$rc"
}
trap 'rc=$?; emergency_stop "$rc" "$LINENO" "$BASH_COMMAND"' ERR

[[ -x "$ZIP_TOOL" && -x "$RELEASE_TOOL" ]]
[[ -f "$ZIP" ]] || { echo RESULT=STOP_COPY_OR_TRANSFER_ERROR; echo COPY_VERIFY=FAIL; echo STEP_WAS_NOT_STARTED=true; exit 20; }
echo '>>> verify ZIP'
echo "$ZIP_SHA  $ZIP" | sha256sum -c -
rm -rf "$WORK"; mkdir -p "$WORK"; chmod 700 "$WORK"
"$ZIP_TOOL" verify --zip "$ZIP" --root "$STEP" --canonical
"$ZIP_TOOL" extract --zip "$ZIP" --destination "$WORK" --root "$STEP" --canonical
DIR="$WORK/$STEP"
[[ -f "$DIR/install.sh" && -f "$DIR/manifest.sha256" && -f "$DIR/release-info.json" ]]
(cd "$DIR" && sha256sum -c manifest.sha256)
contract_version="$(python3 - "$DIR/release-info.json" <<'PYV'
import json,sys
print(int(json.load(open(sys.argv[1],encoding='utf-8')).get('workflow_contract_version') or 0))
PYV
)"
if [[ "$contract_version" -ge 2 ]]; then
  args=(verify --root "$DIR" --step "$STEP" --installer-sha "$INSTALL_SHA")
  [[ -n "$TARGET_SHA" ]] && args+=(--target-sha "$TARGET_SHA")
  "$RELEASE_TOOL" "${args[@]}"
else
  python3 - "$DIR/release-info.json" "$STEP" "$INSTALL_SHA" "$TARGET_SHA" <<'PYLEG'
import json,sys
p,step,ish,tsh=sys.argv[1:]
x=json.load(open(p,encoding='utf-8')); assert x['step_id']==step; assert x['expected_installer_sha256']==ish
if tsh: assert x.get('target_package_sha256')==tsh
PYLEG
fi
if find "$DIR" \( -type d -name __pycache__ -o -type f \( -name '*.pyc' -o -name '*.pyo' \) \) -print -quit | grep -q .; then
  echo RESULT=STOP_BUNDLE_PYTHON_BYTECODE_PRESENT; exit 22
fi
python3 - "$DIR" <<'PYCLASS' | while IFS=$'\t' read -r kind file; do
import sys
from pathlib import Path
root=Path(sys.argv[1])
for p in sorted(x for x in root.rglob('*') if x.is_file()):
    first=p.open('rb').readline(256).decode('ascii','ignore').rstrip('\r\n')
    kind={'#!/usr/bin/env bash':'bash','#!/bin/bash':'bash','#!/bin/sh':'sh','#!/bin/ash':'sh','#!/usr/bin/env python3':'python','#!/usr/bin/python3':'python'}.get(first)
    if kind: print(f'{kind}\t{p}')
PYCLASS
  case "$kind" in
    bash) bash -n "$file" ;;
    sh) sh -n "$file" ;;
    python) python3 - "$file" <<'PYCHECK'
import sys
from pathlib import Path
p=Path(sys.argv[1]); compile(p.read_bytes(),str(p),'exec')
PYCHECK
      ;;
  esac
done
BUNDLE_ZIP="$ZIP" EXPECTED_BUNDLE_SHA256="$ZIP_SHA" BUNDLE_ROOT="$DIR" "$GATE" "$DIR"
echo MANIFEST_VERIFY=PASS
echo SYNTAX_VERIFY=PASS
echo FIXTURE_VERIFY=PASS
echo COPY_VERIFY=PASS
echo "STEP_SHA256=$INSTALL_SHA"
if [[ "$VERIFY_ONLY" == true ]]; then echo RESULT=PASS_ROUTER_STEP_BOOTSTRAP_VERIFY_ONLY; rm -rf "$WORK"; exit 0; fi

echo ">>> start $STEP"
snapshot_latest "$LATEST_BEFORE"
STEP_STARTED=true
if BUNDLE_ZIP="$ZIP" EXPECTED_BUNDLE_SHA256="$ZIP_SHA" EXPECTED_INSTALLER_SHA256="$INSTALL_SHA" "$DIR/install.sh"; then
  rc=0
else
  rc=$?
fi
echo "BOOTSTRAP_INSTALLER_RC=$rc"
if [[ "$rc" -ne 0 ]]; then
  started_stop "$rc" "$LINENO" 'installer returned non-zero'
fi

newest="$(new_started_latest 2>/dev/null || true)"
if [[ -z "$newest" || ! -f "$INCOMING/$newest" ]]; then
  echo RESULT=STOP_ROUTER_STEP_BOOTSTRAP_PASS_WITHOUT_FRESH_LATEST
  echo "STEP=$STEP"
  retain_started_bundle || true
  echo "RETAINED_UNPACK_DIR=$WORK"
  trap - ERR
  exit 74
fi
retain_started_bundle
# LATEST_AFTER was populated by new_started_latest above. Validate the final
# incoming Latest invariant while the work directory still exists; only then
# remove work evidence. This prevents a successful STEP from deleting its own
# .latest-after.txt before bootstrap closure bookkeeping is complete.
latest_count="$(wc -l < "$LATEST_AFTER" | tr -d ' ')"
echo "INCOMING_LATEST_COUNT=$latest_count"
[[ "$latest_count" -eq 1 ]]
trap - ERR
rm -rf "$WORK" || true
cleanup_old_unpacks
echo RESULT=PASS_ROUTER_STEP_BOOTSTRAP_CLOSURE
exit 0
