Files
omarchy-pkgs/.github/scripts/sync-pr-branch.sh
T
Ryan Hughes 4aca3bdbc7 Keep sync PRs building across bot pushes
Three things kept the upstream sync PR (#589) from ever finishing a build:

Scoped dispatches wiped the shared PR. A workflow_dispatch with `packages`
regenerates only those packages from master, and pushing that to
auto/sync-upstream replaced 38 pending updates with one. Scoped runs now
push to their own auto/sync-{upstream,rebuilds}-<packages> branch and PR;
scheduled runs keep the shared branch.

build-approved stopped working after the first bot push. A GITHUB_TOKEN
push creates pull_request runs held for approval but no pull_request_target
run, so approve-pr.yml never saw it: its last run on the branch was the
label itself (2026-09-25T19:26), and each of the next four syncs sat at
action_required. The sync workflows now release the held runs for the
commit they just pushed, from a separate job holding actions: write, and
only for their own bot-authored, same-repo PR while build-approved is on
it.

Each approved push cancelled the in-flight build. Approving the 21:43
sync's build cancelled the label-triggered one still queued on strata and
schist-bin. On auto/sync-* branches a new build now waits for the running
one instead, then reuses its artifacts. The approval script no longer
waits for a lone approved build to start before releasing tests, which a
queued build would have turned into a timeout.
2026-09-26 20:01:17 -04:00

41 lines
1.4 KiB
Bash
Executable File

#!/bin/bash
# Usage: sync-pr-branch.sh BASE_BRANCH [PACKAGE...]
#
# Prints the branch a sync workflow run pushes to, as branch=/scope= lines for
# $GITHUB_OUTPUT. An unscoped (scheduled) run owns BASE_BRANCH and regenerates
# it from master every time. A run scoped to named packages regenerates only
# those, so it gets its own branch and PR: pushing it to BASE_BRANCH would
# replace every other pending update there with just the named packages.
set -euo pipefail
base=${1:?base branch required}
shift
if (( $# == 0 )); then
printf 'branch=%s\nscope=\n' "$base"
exit 0
fi
names=()
for name in "$@"; do
# Package directory names, as pacman allows them. Anything else is a typo
# or an attempt to smuggle something into a ref name or PR title.
if [[ ! $name =~ ^[a-z0-9@_+][a-z0-9@._+-]*$ ]]; then
echo "invalid package name: $name" >&2
exit 1
fi
names+=("$name")
done
mapfile -t names < <(printf '%s\n' "${names[@]}" | sort -u)
scope="${names[*]}"
slug=$(printf '%s\n' "${names[@]}" | sed 's/[^a-z0-9]\{1,\}/-/g; s/^-//; s/-$//' | paste -sd- -)
# Keep long package lists to a readable ref; the hash keeps distinct lists apart.
hash=$(printf '%s' "$scope" | sha256sum | cut -c1-10)
if [[ -z $slug ]]; then
slug=$hash
elif (( ${#slug} > 60 )); then
slug="${slug:0:48}"
slug="${slug%-}-$hash"
fi
printf 'branch=%s-%s\nscope=%s\n' "$base" "$slug" "$scope"