Validated Release #27
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
| name: Validated Release | |
| run-name: "${{ inputs.dry_run && 'Dry-run for ' || 'Perform ' }}${{ inputs.release_type }} release of ${{ github.ref_name }} branch" | |
| on: | |
| workflow_dispatch: | |
| inputs: | |
| release_type: | |
| type: choice | |
| description: The release type | |
| options: | |
| - "major" | |
| - "minor" | |
| - "patch" | |
| - "retag" | |
| default: "minor" | |
| dry_run: | |
| description: Perform the release dry-run | |
| required: true | |
| type: boolean | |
| default: true | |
| skip_tests: | |
| description: Skip pre-release tests (emergency releases only) | |
| required: false | |
| type: boolean | |
| default: false | |
| permissions: | |
| contents: write | |
| actions: read | |
| jobs: | |
| validate-inputs: | |
| runs-on: ubuntu-latest | |
| outputs: | |
| release_version: ${{ steps.compute-version.outputs.release_version }} | |
| next_version: ${{ steps.compute-version.outputs.next_version }} | |
| release_branch: ${{ steps.compute-version.outputs.release_branch }} | |
| steps: | |
| - name: Checkout repository | |
| uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 | |
| with: | |
| fetch-depth: 0 | |
| - name: Setup Java | |
| uses: actions/setup-java@be666c2fcd27ec809703dec50e508c2fdc7f6654 # v5.2.0 | |
| with: | |
| distribution: 'zulu' | |
| java-version: '21' | |
| - name: Validate branch and compute versions | |
| id: compute-version | |
| run: | | |
| BRANCH="${GITHUB_REF_NAME}" | |
| TYPE="${{ inputs.release_type }}" | |
| echo "Current branch: $BRANCH" | |
| echo "Release type: $TYPE" | |
| # Branch validation | |
| if [ "$TYPE" == "patch" ] || [ "$TYPE" == "retag" ]; then | |
| if [[ ! $BRANCH =~ ^release/[0-9]+\.[0-9]+\._$ ]]; then | |
| echo "::error::${TYPE^} can only be performed from 'release/*' branches (format: release/X.Y._)" | |
| exit 1 | |
| fi | |
| else | |
| if [ "$BRANCH" != "main" ]; then | |
| echo "::error::Major or minor releases can only be performed from 'main' branch" | |
| exit 1 | |
| fi | |
| fi | |
| # Get current version | |
| BASE=$(./gradlew printVersion -Psnapshot=false | grep 'Version:' | cut -f2 -d' ') | |
| echo "Current version: $BASE" | |
| # Parse version components | |
| if [[ $BASE =~ ^([0-9]+)\.([0-9]+)\.([0-9]+)$ ]]; then | |
| MAJOR="${BASH_REMATCH[1]}" | |
| MINOR="${BASH_REMATCH[2]}" | |
| PATCH="${BASH_REMATCH[3]}" | |
| else | |
| echo "::error::Invalid version format: $BASE (expected X.Y.Z)" | |
| exit 1 | |
| fi | |
| # Check if this version is already released | |
| if git rev-parse "v_${BASE}" >/dev/null 2>&1; then | |
| ALREADY_RELEASED=true | |
| echo "Version $BASE is already released" | |
| else | |
| ALREADY_RELEASED=false | |
| echo "Version $BASE is not yet released" | |
| fi | |
| # Compute release version based on type | |
| if [ "$TYPE" == "MAJOR" ] || [ "$TYPE" == "major" ]; then | |
| if [ "$ALREADY_RELEASED" == "true" ]; then | |
| RELEASE_VERSION="$((MAJOR + 1)).0.0" | |
| else | |
| RELEASE_VERSION="$BASE" | |
| fi | |
| elif [ "$TYPE" == "MINOR" ] || [ "$TYPE" == "minor" ]; then | |
| if [ "$ALREADY_RELEASED" == "true" ]; then | |
| RELEASE_VERSION="$MAJOR.$((MINOR + 1)).0" | |
| else | |
| RELEASE_VERSION="$BASE" | |
| fi | |
| elif [ "$TYPE" == "retag" ]; then | |
| # Retag reuses the current version; tag must already exist | |
| RELEASE_VERSION="$BASE" | |
| if ! git rev-parse "v_${RELEASE_VERSION}" >/dev/null 2>&1; then | |
| echo "::error::Tag v_${RELEASE_VERSION} does not exist. Use a normal release to create a new tag." | |
| exit 1 | |
| fi | |
| # Refuse if the GitHub release is already public | |
| IS_DRAFT=$(gh release view "v_${RELEASE_VERSION}" --json isDraft --jq '.isDraft' 2>/dev/null || echo "not-found") | |
| if [ "$IS_DRAFT" == "false" ]; then | |
| echo "::error::GitHub release v_${RELEASE_VERSION} is already public. Retagging is not allowed." | |
| exit 1 | |
| fi | |
| else | |
| # PATCH always increments | |
| RELEASE_VERSION="$MAJOR.$MINOR.$((PATCH + 1))" | |
| fi | |
| # Compute release branch | |
| RELEASE_BRANCH="release/${RELEASE_VERSION%.*}._" | |
| # Check if tag already exists (skip for retag, which requires it to exist) | |
| if [ "$TYPE" != "retag" ] && git rev-parse "v_${RELEASE_VERSION}" >/dev/null 2>&1; then | |
| echo "::error::Tag v_${RELEASE_VERSION} already exists" | |
| exit 1 | |
| fi | |
| echo "Release version: $RELEASE_VERSION" | |
| echo "Release branch: $RELEASE_BRANCH" | |
| # Set outputs | |
| echo "release_version=$RELEASE_VERSION" >> $GITHUB_OUTPUT | |
| echo "release_branch=$RELEASE_BRANCH" >> $GITHUB_OUTPUT | |
| # Output summary | |
| echo "## Release Validation" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Release Type**: $TYPE" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Branch**: $BRANCH" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Release Version**: $RELEASE_VERSION" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Release Branch**: $RELEASE_BRANCH" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Tag**: v_$RELEASE_VERSION" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Dry Run**: ${{ inputs.dry_run }}" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Skip Tests**: ${{ inputs.skip_tests }}" >> $GITHUB_STEP_SUMMARY | |
| pre-release-tests: | |
| needs: validate-inputs | |
| if: ${{ inputs.dry_run != true && inputs.skip_tests != true && inputs.release_type != 'retag' }} | |
| uses: ./.github/workflows/test_workflow.yml | |
| with: | |
| configuration: '["debug", "asan"]' | |
| create-release: | |
| needs: [validate-inputs, pre-release-tests] | |
| if: always() && needs.validate-inputs.result == 'success' && (needs.pre-release-tests.result == 'success' || needs.pre-release-tests.result == 'skipped') | |
| runs-on: ubuntu-latest | |
| steps: | |
| - name: Check test results | |
| if: ${{ inputs.dry_run != true && inputs.skip_tests != true && inputs.release_type != 'retag' && needs.pre-release-tests.result != 'success' }} | |
| run: | | |
| echo "::error::Pre-release tests failed. Cannot proceed with release." | |
| exit 1 | |
| - uses: webfactory/ssh-agent@e83874834305fe9a4a2997156cb26c5de65a8555 # v0.10.0 | |
| with: | |
| ssh-private-key: ${{ secrets.SSH_PUSH_SECRET }} | |
| - name: Checkout repository | |
| run: git clone git@github.com:$GITHUB_REPOSITORY.git java-profiler | |
| - name: Configure git | |
| run: | | |
| cd java-profiler | |
| git config --global user.email "java-profiler@datadoghq.com" | |
| git config --global user.name "Datadog Java Profiler" | |
| git checkout $GITHUB_REF_NAME | |
| - name: Setup Java | |
| uses: actions/setup-java@be666c2fcd27ec809703dec50e508c2fdc7f6654 # v5.2.0 | |
| with: | |
| distribution: 'zulu' | |
| java-version: '21' | |
| - name: Create release | |
| env: | |
| GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
| run: | | |
| cd java-profiler | |
| if [ "${{ inputs.dry_run }}" == "true" ]; then | |
| DRY_RUN="--dry-run" | |
| else | |
| DRY_RUN="" | |
| fi | |
| TYPE="${{ inputs.release_type }}" | |
| ./.github/scripts/release.sh ${TYPE^^} $DRY_RUN | |
| - name: Output Release Summary | |
| if: ${{ inputs.dry_run != true }} | |
| run: | | |
| echo "## ✅ Release Created Successfully" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "### Release Details" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Tag**: v_${{ needs.validate-inputs.outputs.release_version }}" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Branch**: ${{ needs.validate-inputs.outputs.release_branch }}" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "### Next Steps (Automatic)" >> $GITHUB_STEP_SUMMARY | |
| echo "1. 🔨 GitLab pipeline will build multi-platform artifacts" >> $GITHUB_STEP_SUMMARY | |
| echo "2. 📦 GitLab will publish to Maven Central" >> $GITHUB_STEP_SUMMARY | |
| echo "3. 🚀 GitHub workflows will create release when Maven artifacts are available" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "### Monitoring" >> $GITHUB_STEP_SUMMARY | |
| echo "- GitHub Releases: ${{ github.server_url }}/${{ github.repository }}/releases" >> $GITHUB_STEP_SUMMARY | |
| echo "- Maven Central: https://repo1.maven.org/maven2/com/datadoghq/ddprof/${{ needs.validate-inputs.outputs.release_version }}/" >> $GITHUB_STEP_SUMMARY | |
| - name: Output Dry-Run Summary | |
| if: ${{ inputs.dry_run == true }} | |
| run: | | |
| echo "## 🔍 Dry-Run Complete" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "This was a dry-run. No changes were made." >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "### Would have created:" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Tag**: v_${{ needs.validate-inputs.outputs.release_version }}" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Branch**: ${{ needs.validate-inputs.outputs.release_branch }}" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "To perform the actual release, run this workflow again with **dry_run = false**" >> $GITHUB_STEP_SUMMARY |