ci(sync): auto-resolve recurring upstream conflicts, fix workflow restore
The weekly upstream sync hard-failed whenever upstream touched files the fork diverges on (README branding) or removed a now-generated file (tests/operations/index.mjs). It also had a latent bug: the workflow restore ran 'git checkout HEAD -- .github/workflows/' *after* the merge had already auto-committed, so HEAD was the merge commit and the restore was a no-op. - Merge with --no-commit so HEAD stays the pre-merge fork commit, making the workflow restore actually keep the fork's workflows. - Auto-resolve the two recurring conflicts: keep the fork's README, and honour upstream deletions of generated/gitignored files. - Fail loudly (and abort the merge) on any other, unexpected conflict instead of pushing a half-resolved tree. - Exit cleanly when already up to date. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
6e85321409
commit
1045fcc3c5
48
.github/workflows/sync_upstream.yml
vendored
48
.github/workflows/sync_upstream.yml
vendored
@ -15,11 +15,55 @@ jobs:
|
|||||||
|
|
||||||
- name: Sync upstream
|
- name: Sync upstream
|
||||||
run: |
|
run: |
|
||||||
|
set -eo pipefail
|
||||||
git config user.email "github-actions[bot]@users.noreply.github.com"
|
git config user.email "github-actions[bot]@users.noreply.github.com"
|
||||||
git config user.name "github-actions[bot]"
|
git config user.name "github-actions[bot]"
|
||||||
git remote add upstream https://github.com/gchq/CyberChef.git
|
git remote add upstream https://github.com/gchq/CyberChef.git
|
||||||
git fetch upstream
|
git fetch upstream
|
||||||
git merge upstream/master
|
|
||||||
|
# Merge without committing so we can post-process the result before
|
||||||
|
# creating a single merge commit:
|
||||||
|
# - auto-resolve the conflicts this fork hits every week,
|
||||||
|
# - keep the fork's own workflow files (HEAD stays the pre-merge
|
||||||
|
# fork commit while --no-commit is in effect).
|
||||||
|
git merge --no-commit --no-ff upstream/master || true
|
||||||
|
|
||||||
|
if ! git rev-parse -q --verify MERGE_HEAD >/dev/null; then
|
||||||
|
echo "Already up to date with upstream."
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Resolve known, recurring conflicts; bail out loudly on anything
|
||||||
|
# unexpected so we never push a half-resolved tree to master.
|
||||||
|
unresolved=""
|
||||||
|
for f in $(git diff --name-only --diff-filter=U); do
|
||||||
|
if [ "$f" = "README.md" ]; then
|
||||||
|
# The fork's README intentionally diverges (jacobmarks.com
|
||||||
|
# branding + extra demo links); keep our version.
|
||||||
|
git checkout --ours -- "$f"
|
||||||
|
git add -- "$f"
|
||||||
|
echo "Resolved $f -> kept fork version"
|
||||||
|
elif ! git cat-file -e "upstream/master:$f" 2>/dev/null \
|
||||||
|
&& git check-ignore -q --no-index "$f"; then
|
||||||
|
# Generated/gitignored file that upstream has deleted (e.g.
|
||||||
|
# tests/operations/index.mjs is now produced by grunt
|
||||||
|
# configTests); honour the deletion.
|
||||||
|
git rm -q -- "$f"
|
||||||
|
echo "Resolved $f -> honoured upstream deletion (generated file)"
|
||||||
|
else
|
||||||
|
unresolved="$unresolved $f"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
|
if [ -n "$unresolved" ]; then
|
||||||
|
echo "::error::Unresolved merge conflicts need manual resolution:$unresolved"
|
||||||
|
git merge --abort
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Keep the fork's own workflow files instead of adopting upstream's.
|
||||||
git checkout HEAD -- .github/workflows/
|
git checkout HEAD -- .github/workflows/
|
||||||
git commit --amend --no-edit
|
git add -A .github/workflows/
|
||||||
|
|
||||||
|
git commit --no-edit
|
||||||
git push origin master
|
git push origin master
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user