@@ -7,11 +7,25 @@ source "$HOOK_DIR/lib/project-root.sh"
77COMMAND=$( hook_command_from_input " $INPUT " || true)
88GIT_PREFIX=' (^|[;&|][[:space:]]*)git([[:space:]]+(-C[[:space:]]+[^[:space:];&|]+|--no-pager|-c[[:space:]]+[^[:space:];&|]+|--work-tree(=|[[:space:]]+)[^[:space:];&|]+))*[[:space:]]+'
99
10+ if [[ -z " ${NVE_AGENT:- } " && -n " ${CURSOR_AGENT+x} " && -z " ${CURSOR_SANDBOX+x} " ]]; then
11+ export NVE_AGENT=" cursor-cloud-agent"
12+ fi
13+
1014# Exit early if not a git command
1115if [[ -z " $COMMAND " ]] || ! echo " $COMMAND " | grep -qE ' (^|[;&|][[:space:]]*)git([[:space:]]|$)' ; then
1216 exit 0
1317fi
1418
19+ warn () {
20+ echo " WARNING: Destructive git operation detected." >&2
21+ echo " Command: $COMMAND " >&2
22+ echo " Reason: $1 ." >&2
23+ echo " " >&2
24+ echo " Per AGENTS.md policy, destructive git operations require explicit user confirmation on user machines." >&2
25+ echo " In isolated VM environments, this hook is warning instead of blocking." >&2
26+ exit 0
27+ }
28+
1529block () {
1630 echo " BLOCKED: Destructive git operation detected." >&2
1731 echo " Command: $COMMAND " >&2
@@ -22,19 +36,27 @@ block() {
2236 exit 2
2337}
2438
25- echo " $COMMAND " | grep -qF " reset --hard" && block " git reset --hard discards all uncommitted changes irreversibly"
26- echo " $COMMAND " | grep -qF " push --force" && block " git push --force can overwrite remote history and destroy teammates' work"
27- echo " $COMMAND " | grep -qF " push -f" && block " git push -f can overwrite remote history and destroy teammates' work"
28- echo " $COMMAND " | grep -qF " clean -f" && block " git clean -f permanently deletes untracked files"
29- echo " $COMMAND " | grep -qF " checkout -- ." && block " git checkout -- . discards all unstaged changes irreversibly"
30- echo " $COMMAND " | grep -qF " branch -D" && block " git branch -D force-deletes a branch without merge checks"
31-
32- echo " $COMMAND " | grep -qE " ${GIT_PREFIX} (add|stage)([[:space:]]|$)" && block " git add/stage modifies the index"
33- echo " $COMMAND " | grep -qE " ${GIT_PREFIX} restore([[:space:]][^;&|]*)?[[:space:]]--staged([[:space:]]|$)" && block " git restore --staged removes files from the index"
34- echo " $COMMAND " | grep -qE " ${GIT_PREFIX} reset([[:space:]]|$)" && block " git reset modifies the index or moves HEAD"
35- echo " $COMMAND " | grep -qE " ${GIT_PREFIX} rm([[:space:]][^;&|]*)?[[:space:]]--cached([[:space:]]|$)" && block " git rm --cached removes files from the index"
36- echo " $COMMAND " | grep -qE " ${GIT_PREFIX} rm([[:space:]]|$)" && block " git rm stages file removals"
37- echo " $COMMAND " | grep -qE " ${GIT_PREFIX} mv([[:space:]]|$)" && block " git mv stages file renames"
38- echo " $COMMAND " | grep -qE " ${GIT_PREFIX} update-index([[:space:]]|$)" && block " git update-index modifies the index"
39+ handle_blocked_operation () {
40+ if [[ " ${NVE_AGENT:- } " == * cloud* ]]; then
41+ warn " $1 "
42+ fi
43+
44+ block " $1 "
45+ }
46+
47+ echo " $COMMAND " | grep -qF " reset --hard" && handle_blocked_operation " git reset --hard discards all uncommitted changes irreversibly"
48+ echo " $COMMAND " | grep -qF " push --force" && handle_blocked_operation " git push --force can overwrite remote history and destroy teammates' work"
49+ echo " $COMMAND " | grep -qF " push -f" && handle_blocked_operation " git push -f can overwrite remote history and destroy teammates' work"
50+ echo " $COMMAND " | grep -qF " clean -f" && handle_blocked_operation " git clean -f permanently deletes untracked files"
51+ echo " $COMMAND " | grep -qF " checkout -- ." && handle_blocked_operation " git checkout -- . discards all unstaged changes irreversibly"
52+ echo " $COMMAND " | grep -qF " branch -D" && handle_blocked_operation " git branch -D force-deletes a branch without merge checks"
53+
54+ echo " $COMMAND " | grep -qE " ${GIT_PREFIX} (add|stage)([[:space:]]|$)" && handle_blocked_operation " git add/stage modifies the index"
55+ echo " $COMMAND " | grep -qE " ${GIT_PREFIX} restore([[:space:]][^;&|]*)?[[:space:]]--staged([[:space:]]|$)" && handle_blocked_operation " git restore --staged removes files from the index"
56+ echo " $COMMAND " | grep -qE " ${GIT_PREFIX} reset([[:space:]]|$)" && handle_blocked_operation " git reset modifies the index or moves HEAD"
57+ echo " $COMMAND " | grep -qE " ${GIT_PREFIX} rm([[:space:]][^;&|]*)?[[:space:]]--cached([[:space:]]|$)" && handle_blocked_operation " git rm --cached removes files from the index"
58+ echo " $COMMAND " | grep -qE " ${GIT_PREFIX} rm([[:space:]]|$)" && handle_blocked_operation " git rm stages file removals"
59+ echo " $COMMAND " | grep -qE " ${GIT_PREFIX} mv([[:space:]]|$)" && handle_blocked_operation " git mv stages file renames"
60+ echo " $COMMAND " | grep -qE " ${GIT_PREFIX} update-index([[:space:]]|$)" && handle_blocked_operation " git update-index modifies the index"
3961
4062exit 0
0 commit comments