@@ -73,24 +73,59 @@ jobs:
7373 echo "ℹ️ Tag ${TAG} does not exist yet"
7474 fi
7575
76+ - name : Tag - Validate existing tag versions
77+ id : validate-existing
78+ if : steps.check-tag.outputs.tag_exists == 'true'
79+ run : |
80+ TAG="${{ steps.version.outputs.version }}"
81+ RELEASE_NAME="${{ steps.version.outputs.release_name }}"
82+ echo "Validating versions on existing tag ${TAG}..."
83+ git checkout "refs/tags/${TAG}" --quiet
84+ chmod +x ./scripts/update-release-version.sh
85+ if ./scripts/update-release-version.sh --check "${RELEASE_NAME}"; then
86+ echo "✅ Existing tag ${TAG} has correct versions"
87+ echo "versions_valid=true" >> $GITHUB_OUTPUT
88+ else
89+ echo ""
90+ echo "⚠️ Existing tag ${TAG} has incorrect versions — will delete and recreate"
91+ git checkout - --quiet
92+ git tag -d "${TAG}" 2>/dev/null || true
93+ git push origin --delete "${TAG}" 2>/dev/null || true
94+ echo "versions_valid=false" >> $GITHUB_OUTPUT
95+ fi
96+
97+ - name : Tag - Determine if tag creation is needed
98+ id : needs-creation
99+ run : |
100+ if [ "${{ steps.check-tag.outputs.tag_exists }}" != "true" ]; then
101+ echo "needed=true" >> $GITHUB_OUTPUT
102+ echo "ℹ️ Tag does not exist — creation needed"
103+ elif [ "${{ steps.validate-existing.outputs.versions_valid }}" != "true" ]; then
104+ echo "needed=true" >> $GITHUB_OUTPUT
105+ echo "ℹ️ Existing tag had wrong versions — recreation needed"
106+ else
107+ echo "needed=false" >> $GITHUB_OUTPUT
108+ echo "ℹ️ Existing tag is valid — no creation needed"
109+ fi
110+
76111 - name : Tag - Update release version
77- if : steps.check-tag .outputs.tag_exists ! = 'true'
112+ if : steps.needs-creation .outputs.needed = = 'true'
78113 run : |
79114 TAG_VERSION="${{ steps.version.outputs.release_name }}"
80115 echo "Updating all version-bearing files to '${TAG_VERSION}'..."
81116 chmod +x ./scripts/update-release-version.sh
82117 ./scripts/update-release-version.sh "${TAG_VERSION}"
83118
84119 - name : Tag - Install QLT
85- if : steps.check-tag .outputs.tag_exists ! = 'true'
120+ if : steps.needs-creation .outputs.needed = = 'true'
86121 id : install-qlt
87122 uses : advanced-security/codeql-development-toolkit/.github/actions/install-qlt@main
88123 with :
89124 qlt-version : ' latest'
90125 add-to-path : true
91126
92127 - name : Tag - Install CodeQL
93- if : steps.check-tag .outputs.tag_exists ! = 'true'
128+ if : steps.needs-creation .outputs.needed = = 'true'
94129 shell : bash
95130 run : |
96131 echo "Installing CodeQL"
@@ -100,7 +135,7 @@ jobs:
100135 echo "CodeQL Binary: $QLT_CODEQL_PATH"
101136
102137 - name : Tag - Upgrade CodeQL pack lock files
103- if : steps.check-tag .outputs.tag_exists ! = 'true'
138+ if : steps.needs-creation .outputs.needed = = 'true'
104139 shell : bash
105140 run : |
106141 echo "Upgrading CodeQL pack lock files"
@@ -114,29 +149,29 @@ jobs:
114149 echo "Finished upgrading all CodeQL pack lock files"
115150
116151 - name : Tag - Install QL packs
117- if : steps.check-tag .outputs.tag_exists ! = 'true'
152+ if : steps.needs-creation .outputs.needed = = 'true'
118153 shell : bash
119154 run : |
120155 export PATH="$(dirname "$QLT_CODEQL_PATH"):$PATH"
121156 chmod +x ./scripts/install-packs.sh
122157 ./scripts/install-packs.sh
123158
124159 - name : Tag - Setup Node.js for CDS compilation
125- if : steps.check-tag .outputs.tag_exists ! = 'true'
160+ if : steps.needs-creation .outputs.needed = = 'true'
126161 uses : actions/setup-node@v6
127162 with :
128163 node-version : ' 20'
129164 cache : ' npm'
130165 cache-dependency-path : ' extractors/cds/tools/package-lock.json'
131166
132167 - name : Tag - Compile CAP CDS files
133- if : steps.check-tag .outputs.tag_exists ! = 'true'
168+ if : steps.needs-creation .outputs.needed = = 'true'
134169 run : |
135170 chmod +x ./extractors/cds/tools/workflow/cds-compilation-for-actions.sh
136171 ./extractors/cds/tools/workflow/cds-compilation-for-actions.sh
137172
138173 - name : Tag - Run CodeQL unit tests
139- if : steps.check-tag .outputs.tag_exists ! = 'true'
174+ if : steps.needs-creation .outputs.needed = = 'true'
140175 env :
141176 LGTM_INDEX_XML_MODE : all
142177 LGTM_INDEX_FILETYPES : " .json:JSON\n .cds:JSON"
@@ -150,15 +185,15 @@ jobs:
150185 -- javascript/
151186
152187 - name : Tag - Validate version consistency
153- if : steps.check-tag .outputs.tag_exists ! = 'true'
188+ if : steps.needs-creation .outputs.needed = = 'true'
154189 run : |
155190 RELEASE_NAME="${{ steps.version.outputs.release_name }}"
156191 echo "Validating all version-bearing files match ${RELEASE_NAME}..."
157192 ./scripts/update-release-version.sh --check "${RELEASE_NAME}"
158193
159194 - name : Tag - Commit version changes and create tag
160195 id : create-tag
161- if : steps.check-tag .outputs.tag_exists ! = 'true'
196+ if : steps.needs-creation .outputs.needed = = 'true'
162197 run : |
163198 TAG="${{ steps.version.outputs.version }}"
164199 RELEASE_NAME="${{ steps.version.outputs.release_name }}"
@@ -167,12 +202,16 @@ jobs:
167202 git config user.name "github-actions[bot]"
168203 git config user.email "41898282+github-actions[bot]@users.noreply.github.com"
169204
205+ # Detach HEAD so we never push to a protected branch.
206+ # The version-update commit will only be reachable via the tag.
207+ git checkout --detach HEAD
208+
170209 # Stage version-bearing files and lockfile changes
171210 git add -A
172- # Ensure generated artifacts (CodeQL, CAP compilation) are not staged for commit
173- git restore --staged .codeql || true
174- git restore --staged '*.qlx' || true
175- git restore --staged 'javascript/frameworks/cap/test/**/model.cds.json' || true
211+ # Ensure generated artifacts (CodeQL, CAP compilation) are not staged
212+ git restore --staged .codeql 2>/dev/null || true
213+ git restore --staged '*.qlx' 2>/dev/null || true
214+ git restore --staged 'javascript/frameworks/cap/test/**/model.cds.json' 2>/dev/null || true
176215
177216 # Check if there are changes to commit
178217 if git diff --cached --quiet; then
@@ -181,26 +220,25 @@ jobs:
181220 else
182221 git commit -m "Release ${TAG}: update versions to ${RELEASE_NAME}"
183222 CURRENT_SHA=$(git rev-parse HEAD)
184- git push origin HEAD
185- echo "✅ Committed version changes at ${CURRENT_SHA:0:8}"
223+ echo "✅ Created version commit at ${CURRENT_SHA:0:8}"
186224 fi
187225
188- # Create and push the tag
226+ # Push only the tag — never the branch
189227 git tag -a "${TAG}" -m "Release ${TAG}" "${CURRENT_SHA}"
190- git push origin "${TAG}"
228+ git push origin "refs/tags/ ${TAG}"
191229 echo "✅ Created and pushed tag ${TAG} at commit ${CURRENT_SHA:0:8}"
192230 echo "tag_sha=${CURRENT_SHA}" >> $GITHUB_OUTPUT
193231
194232 - name : Tag - Output existing tag SHA
195233 id : existing-tag
196- if : steps.check-tag .outputs.tag_exists == 'true '
234+ if : steps.needs-creation .outputs.needed == 'false '
197235 run : |
198236 echo "tag_sha=${{ steps.check-tag.outputs.tag_sha }}" >> $GITHUB_OUTPUT
199237
200238 - name : Tag - Set final tag SHA output
201239 id : final-sha
202240 run : |
203- if [ "${{ steps.check-tag .outputs.tag_exists }}" == "true " ]; then
241+ if [ "${{ steps.needs-creation .outputs.needed }}" == "false " ]; then
204242 SHA="${{ steps.check-tag.outputs.tag_sha }}"
205243 else
206244 SHA="${{ steps.create-tag.outputs.tag_sha }}"
@@ -212,11 +250,15 @@ jobs:
212250 TAG="${{ steps.version.outputs.version }}"
213251 echo "## Release Tag Summary" >> $GITHUB_STEP_SUMMARY
214252 echo "" >> $GITHUB_STEP_SUMMARY
215- if [ "${{ steps.check-tag .outputs.tag_exists }}" == "true " ]; then
216- echo "ℹ️ Tag \`${TAG}\` already existed at \`${{ steps.check-tag.outputs.tag_sha }}\`" >> $GITHUB_STEP_SUMMARY
253+ if [ "${{ steps.needs-creation .outputs.needed }}" == "false " ]; then
254+ echo "ℹ️ Tag \`${TAG}\` already existed at \`${{ steps.check-tag.outputs.tag_sha }}\` with correct versions " >> $GITHUB_STEP_SUMMARY
217255 else
218256 echo "✅ Created tag \`${TAG}\` at \`${{ steps.create-tag.outputs.tag_sha }}\`" >> $GITHUB_STEP_SUMMARY
219257 echo "" >> $GITHUB_STEP_SUMMARY
258+ if [ "${{ steps.check-tag.outputs.tag_exists }}" == "true" ]; then
259+ echo "⚠️ Previous tag had incorrect versions and was replaced" >> $GITHUB_STEP_SUMMARY
260+ echo "" >> $GITHUB_STEP_SUMMARY
261+ fi
220262 echo "| Step | Status |" >> $GITHUB_STEP_SUMMARY
221263 echo "| ---- | ------ |" >> $GITHUB_STEP_SUMMARY
222264 echo "| Version update | ✅ All files updated to ${{ steps.version.outputs.release_name }} |" >> $GITHUB_STEP_SUMMARY
0 commit comments