@@ -118,31 +118,75 @@ if [[ -n "$append_file" && ! -f "$append_file" ]]; then
118118 exit 1
119119fi
120120
121- if ! command -v gh > /dev/null 2>&1 ; then
121+ GH_BIN=" ${GH_BIN:- gh} "
122+ if ! command -v " $GH_BIN " > /dev/null 2>&1 ; then
122123 echo " error: gh CLI required" >&2
123124 exit 1
124125fi
125126
126127SCRIPT_DIR=" $( cd " $( dirname " ${BASH_SOURCE[0]} " ) " && pwd) "
127128GRANT_LIB=" $SCRIPT_DIR /pr-body-grant-lib.py"
128129
129- verify_cmd=(python3 " $GRANT_LIB " verify --repo " $repo_slug " --pr " $pr_number " )
130+ grant_append_args=( --repo " $repo_slug " --pr " $pr_number " )
130131if [[ -n " $append_file " ]]; then
131- verify_cmd +=(--file " $append_file " )
132+ grant_append_args +=(--file " $append_file " )
132133else
133- verify_cmd +=(--message " $append_message " )
134+ grant_append_args +=(--message " $append_message " )
134135fi
136+
137+ verify_cmd=(python3 " $GRANT_LIB " verify " ${grant_append_args[@]} " )
135138if ! " ${verify_cmd[@]} " ; then
136139 echo " hint: operator runs grant-pr-body-human-override.sh with the same --file|--message" >&2
137140 exit 1
138141fi
139142
143+ if [[ -z " $title " ]]; then
144+ title=" $( normalize_follow_up_title " Follow-up ($( date -u +%Y-%m-%d) )" ) "
145+ else
146+ title=" $( normalize_follow_up_title " $title " ) "
147+ fi
148+
140149if [[ -n " $append_file " ]]; then
141150 append_block=" $( cat " $append_file " ) "
142151else
143152 append_block=" $append_message "
144153fi
145154
155+ remote_tmp=" $( mktemp) "
156+ out=" $( mktemp) "
157+ grant_finalized=0
158+ release_on_fail () {
159+ if [[ " $grant_finalized " -eq 1 ]]; then
160+ return 0
161+ fi
162+ python3 " $GRANT_LIB " release " ${grant_append_args[@]} " > /dev/null 2>&1 || true
163+ }
164+ trap ' release_on_fail; rm -f "$out" "$remote_tmp"' EXIT
165+
166+ " $GH_BIN " pr view " $pr_number " --repo " $repo_slug " --json body --jq .body > " $remote_tmp "
167+ reconcile_rc=0
168+ reconcile_cmd=(
169+ python3 " $GRANT_LIB " reconcile " ${grant_append_args[@]} "
170+ --title " $title " --remote-body-file " $remote_tmp "
171+ )
172+ reconcile_cmd_output=" $( " ${reconcile_cmd[@]} " 2>&1 ) " || reconcile_rc=$?
173+ if [[ " $reconcile_rc " -eq 0 ]]; then
174+ echo " $reconcile_cmd_output "
175+ grant_finalized=1
176+ echo " updated: https://github.com/${repo_slug} /pull/${pr_number} "
177+ exit 0
178+ fi
179+ if [[ " $reconcile_rc " -ne 2 ]]; then
180+ echo " $reconcile_cmd_output " >&2
181+ exit 1
182+ fi
183+
184+ reserve_cmd=(python3 " $GRANT_LIB " reserve " ${grant_append_args[@]} " )
185+ if ! " ${reserve_cmd[@]} " ; then
186+ echo " hint: operator runs grant-pr-body-human-override.sh with the same --file|--message" >&2
187+ exit 1
188+ fi
189+
146190if [[ " $append_block " == * " $CURSOR_BODY_END " * || " $append_block " == * " $CODERABBIT_MARKER " * ]]; then
147191 echo " error: append content must not contain reserved PR body delimiters" >&2
148192 exit 1
@@ -154,7 +198,7 @@ ts="$(date -u +%Y%m%dT%H%M%SZ)"
154198safe_slug=" ${repo_slug// \/ / -} "
155199backup_path=" $( mktemp " ${backup_dir} /${safe_slug} -pr${pr_number} -${ts} .XXXXXX" ) "
156200
157- current_body=" $( gh pr view " $pr_number " --repo " $repo_slug " --json body --jq .body ) "
201+ current_body=" $( cat " $remote_tmp " ) "
158202printf ' %s\n' " $current_body " > " $backup_path "
159203echo " backup: $backup_path "
160204
@@ -169,12 +213,6 @@ if ((coderabbit_delim_count > 1)); then
169213 exit 1
170214fi
171215
172- if [[ -z " $title " ]]; then
173- title=" $( normalize_follow_up_title " Follow-up ($( date -u +%Y-%m-%d) )" ) "
174- else
175- title=" $( normalize_follow_up_title " $title " ) "
176- fi
177-
178216follow_up=$(
179217 cat << EOF
180218
@@ -196,27 +234,30 @@ else
196234 merged=" ${merged}${follow_up} "
197235fi
198236
199- remote_body=" $( gh pr view " $pr_number " --repo " $repo_slug " --json body --jq .body) "
237+ remote_body=" $( " $GH_BIN " pr view " $pr_number " --repo " $repo_slug " --json body --jq .body) "
200238if [[ " $remote_body " != " $current_body " ]]; then
201239 echo " error: PR body changed since initial read; aborting to avoid overwrite" >&2
202240 echo " hint: review concurrent edits and re-run append-pr-body.sh" >&2
203241 exit 1
204242fi
205243
206- out=" $( mktemp) "
207- trap ' rm -f "$out"' EXIT
208244printf ' %s\n' " $merged " > " $out "
209- gh pr edit " $pr_number " --repo " $repo_slug " --body-file " $out "
245+ if ! " $GH_BIN " pr edit " $pr_number " --repo " $repo_slug " --body-file " $out " ; then
246+ echo " error: gh pr edit failed" >&2
247+ exit 1
248+ fi
210249
211- consume_cmd=(python3 " $GRANT_LIB " consume --repo " $repo_slug " --pr " $pr_number " )
212- if [[ -n " $append_file " ]]; then
213- consume_cmd+=(--file " $append_file " )
214- else
215- consume_cmd+=(--message " $append_message " )
250+ mark_cmd=(python3 " $GRANT_LIB " mark-applied " ${grant_append_args[@]} " )
251+ if ! " ${mark_cmd[@]} " ; then
252+ echo " error: grant mark-applied failed after PR body update — treat as security incident" >&2
253+ exit 1
216254fi
255+
256+ consume_cmd=(python3 " $GRANT_LIB " consume " ${grant_append_args[@]} " )
217257if ! " ${consume_cmd[@]} " ; then
218258 echo " error: grant consume failed after PR body update — treat as security incident" >&2
219259 exit 1
220260fi
221261
262+ grant_finalized=1
222263echo " updated: https://github.com/${repo_slug} /pull/${pr_number} "
0 commit comments