11name : Publish gem
22
33# TODO: Implement a dry-run mode to verify the checks without publishing
4- on : workflow_dispatch # yamllint disable-line rule:truthy
4+ on : # yamllint disable-line rule:truthy
5+ workflow_dispatch :
6+ inputs :
7+ force :
8+ description : ' Force release bypassing verification checks'
9+ type : boolean
10+ default : false
11+ required : false
512
613concurrency : " rubygems" # Only one publish job at a time
714
1421 runs-on : ubuntu-24.04
1522 permissions :
1623 checks : read
24+ contents : read
1725 outputs :
1826 version : ${{ steps.version.outputs.version }}
1927 steps :
2937
3038 # Check if the gem version is already published
3139 - name : Verify gem version
40+ if : ${{ !inputs.force }}
3241 env :
3342 GEM_VERSION : ${{ steps.version.outputs.version }}
3443 run : |
@@ -39,12 +48,67 @@ jobs:
3948 echo "Version $GEM_VERSION is not published yet"
4049 fi
4150
42- # TODO: Verify draft release
43- # TODO: Verify milestone
51+ # Check if there is a draft release for this version
52+ # API: https://docs.github.com/en/rest/releases/releases?apiVersion=2022-11-28#list-releases
53+ - name : Verify draft release
54+ if : ${{ !inputs.force }}
55+ continue-on-error : true # TODO: Remove when figuring out why draft release are not returned from API
56+ env :
57+ GEM_VERSION : ${{ steps.version.outputs.version }}
58+ uses : actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1
59+ with :
60+ script : |
61+ const { data: releases } = await github.rest.repos.listReleases({
62+ owner: context.repo.owner,
63+ repo: context.repo.repo,
64+ });
65+
66+ console.log(releases);
67+
68+ const versionTag = `v${process.env.GEM_VERSION}`;
69+ const draftRelease = releases.find(
70+ release => release.tag_name === versionTag && release.draft === true
71+ );
72+
73+ if (!draftRelease) {
74+ core.setFailed(`No draft release found with tag ${versionTag}. Please create a draft release first.`);
75+ return;
76+ }
77+
78+ console.log(`Found draft release with tag ${versionTag} (ID: ${draftRelease.id})`);
79+
80+ # Check if there is an open milestone for this version
81+ # API: https://docs.github.com/en/rest/issues/milestones?apiVersion=2022-11-28#list-milestones
82+ - name : Verify milestone
83+ if : ${{ !inputs.force }}
84+ env :
85+ GEM_VERSION : ${{ steps.version.outputs.version }}
86+ uses : actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1
87+ with :
88+ script : |
89+ const { data: milestones } = await github.rest.issues.listMilestones({
90+ owner: context.repo.owner,
91+ repo: context.repo.repo,
92+ state: 'open'
93+ });
94+
95+ console.log(milestones);
96+
97+ const versionMilestone = milestones.find(
98+ milestone => milestone.title === process.env.GEM_VERSION
99+ );
100+
101+ if (!versionMilestone) {
102+ core.setFailed(`No open milestone found with title ${process.env.GEM_VERSION}. Please create a milestone first.`);
103+ return;
104+ }
105+
106+ console.log(`Found open milestone ${process.env.GEM_VERSION} (ID: ${versionMilestone.number})`);
44107
45108 # Check if the commit has passed all Github checks
46109 # API: https://docs.github.com/en/rest/checks/runs?apiVersion=2022-11-28#list-check-runs-for-a-git-reference
47110 - name : Verify check runs
111+ if : ${{ !inputs.force }}
48112 uses : actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1
49113 with :
50114 script : |
69133 # Check if the commit has passed external CI checks
70134 # API: https://docs.github.com/en/rest/commits/statuses?apiVersion=2022-11-28#get-the-combined-status-for-a-specific-reference
71135 - name : Verify commit status
136+ if : ${{ !inputs.force }}
72137 uses : actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1
73138 with :
74139 script : |
84149
85150 # Check if the commit has all the checks passed
86151 - name : Verify deferred commit data
152+ if : ${{ !inputs.force }}
87153 # NOTE:
88154 #
89155 # This step uses Github's internal API (for rendering the status of the checks in UI),
@@ -100,7 +166,10 @@ jobs:
100166 echo "::error::Status check state is '$STATUS'. See: $COMMIT_URL"
101167 exit 1
102168 fi
103-
169+ - name : Warning for bypassing checks
170+ if : ${{ inputs.force }}
171+ run : |
172+ echo "::warning::Bypassing verification checks"
104173
105174 rubygems-release :
106175 name : Build and push gem to RubyGems.org
0 commit comments