#!/usr/bin/env bash
# main-repo-readonly-guard.sh — Claude Code UserPromptSubmit hook
#
# 强制"主仓库工作目录只读"铁律 + 后台保持跟 origin/develop 对齐。
# 详见 CLAUDE.md「主仓库工作目录只读（铁律）」段。
#
# 触发：UserPromptSubmit（每次发消息）
# cwd 是 ffoa workspace 主仓库（不是 slot/worktree） → 执行；否则静默 exit 0
#
# 行为：
#   主仓库 dirty   → stdout 输出 <system-reminder>，让 AI/用户立即看见；不阻断
#   主仓库 clean   → 后台 git fetch + git pull --ff-only origin develop（5 分钟节流）
#
# 设计原则：
#   - 永不阻断 prompt（任何失败 exit 0）
#   - 后台跑同步，用户感觉零延迟
#   - 节流，避免连续消息时反复 fetch
#   - 只检查 ffoa workspace（凭 scripts/dev/agent-pool/ 特征文件判定，不写死路径）
#
# 安装：项目 .claude/settings.json UserPromptSubmit hooks 数组追加
#   {"type": "command", "command": "./scripts/ops/hooks/main-repo-readonly-guard.sh"}
set -uo pipefail

# 1. 必须在 git 仓库
REPO_ROOT="$(git rev-parse --show-toplevel 2>/dev/null)" || exit 0
[ -n "$REPO_ROOT" ] || exit 0

# 2. 必须不是 slot/worktree（slot 内允许改）
case "$REPO_ROOT" in
  */.agent-pool/slot-*) exit 0 ;;
  */ffworkspace-wt/*)   exit 0 ;;
esac

# 3. 必须是 ffoa workspace（凭特征文件，不写死路径——别的开发者机器路径不一样）
[ -d "$REPO_ROOT/scripts/dev/agent-pool" ] || exit 0
[ -f "$REPO_ROOT/CLAUDE.md" ] || exit 0

# 4. dirty 检查
DIRTY_LINES="$(git -C "$REPO_ROOT" status --porcelain 2>/dev/null)"
DIRTY_COUNT="$(printf '%s\n' "$DIRTY_LINES" | grep -c . || true)"

if [ "$DIRTY_COUNT" -gt 0 ]; then
  PREVIEW="$(printf '%s\n' "$DIRTY_LINES" | head -10)"
  REST=$((DIRTY_COUNT - 10))
  cat <<EOF
<system-reminder>
⚠ 主仓库 dirty（$DIRTY_COUNT 条改动），违反「主仓库工作目录只读」铁律（CLAUDE.md「核心不变量」段）。

前 10 条：
$PREVIEW
$([ $REST -gt 0 ] && echo "... 还有 $REST 条")

处理路径（按可能性排序）：
  1. 是真工作 → claim 一个 slot，把改动挪过去（git stash → 在 slot 里 git stash pop）
  2. 是临时文件/截图/日志 → mv 到 /tmp/ 或加 .gitignore
  3. 是别的 session 留的 leak → 给用户看清单，问怎么处理（保留 / 丢弃 / 接手）
  4. 不确定 → 不要继续往主仓库写新东西，先把现状给用户审

铁律理由：主仓库 dirty → git pull 会冲突 → origin/* ref 长期漂移 → 任何"读代码/读 ref 推理"基准都过期。详见 .learnings/2026-05-19-main-repo-drift-meta-rootcause.md
</system-reminder>
EOF
  exit 0
fi

# 5. 干净 → 后台 fetch + ff pull（5 分钟节流）
FETCH_HEAD="$REPO_ROOT/.git/FETCH_HEAD"
NOW="$(date +%s)"
SHOULD_FETCH=1
if [ -f "$FETCH_HEAD" ]; then
  LAST="$(stat -c %Y "$FETCH_HEAD" 2>/dev/null || echo 0)"
  if [ "$((NOW - LAST))" -lt 300 ]; then
    SHOULD_FETCH=0
  fi
fi

if [ "$SHOULD_FETCH" -eq 1 ]; then
  # 后台同步，本 prompt 不等。
  # 只在 develop 分支才自动 pull（主仓库按铁律永远在 develop，但 defense-in-depth）。
  (
    git -C "$REPO_ROOT" fetch --quiet origin 2>/dev/null || true
    CUR="$(git -C "$REPO_ROOT" branch --show-current 2>/dev/null || echo '')"
    if [ "$CUR" = "develop" ]; then
      git -C "$REPO_ROOT" pull --ff-only --quiet origin develop 2>/dev/null || true
    fi
  ) >/dev/null 2>&1 &
fi

exit 0
