diff --git a/.github/workflows/pre-release.yaml b/.github/workflows/pre-release.yaml new file mode 100644 index 00000000..1119dd65 --- /dev/null +++ b/.github/workflows/pre-release.yaml @@ -0,0 +1,65 @@ +# Workflow to fetch the latest commit hash on the main branch and upload artifacts to CF storage. +name: Build and upload from main +on: + workflow_dispatch: + +concurrency: ${{ github.workflow }}-${{ github.ref }} + +jobs: + define-matrix: + name: Define Matrix + runs-on: blacksmith-2vcpu-ubuntu-2204 + outputs: + releases: ${{ steps.prepare-matrix.outputs.releases }} + commit_hash: ${{ steps.get-commit-hash.outputs.hash }} + + steps: + - name: Checkout repository + uses: actions/checkout@v4 + + - name: Install dependencies + run: sudo apt-get install -y jq + + - name: Get latest commit hash + id: get-commit-hash + run: echo "hash=$(git rev-parse --short HEAD)" >> "$GITHUB_OUTPUT" + + - name: Prepare JSON output for matrix + id: prepare-matrix + run: | + RELEASES_JSON=$(find contracts -maxdepth 1 -mindepth 1 -type d | sed 's|contracts/||' | jq -R . | jq -s --arg commit "${{ steps.get-commit-hash.outputs.hash }}" 'map({ + package_name: ., + version: $commit, + package_git_tag: "\(.)_\($commit)" + })') + echo "releases=$(echo "$RELEASES_JSON" | jq -c)" >> "$GITHUB_OUTPUT" + + build: + needs: define-matrix + uses: ./.github/workflows/reusable-build.yaml + with: + commit-hash: ${{ needs.define-matrix.outputs.commit_hash }} + + upload: + needs: [define-matrix, build] + strategy: + matrix: + releases: ${{ fromJson(needs.define-matrix.outputs.releases) }} + + uses: ./.github/workflows/reusable-upload.yaml + permissions: + id-token: write + contents: read + with: + package-name: ${{ matrix.releases.package_name }} + package-version: ${{ matrix.releases.version }} + package-git-tag: ${{ matrix.releases.package_git_tag }} + artifact-name: ${{ needs.build.outputs.artifact-name }} + cf-bucket-name: ${{ vars.CF_BUCKET_NAME }} + cf-config-bucket-root-key: ${{ vars.CF_BUCKET_ROOT_KEY }} + github-release: false + secrets: + github-token: ${{ secrets.PAT_TOKEN }} + cf-endpoint-url: ${{ secrets.CF_ENDPOINT_URL }} + cf-bucket-access-key-id: ${{ secrets.CF_BUCKET_ACCESS_KEY_ID }} + cf-bucket-secret-access-key: ${{ secrets.CF_BUCKET_SECRET_ACCESS_KEY }} diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml index c1778982..def28a21 100644 --- a/.github/workflows/release.yaml +++ b/.github/workflows/release.yaml @@ -6,7 +6,7 @@ on: pull_request: branches: - main - - 'releases/**' + - "releases/**" types: [closed] workflow_dispatch: @@ -14,7 +14,6 @@ on: concurrency: ${{ github.workflow }}-${{ github.ref }} jobs: - # Publishes a release in case the release isn't published publish-release: name: Publish releases @@ -24,10 +23,11 @@ jobs: ((github.event.pull_request.merged == true) && contains(github.event.pull_request.labels.*.name, 'release')) - runs-on: blacksmith-8vcpu-ubuntu-2204 + runs-on: blacksmith-2vcpu-ubuntu-2204 outputs: releases: ${{ steps.prepare-matrix.outputs.releases }} + commit_hash: ${{ steps.get-commit-hash.outputs.hash }} steps: - name: Checkout repository @@ -39,6 +39,10 @@ jobs: - name: Install Rust toolchain uses: dtolnay/rust-toolchain@stable + - name: Get commit hash + id: get-commit-hash + run: echo "hash=$(git rev-parse HEAD)" >> "$GITHUB_OUTPUT" + # Creates git tags and publishes the crates of the new releases - name: Publish release id: publish-release @@ -56,35 +60,32 @@ jobs: run: | echo "releases=$(echo '${{ steps.publish-release.outputs.releases }}' | jq -c '.')" >> $GITHUB_OUTPUT - # Creates other artifacts needed (`wasm` files) - build-and-upload: - name: Build artifacts for ${{ matrix.releases.package_name }}-v${{ matrix.releases.version }} + build: needs: publish-release + uses: ./.github/workflows/reusable-build.yaml + with: + commit-hash: ${{ needs.publish-release.outputs.commit_hash }} - # Once a release is done for a package, we iterate on each of these packages and build its corresponding artifacts and upload them + upload: + needs: [publish-release, build] strategy: matrix: releases: ${{ fromJson(needs.publish-release.outputs.releases) }} - uses: ./.github/workflows/reusable-build-upload.yaml - + uses: ./.github/workflows/reusable-upload.yaml permissions: id-token: write contents: read - with: - package-name: "${{ matrix.releases.package_name }}" - package-version: "${{ matrix.releases.version }}" - package-git-tag: "${{ matrix.releases.tag }}" - - # CF Bucket related variables - cf-bucket-name: "${{ vars.CF_BUCKET_NAME }}" - - # The root key to be used for accessing the configs. (ex: `test-root-key` puts releases in `test-root-key/*`) - cf-config-bucket-root-key: "${{ vars.CF_BUCKET_ROOT_KEY }}" - + package-name: ${{ matrix.releases.package_name }} + package-version: ${{ matrix.releases.version }} + package-git-tag: ${{ matrix.releases.tag }} + artifact-name: ${{ needs.build.outputs.artifact-name }} + cf-bucket-name: ${{ vars.CF_BUCKET_NAME }} + cf-config-bucket-root-key: ${{ vars.CF_BUCKET_ROOT_KEY }} + github-release: true secrets: - github-token: "${{ secrets.PAT_TOKEN }}" - cf-endpoint-url: "${{ secrets.CF_ENDPOINT_URL }}" + github-token: ${{ secrets.PAT_TOKEN }} + cf-endpoint-url: ${{ secrets.CF_ENDPOINT_URL }} cf-bucket-access-key-id: ${{ secrets.CF_BUCKET_ACCESS_KEY_ID }} cf-bucket-secret-access-key: ${{ secrets.CF_BUCKET_SECRET_ACCESS_KEY }} diff --git a/.github/workflows/reusable-build.yaml b/.github/workflows/reusable-build.yaml new file mode 100644 index 00000000..67157adb --- /dev/null +++ b/.github/workflows/reusable-build.yaml @@ -0,0 +1,69 @@ +name: "Build Contracts" + +on: + workflow_call: + inputs: + commit-hash: + description: "The commit hash to build from" + type: string + required: true + outputs: + artifact-name: + description: "Name of the uploaded artifact containing all builds" + value: ${{ jobs.build.outputs.artifact-name }} + +jobs: + build: + runs-on: blacksmith-8vcpu-ubuntu-2204 + outputs: + artifact-name: ${{ steps.set-artifact-name.outputs.name }} + + steps: + - name: Checkout repository + uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - name: Checkout specific commit + run: git checkout ${{ inputs.commit-hash }} + + - name: Install Rust toolchain + uses: dtolnay/rust-toolchain@stable + with: + toolchain: 1.81.0 + targets: wasm32-unknown-unknown + + - name: Set artifact name + id: set-artifact-name + run: | + echo "name=wasm-builds-${{ inputs.commit-hash }}" >> $GITHUB_OUTPUT + + - name: Build all contracts + run: | + # 21.1.1 is the latest rust 1.76.0 compatible version, the version after is 21.2.0 which is compatible with 1.79.0 (different than the workspace's version) + cargo install --locked stellar-cli --version 22.2.0 --features opt + + # Build all contracts + cargo wasm + ./optimize.sh + + # Create directory for storing optimized WASM files + mkdir -p wasm-builds + + # Process in the release directory + cd target/wasm32-unknown-unknown/release + + # Remove unoptimized files and rename optimized ones + # This ensures we only keep the optimized versions + find . -type f -name "*.wasm" ! -name "*.optimized.wasm" -maxdepth 1 -delete + find . -name "*.optimized.wasm" -maxdepth 1 -exec sh -c 'mv "$0" "${0%.optimized.wasm}.wasm"' {} \; + + # Move all optimized WASM files to the builds directory + mv *.wasm ../../../wasm-builds/ + + - name: Upload artifact + uses: actions/upload-artifact@v4 + with: + name: ${{ steps.set-artifact-name.outputs.name }} + path: wasm-builds + retention-days: 1 diff --git a/.github/workflows/reusable-build-upload.yaml b/.github/workflows/reusable-upload.yaml similarity index 81% rename from .github/workflows/reusable-build-upload.yaml rename to .github/workflows/reusable-upload.yaml index ee6b103c..a3bf0e52 100644 --- a/.github/workflows/reusable-build-upload.yaml +++ b/.github/workflows/reusable-upload.yaml @@ -1,9 +1,8 @@ -name: "Publish specific rust package" +name: "Upload Contract to Cloudflare" on: workflow_call: inputs: - # Package related variables package-name: description: "The package name to use (ex: gz-srv)" type: string @@ -22,7 +21,11 @@ on: required: true default: "" - # CF Bucket related variables + artifact-name: + description: "Name of the artifact containing the builds" + type: string + required: true + cf-bucket-name: description: "The CF bucket name to use" required: true @@ -33,6 +36,11 @@ on: required: true type: string + github-release: + description: "Whether to upload as a github release" + type: boolean + default: true + secrets: github-token: description: "The github token to use to do the tag updates" @@ -48,36 +56,22 @@ on: required: true jobs: - build-and-upload: - runs-on: blacksmith-8vcpu-ubuntu-2204 + upload: + name: upload ${{ inputs.package-git-tag }} + runs-on: blacksmith-2vcpu-ubuntu-2204 steps: - - name: Checkout repository - uses: actions/checkout@v4 - with: - fetch-depth: 0 - token: ${{ secrets.github-token }} - - - name: Install Rust toolchain - uses: dtolnay/rust-toolchain@stable + - name: Download artifact + uses: actions/download-artifact@v4 with: - toolchain: 1.81.0 - targets: wasm32-unknown-unknown - - - name: Build artifacts for ${{ inputs.package-name }}-v${{ inputs.package-version }} - run: | - echo "Building wasm for '${{ inputs.package-name }}-v${{ inputs.package-version }}'"; - cargo install --locked stellar-cli --version 22.2.0 --features opt - cargo wasm -p ${{ inputs.package-name }} - stellar contract build - ./optimize.sh + name: ${{ inputs.artifact-name }} + path: wasm-builds - # Prepare the variables that will be used across the different next steps - name: Prepare cross-steps variables run: | export PACKAGE_NAME='${{ inputs.package-name }}' - export PACKAGE_VERSION='v${{ inputs.package-version }}' + export PACKAGE_VERSION=${{ inputs.github-release && format('v{0}', inputs.package-version) || inputs.package-version }} - export BASE_ARTIFACTS_DIR="./target/wasm32-unknown-unknown/release" + export BASE_ARTIFACTS_DIR="./wasm-builds" export ARTIFACT_NAME="axelar-cgp-stellar-wasm-${PACKAGE_NAME}-${PACKAGE_VERSION}" export BASE_ARTIFACTS_VERSIONED_DIR="$(dirname ${BASE_ARTIFACTS_DIR})/${ARTIFACT_NAME}" # Regardless of the dir type, relative or absolute @@ -88,13 +82,13 @@ jobs: # Ensures that this dir is created mkdir -p ${ARCHIVES_OUTPUT_DIR} - # ex: stellar-axelar-gas-service + # ex: axelar-gas-service echo "PACKAGE_NAME=${PACKAGE_NAME}" >> $GITHUB_ENV # ex: v0.1.0 echo "PACKAGE_VERSION=${PACKAGE_VERSION}" >> $GITHUB_ENV - # ex: ./target/wasm32-unknown-unknown/release + # ex: ./wasm-builds echo "BASE_ARTIFACTS_DIR=${BASE_ARTIFACTS_DIR}" >> $GITHUB_ENV # ex: axelar-cgp-stellar-wasm-stellar-axelar-gas-service-v0.1.0 @@ -115,12 +109,6 @@ jobs: # This cd to keep the dir structure of the artifacts archive cd ${{ env.BASE_ARTIFACTS_VERSIONED_DIR }} - # Remove "unoptimized" built wasm files - find "." -type f -name "*.wasm" ! -name "*.optimized.wasm" -maxdepth 1 -delete - - # Rename the optimized ones and remove the ".optimized" suffix - find . -name "*.optimized.wasm" -maxdepth 1 -exec sh -c 'mv "$0" "${0%.optimized.wasm}.wasm"' {} \; - # Archive the wasm find "." -type f -name "*.wasm" -maxdepth 1 -print | zip "${{ env.ZIP_ARCHIVE_FILE }}" -@ find "." -type f -name "*.wasm" -maxdepth 1 -print | tar -czvf "${{ env.TAR_ARCHIVE_FILE }}" -T - @@ -176,6 +164,7 @@ jobs: # https://github.com/orgs/community/discussions/26263#discussioncomment-3251069 - name: Update the GitHub Release uses: softprops/action-gh-release@c062e08bd532815e2082a85e87e3ef29c3e6d191 # v2.0.8 + if: inputs.github-release with: tag_name: ${{ inputs.package-git-tag }} # This uses the tag from the push files: |