🔁 Post-Release Sync #1
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| # This workflow merges release back into main after a successful release run. | |
| # If there are no conflicts, it commits directly and deletes the release branch. | |
| # If there are conflicts, it creates a sync PR for manual resolution. | |
| # Can also be started manually from the Actions tab. | |
| name: 🔁 Post-Release Sync | |
| on: | |
| workflow_dispatch: | |
| workflow_run: | |
| workflows: ["🚀 Release Builder"] | |
| types: [completed] | |
| permissions: | |
| contents: write | |
| pull-requests: write | |
| env: | |
| SOURCE_BRANCH: "release" | |
| TARGET_BRANCH: "main" | |
| RELEASE_GIT_USER_NAME: "thunder-automation-bot" | |
| RELEASE_GIT_USER_EMAIL: "thunder-bot@wso2.com" | |
| jobs: | |
| sync-release-to-main: | |
| name: 🔀 Sync release -> main | |
| if: ${{ github.event_name == 'workflow_dispatch' || github.event.workflow_run.conclusion == 'success' }} | |
| runs-on: ubuntu-latest | |
| steps: | |
| - name: 📥 Checkout Target Branch | |
| uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4 | |
| with: | |
| fetch-depth: 0 | |
| token: ${{ secrets.THUNDER_AUTOMATION_BOT }} | |
| ref: ${{ env.TARGET_BRANCH }} | |
| - name: 🔧 Configure Git | |
| run: | | |
| git config --local user.name "${{ env.RELEASE_GIT_USER_NAME }}" | |
| git config --local user.email "${{ env.RELEASE_GIT_USER_EMAIL }}" | |
| - name: 🔄 Merge Release Branch into Main | |
| id: merge_sync | |
| run: | | |
| set -euo pipefail | |
| git fetch origin "${SOURCE_BRANCH}" "${TARGET_BRANCH}" | |
| git checkout "${TARGET_BRANCH}" | |
| AHEAD=$(git rev-list --count "HEAD..origin/${SOURCE_BRANCH}") | |
| if [ "${AHEAD}" = "0" ]; then | |
| echo "✅ ${TARGET_BRANCH} is already up to date with ${SOURCE_BRANCH}. Nothing to sync." | |
| echo "conflict_detected=false" >> "$GITHUB_OUTPUT" | |
| echo "merged=false" >> "$GITHUB_OUTPUT" | |
| exit 0 | |
| fi | |
| if ! git merge --no-ff --no-edit "origin/${SOURCE_BRANCH}"; then | |
| echo "❌ Merge conflict detected while merging ${SOURCE_BRANCH} into ${TARGET_BRANCH}." | |
| git merge --abort || true | |
| echo "conflict_detected=true" >> "$GITHUB_OUTPUT" | |
| echo "merged=false" >> "$GITHUB_OUTPUT" | |
| exit 0 | |
| fi | |
| git push origin "HEAD:${TARGET_BRANCH}" | |
| echo "✅ Successfully merged ${SOURCE_BRANCH} into ${TARGET_BRANCH}." | |
| echo "conflict_detected=false" >> "$GITHUB_OUTPUT" | |
| echo "merged=true" >> "$GITHUB_OUTPUT" | |
| - name: 🗑️ Delete Release Branch | |
| if: steps.merge_sync.outputs.merged == 'true' | |
| run: | | |
| git push origin --delete "${SOURCE_BRANCH}" | |
| echo "✅ Deleted '${SOURCE_BRANCH}' branch." | |
| - name: 🔔 Create Sync PR for Conflict Resolution | |
| if: steps.merge_sync.outputs.conflict_detected == 'true' | |
| uses: actions/github-script@f28e40c7f34bde8b3046d885e986cb6290c5673b # v7 | |
| with: | |
| script: | | |
| const owner = context.repo.owner; | |
| const repo = context.repo.repo; | |
| const base = process.env.TARGET_BRANCH; | |
| const headBranch = process.env.SOURCE_BRANCH; | |
| const head = `${owner}:${headBranch}`; | |
| const runUrl = `${context.serverUrl}/${owner}/${repo}/actions/runs/${context.runId}`; | |
| const triggerLine = context.eventName === 'workflow_dispatch' | |
| ? `Triggered manually from Actions: ${runUrl}` | |
| : `Triggered after successful release workflow run: ${context.payload.workflow_run.html_url}`; | |
| const existing = await github.rest.pulls.list({ | |
| owner, | |
| repo, | |
| state: 'open', | |
| base, | |
| head | |
| }); | |
| if (existing.data.length > 0) { | |
| const pr = existing.data[0]; | |
| core.info(`Existing sync PR found: #${pr.number} ${pr.html_url}`); | |
| return; | |
| } | |
| const created = await github.rest.pulls.create({ | |
| owner, | |
| repo, | |
| title: `Sync ${headBranch} branch back to ${base}`, | |
| head: headBranch, | |
| base, | |
| body: [ | |
| 'Automated PR created because post-release sync hit merge conflicts.', | |
| '', | |
| `Source branch: ${headBranch}`, | |
| `Target branch: ${base}`, | |
| '', | |
| triggerLine | |
| ].join('\n') | |
| }); | |
| core.info(`Created sync PR: #${created.data.number} ${created.data.html_url}`); | |
| await core.summary | |
| .addHeading('⚠️ Merge Conflict Detected', 3) | |
| .addRaw(`Conflicts were found while merging \`${headBranch}\` into \`${base}\`. A pull request has been opened for manual resolution.`) | |
| .addBreak() | |
| .addRaw(`**PR:** [#${created.data.number} — ${created.data.title}](${created.data.html_url})`) | |
| .write(); |