From 0d9f754dd5d4577cf3197ee9eb6675dab28450ce Mon Sep 17 00:00:00 2001 From: Alexey Alter-Pesotskiy Date: Wed, 31 Jul 2024 17:48:32 +0100 Subject: [PATCH 1/6] [CI] Automate the merge of the release branches --- .github/workflows/release-merge.yml | 30 +++++++++++++++ ...ublish-release.yml => release-publish.yml} | 4 ++ ...tart-new-release.yml => release-start.yml} | 0 fastlane/Fastfile | 38 ++++++++++++------- 4 files changed, 59 insertions(+), 13 deletions(-) create mode 100644 .github/workflows/release-merge.yml rename .github/workflows/{publish-release.yml => release-publish.yml} (99%) rename .github/workflows/{start-new-release.yml => release-start.yml} (100%) diff --git a/.github/workflows/release-merge.yml b/.github/workflows/release-merge.yml new file mode 100644 index 0000000000..55c962d032 --- /dev/null +++ b/.github/workflows/release-merge.yml @@ -0,0 +1,30 @@ +name: "Merge release" + +on: + issue_comment: + types: [created] + + workflow_dispatch: + +jobs: + merge-comment: + name: Merge release to main + runs-on: macos-14 + if: github.event.issue.pull_request && github.event.comment.body == '/merge' && github.event.issue.state == 'open' + steps: + - name: Connect iOS Bot + uses: webfactory/ssh-agent@v0.7.0 + with: + ssh-private-key: ${{ secrets.BOT_SSH_PRIVATE_KEY }} + + - uses: actions/checkout@v4.1.1 + with: + fetch-depth: 0 + + - uses: ./.github/actions/ruby-cache + + - name: Create Release PR + run: bundle exec fastlane merge_release_to_main --verbose + env: + GITHUB_TOKEN: ${{ secrets.DANGER_GITHUB_API_TOKEN }} + GITHUB_PR_NUM: ${{ github.event.issue.number }} diff --git a/.github/workflows/publish-release.yml b/.github/workflows/release-publish.yml similarity index 99% rename from .github/workflows/publish-release.yml rename to .github/workflows/release-publish.yml index 3252341897..d1ec19d3ec 100644 --- a/.github/workflows/publish-release.yml +++ b/.github/workflows/release-publish.yml @@ -17,14 +17,18 @@ jobs: uses: webfactory/ssh-agent@v0.7.0 with: ssh-private-key: ${{ secrets.BOT_SSH_PRIVATE_KEY }} + - uses: actions/checkout@v4.1.1 + - name: Extract version from branch name (for release branches) if: startsWith(github.event.pull_request.head.ref, 'release/') run: | BRANCH_NAME="${{ github.event.pull_request.head.ref }}" VERSION=${BRANCH_NAME#release/} echo "RELEASE_VERSION=$VERSION" >> $GITHUB_ENV + - uses: ./.github/actions/ruby-cache + - name: "Fastlane - Publish Release" if: startsWith(github.event.pull_request.head.ref, 'release/') env: diff --git a/.github/workflows/start-new-release.yml b/.github/workflows/release-start.yml similarity index 100% rename from .github/workflows/start-new-release.yml rename to .github/workflows/release-start.yml diff --git a/fastlane/Fastfile b/fastlane/Fastfile index ce82c9279c..02eb59f347 100644 --- a/fastlane/Fastfile +++ b/fastlane/Fastfile @@ -115,24 +115,36 @@ lane :publish_release do |options| end lane :merge_release_to_main do - ensure_git_status_clean - sh('git checkout main') - sh('git pull') + release_branch = + if is_ci + sh('git config --global user.name "Stream Bot"') + sh('git reset --hard') + current_branch + else + ensure_git_status_clean + release_branches = sh(command: 'git branch -a', log: false).delete(' ').split("\n").grep(%r(origin/.*release/)) + UI.user_error!("Expected 1 release branch, found #{release_branches.size}") if release_branches.size != 1 + release_branches.first + end + + UI.user_error!("`#{release_branch}`` branch does not match the release branch pattern: `release/*`") unless release_branch.start_with?('release/') - # Grep all remote release branches and ensure there's only one - release_branches = sh(command: 'git branch -a', log: false).delete(' ').split("\n").grep(%r(origin/.*release/)) - UI.user_error!("Expected 1 release branch, found #{release_branches.size}") if release_branches.size != 1 + sh('git checkout origin/main') + sh('git pull origin main') # Merge release branch to main. For more info, read: https://notion.so/iOS-Branching-Strategy-37c10127dc26493e937769d44b1d6d9a - sh("git merge #{release_branches.first} --ff-only") - UI.user_error!('Not pushing changes') unless prompt(text: 'Will push changes. All looking good?', boolean: true) - sh('git push') - UI.important('Please, wait for the `Publish new release` workflow to pass on GitHub Actions: ' \ - "https://github.com/#{github_repo}/actions/workflows/publish-release.yml") + sh("git merge #{release_branch} --ff-only") + sh('git push origin main') + + comment = 'Please, wait for the `Publish new release` workflow to pass on GitHub Actions: ' \ + "https://github.com/#{github_repo}/actions/workflows/release-publish.yml" + UI.important(comment) + create_pr_comment(pr_num: ENV.fetch('GITHUB_PR_NUM'), text: comment, edit_last_comment_with_text: comment) end lane :merge_main_to_develop do if is_ci + sh('git config --global user.name "Stream Bot"') sh('git reset --hard') else ensure_git_status_clean @@ -140,11 +152,11 @@ lane :merge_main_to_develop do sh('git checkout main') sh('git pull origin main') - sh('git checkout develop') + sh('git checkout origin/develop') sh('git pull origin develop') sh('git log develop..main') sh('git merge main') - sh('git push') + sh('git push origin develop') end desc 'Compresses the XCFrameworks into zip files' From 715b3141240c29a687a598c8347a0a80dee3ed65 Mon Sep 17 00:00:00 2001 From: Alexey Alter-Pesotskiy Date: Thu, 1 Aug 2024 09:30:05 +0100 Subject: [PATCH 2/6] Make it more strict to be able to merge the release --- .github/workflows/release-merge.yml | 2 +- fastlane/Fastfile | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/release-merge.yml b/.github/workflows/release-merge.yml index 55c962d032..a6615dc391 100644 --- a/.github/workflows/release-merge.yml +++ b/.github/workflows/release-merge.yml @@ -10,7 +10,7 @@ jobs: merge-comment: name: Merge release to main runs-on: macos-14 - if: github.event.issue.pull_request && github.event.comment.body == '/merge' && github.event.issue.state == 'open' + if: github.event.issue.pull_request && github.event.comment.body == '/merge' && github.event.issue.state == 'open' && endsWith(github.event.issue.title, 'Release') steps: - name: Connect iOS Bot uses: webfactory/ssh-agent@v0.7.0 diff --git a/fastlane/Fastfile b/fastlane/Fastfile index 02eb59f347..054f235cd1 100644 --- a/fastlane/Fastfile +++ b/fastlane/Fastfile @@ -139,7 +139,7 @@ lane :merge_release_to_main do comment = 'Please, wait for the `Publish new release` workflow to pass on GitHub Actions: ' \ "https://github.com/#{github_repo}/actions/workflows/release-publish.yml" UI.important(comment) - create_pr_comment(pr_num: ENV.fetch('GITHUB_PR_NUM'), text: comment, edit_last_comment_with_text: comment) + create_pr_comment(pr_num: ENV.fetch('GITHUB_PR_NUM'), text: comment) end lane :merge_main_to_develop do @@ -951,7 +951,7 @@ end private_lane :create_pr_comment do |options| if is_ci && !options[:pr_num].to_s.empty? last_comment = sh("gh pr view #{options[:pr_num]} --json comments --jq '.comments | map(select(.author.login == \"Stream-iOS-Bot\")) | last'") - edit_last_comment = last_comment.include?(options[:edit_last_comment_with_text]) ? '--edit-last' : '' + edit_last_comment = options[:edit_last_comment_with_text] && last_comment.include?(options[:edit_last_comment_with_text]) ? '--edit-last' : '' sh("gh pr comment #{options[:pr_num]} #{edit_last_comment} -b '#{options[:text]}'") end end From be3e37216a89a4482407de6423a6b4deea5c40ab Mon Sep 17 00:00:00 2001 From: Alexey Alter-Pesotskiy Date: Thu, 1 Aug 2024 10:13:45 +0100 Subject: [PATCH 3/6] Update comment --- .github/workflows/release-merge.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/release-merge.yml b/.github/workflows/release-merge.yml index a6615dc391..9e7d19af53 100644 --- a/.github/workflows/release-merge.yml +++ b/.github/workflows/release-merge.yml @@ -10,7 +10,7 @@ jobs: merge-comment: name: Merge release to main runs-on: macos-14 - if: github.event.issue.pull_request && github.event.comment.body == '/merge' && github.event.issue.state == 'open' && endsWith(github.event.issue.title, 'Release') + if: github.event.issue.pull_request && github.event.comment.body == '/merge release' && github.event.issue.state == 'open' steps: - name: Connect iOS Bot uses: webfactory/ssh-agent@v0.7.0 From af50b9363a4073feafa3b826e773292346082278 Mon Sep 17 00:00:00 2001 From: Alexey Alter-Pesotskiy Date: Thu, 1 Aug 2024 11:30:51 +0100 Subject: [PATCH 4/6] Check comment author --- .github/workflows/release-merge.yml | 4 ++-- fastlane/Fastfile | 9 ++++++--- 2 files changed, 8 insertions(+), 5 deletions(-) diff --git a/.github/workflows/release-merge.yml b/.github/workflows/release-merge.yml index 9e7d19af53..1f073f3afe 100644 --- a/.github/workflows/release-merge.yml +++ b/.github/workflows/release-merge.yml @@ -10,7 +10,7 @@ jobs: merge-comment: name: Merge release to main runs-on: macos-14 - if: github.event.issue.pull_request && github.event.comment.body == '/merge release' && github.event.issue.state == 'open' + if: github.event.issue.pull_request && github.event.issue.state == 'open' && github.event.comment.body == '/merge release' steps: - name: Connect iOS Bot uses: webfactory/ssh-agent@v0.7.0 @@ -24,7 +24,7 @@ jobs: - uses: ./.github/actions/ruby-cache - name: Create Release PR - run: bundle exec fastlane merge_release_to_main --verbose + run: bundle exec fastlane merge_release_to_main author:"${{ github.event.comment.user.login }}" --verbose env: GITHUB_TOKEN: ${{ secrets.DANGER_GITHUB_API_TOKEN }} GITHUB_PR_NUM: ${{ github.event.issue.number }} diff --git a/fastlane/Fastfile b/fastlane/Fastfile index 054f235cd1..f87c254224 100644 --- a/fastlane/Fastfile +++ b/fastlane/Fastfile @@ -114,16 +114,20 @@ lane :publish_release do |options| merge_main_to_develop end -lane :merge_release_to_main do +lane :merge_release_to_main do |options| release_branch = if is_ci sh('git config --global user.name "Stream Bot"') sh('git reset --hard') + ios_team = sh('gh api "orgs/GetStream/teams/ios-developers/members" --jq ".[].login"', log: false).split + UI.user_error!("#{options[:author]} is not a member of the iOS Team") unless ios_team.include?(options[:author]) + current_branch else ensure_git_status_clean release_branches = sh(command: 'git branch -a', log: false).delete(' ').split("\n").grep(%r(origin/.*release/)) UI.user_error!("Expected 1 release branch, found #{release_branches.size}") if release_branches.size != 1 + release_branches.first end @@ -136,8 +140,7 @@ lane :merge_release_to_main do sh("git merge #{release_branch} --ff-only") sh('git push origin main') - comment = 'Please, wait for the `Publish new release` workflow to pass on GitHub Actions: ' \ - "https://github.com/#{github_repo}/actions/workflows/release-publish.yml" + comment = "[Publication of the release](https://github.com/#{github_repo}/actions/workflows/release-publish.yml) has been launched 👍" UI.important(comment) create_pr_comment(pr_num: ENV.fetch('GITHUB_PR_NUM'), text: comment) end From a4f5e5e1a83e00d20304a2f0ef68fc9fa70e5925 Mon Sep 17 00:00:00 2001 From: Alexey Alter-Pesotskiy Date: Thu, 1 Aug 2024 11:34:38 +0100 Subject: [PATCH 5/6] Remove workflow dispatch --- .github/workflows/release-merge.yml | 2 -- 1 file changed, 2 deletions(-) diff --git a/.github/workflows/release-merge.yml b/.github/workflows/release-merge.yml index 1f073f3afe..fd7ec767de 100644 --- a/.github/workflows/release-merge.yml +++ b/.github/workflows/release-merge.yml @@ -4,8 +4,6 @@ on: issue_comment: types: [created] - workflow_dispatch: - jobs: merge-comment: name: Merge release to main From 36fae41e61b1dc24f5b119b8d2d57723061f55f8 Mon Sep 17 00:00:00 2001 From: Alexey Alter-Pesotskiy Date: Thu, 1 Aug 2024 12:06:55 +0100 Subject: [PATCH 6/6] Rename step --- .github/workflows/release-merge.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/release-merge.yml b/.github/workflows/release-merge.yml index fd7ec767de..f1c62abe0f 100644 --- a/.github/workflows/release-merge.yml +++ b/.github/workflows/release-merge.yml @@ -21,7 +21,7 @@ jobs: - uses: ./.github/actions/ruby-cache - - name: Create Release PR + - name: Merge run: bundle exec fastlane merge_release_to_main author:"${{ github.event.comment.user.login }}" --verbose env: GITHUB_TOKEN: ${{ secrets.DANGER_GITHUB_API_TOKEN }}