forked from bchanot/claude
feat(gitflow): push-mode verb; /close reports the push state instead of pushing
Run C1 of manual-push mode (BDR-111/BDR-112).
- lib/gitflow.sh: `gitflow.sh push-mode` prints auto | manual | invalid
(rc 0; an invalid value is named on stderr). It is the one reader a
skill may call: the bare `git config … gitflow.*` read is denied to
Claude since run B. Ignores GITFLOW_NO_PUSH by design (documented).
- skills/capitalize/SKILL.md STEP 5C: the explicit `git push origin
develop` is gone — `finish` has pushed develop itself since BDR-095,
mode-aware since run A. 5C is now three separate read-only calls
(finish; push-mode; `git rev-list --count origin/develop..develop`)
and prose outcomes keyed on the real ahead count: pushed / manual push
mode, you push / not on origin / push FAILED / invalid value named,
plus a finish-failure outcome (merge vs delete rc distinguished).
STEP 6 closing lines and the recap carry every outcome; the
`--no-push` line reads the branch's own ahead count ("this disk only"
only when true). Invariant: no `git push` inside any Bash call; the
user hints are prose.
- skills/close/SKILL.md, lib/gitflow-aiguillage.md: "push" claims
qualified "in auto-push mode".
- lib/gitflow-test.sh T11b: six cases for the verb (default, true,
false, non-boolean with stderr + rc 0, corrupt config, usage).
Polish items from the gates are listed in TODO.md (C1 polish).
This commit is contained in:
@@ -37,8 +37,8 @@ exemption still lets a *manual* memory commit through on a protected base, but a
|
||||
skill-driven one now branches to `chore/*` first.
|
||||
|
||||
**Integration is human-gated by default** — these flows commit, they do not merge.
|
||||
EXCEPTION: `/capitalize` + `/close` auto-persist their memory-only commit (finish →
|
||||
develop + push) when THEY branched a `chore/*` off develop this run (BDR-068 — a
|
||||
EXCEPTION: `/capitalize` + `/close` auto-persist their memory-only commit (finish → develop; the lib pushes develop in auto-push mode only)
|
||||
when THEY branched a `chore/*` off develop this run (BDR-068 — a
|
||||
scoped [[LRN-069]] exception; see the capitalize skill's STEP 5C). `/prune-memory`
|
||||
+ `/reconcile` stay fully human-gated: never run `gitflow finish` from them.
|
||||
|
||||
|
||||
@@ -172,6 +172,22 @@ if bash "$HERE/gitflow.sh" protected-base main; then ok "cli protected-bas
|
||||
if bash "$HERE/gitflow.sh" protected-base feature/x; then no "cli protected-base feature (rc0?)"; else ok "cli protected-base feature → rc1"; fi
|
||||
chk "cli base-for hotfix=main" '[ "$(bash "$HERE/gitflow.sh" base-for hotfix)" = main ]'
|
||||
|
||||
echo "T11b — push-mode verb (the sanctioned reader for skills, BDR-112)"
|
||||
newrepo pm; echo a>a
|
||||
bash "$HERE/gitflow.sh" init >/dev/null 2>&1
|
||||
chk "cli push-mode default auto" '[ "$(bash "$HERE/gitflow.sh" push-mode)" = auto ]'
|
||||
git config gitflow.autopush true
|
||||
chk "cli push-mode true auto" '[ "$(bash "$HERE/gitflow.sh" push-mode)" = auto ]'
|
||||
git config gitflow.autopush false
|
||||
chk "cli push-mode manual" '[ "$(bash "$HERE/gitflow.sh" push-mode)" = manual ]'
|
||||
git config gitflow.autopush flase
|
||||
pm_out=$(bash "$HERE/gitflow.sh" push-mode 2>"$WORK/pm.err"); pm_rc=$?
|
||||
chk "cli push-mode invalid, rc 0, value on stderr" "[ $pm_rc -eq 0 ] && [ \"$pm_out\" = invalid ] && grep -q flase \"$WORK/pm.err\""
|
||||
printf '[gitflow\n' >> .git/config
|
||||
pm2_out=$(bash "$HERE/gitflow.sh" push-mode 2>/dev/null); pm2_rc=$?
|
||||
chk "cli push-mode corrupt config → invalid, rc 0" "[ $pm2_rc -eq 0 ] && [ \"$pm2_out\" = invalid ]"
|
||||
chk "cli usage lists push-mode" 'grep -q push-mode <<<"$(bash "$HERE/gitflow.sh" nope 2>&1)"'
|
||||
|
||||
echo "T12 — finish arg-guard (named branch must equal current, else refuse)"
|
||||
newrepo finargs; echo a>a; hookon; gitflow_init >/dev/null 2>&1
|
||||
gitflow_start feature standon >/dev/null 2>&1; echo w>w.txt; git add w.txt; git commit -q -m w
|
||||
|
||||
+28
-1
@@ -68,6 +68,32 @@ gitflow_release_open() {
|
||||
[ -n "$(git for-each-ref --format='%(refname:short)' 'refs/heads/release/*')" ]
|
||||
}
|
||||
|
||||
# gitflow_push_mode -> stdout auto | manual | invalid, rc 0 always. The ONE
|
||||
# reader skills may call: `git config ... gitflow.*` is statically denied to
|
||||
# Claude (BDR-112). manual = key reads false; auto = true or unset; invalid =
|
||||
# anything else (unparseable value, git failure); the raw value goes to
|
||||
# stderr so the caller can name it. Reads only. Ignores GITFLOW_NO_PUSH (a
|
||||
# test-repo switch, not a mode): a caller that pushes must not rely on this
|
||||
# verb alone, the lib's own push sites use _gitflow_push_off.
|
||||
gitflow_push_mode() {
|
||||
local val rc raw
|
||||
val=$(git config --bool gitflow.autopush 2>/dev/null); rc=$?
|
||||
case "$rc:$val" in
|
||||
0:false) echo manual ;;
|
||||
0:true|1:*) echo auto ;;
|
||||
*) raw=$(git config gitflow.autopush 2>/dev/null)
|
||||
if [ -n "$raw" ]; then
|
||||
echo "gitflow.sh push-mode: gitflow.autopush='$raw'" \
|
||||
"is not a boolean (git rc $rc)" >&2
|
||||
else
|
||||
echo "gitflow.sh push-mode: could not read" \
|
||||
"gitflow.autopush (git rc $rc)" >&2
|
||||
fi
|
||||
echo invalid ;;
|
||||
esac
|
||||
return 0
|
||||
}
|
||||
|
||||
# ── start ────────────────────────────────────────────────────────────────────
|
||||
|
||||
# rc 0 when pushing is off: GITFLOW_NO_PUSH=1 (throwaway test repos) or
|
||||
@@ -597,6 +623,7 @@ if [ "${BASH_SOURCE[0]}" = "${0}" ]; then
|
||||
delete) gitflow_delete "$@" ;;
|
||||
merged) [ -n "${1:-}" ] || { echo "usage: gitflow.sh merged <branch>" >&2; exit 2; }
|
||||
gitflow_merged_into_base "$1" ;;
|
||||
push-mode) gitflow_push_mode ;;
|
||||
hooks) printf '%s\n' "${GITFLOW_HOOKS[@]}" ;;
|
||||
init) gitflow_init "$@" ;;
|
||||
reconcile) gitflow_reconcile_gitignore "$@" ;;
|
||||
@@ -606,6 +633,6 @@ if [ "${BASH_SOURCE[0]}" = "${0}" ]; then
|
||||
global-hooks) gitflow_global_hooks "$@" ;;
|
||||
emit-hook) _gitflow_emit_hook "${1:-pre-commit}" \
|
||||
|| { echo "gitflow.sh emit-hook {$(IFS='|'; echo "${GITFLOW_HOOKS[*]}")}" >&2; exit 2; } ;;
|
||||
*) echo "usage: gitflow.sh {type|protected-base|base-for|release-open|start|finish|delete <br>|merged <br>|init|reconcile|purge-transient|install-hook|reconcile-hooks|global-hooks <dir> [value]|hooks|emit-hook <name>}" >&2; exit 2 ;;
|
||||
*) echo "usage: gitflow.sh {type|protected-base|base-for|release-open|start|finish|delete <br>|merged <br>|push-mode|init|reconcile|purge-transient|install-hook|reconcile-hooks|global-hooks <dir> [value]|hooks|emit-hook <name>}" >&2; exit 2 ;;
|
||||
esac
|
||||
fi
|
||||
|
||||
Reference in New Issue
Block a user