From 3923643e2e0ecf4ac198424e0b07e9bed2e80ff2 Mon Sep 17 00:00:00 2001 From: Brian Clozel Date: Thu, 11 Jul 2024 17:13:13 +0200 Subject: [PATCH] Migrate all workflows to GitHub Actions This commit completes the migration from Concourse to GitHub Actions, adding the CI variants and release workflows. See gh-1024 --- .github/actions/build-and-publish/action.yml | 56 ++++ .../actions/create-github-release/action.yml | 23 ++ .../changelog-generator.yml | 7 +- .../actions/prepare-gradle-build/action.yml | 49 +++ .github/actions/send-notification/action.yml | 2 +- .../actions/sync-to-maven-central/action.yml | 50 +++ .../sync-to-maven-central/artifacts.spec | 20 ++ .github/workflows/backport-bot.yml | 13 +- .../workflows/build-and-deploy-snapshot.yml | 51 ++- .github/workflows/ci.yml | 41 +++ .github/workflows/release.yml | 77 +++++ ci/README.adoc | 52 ---- ci/config/release-scripts.yml | 10 - ci/images/README.adoc | 21 -- ci/images/ci-image/Dockerfile | 11 - ci/images/docker-lib.sh | 97 ------ ci/images/get-docker-url.sh | 5 - ci/images/get-jdk-url.sh | 14 - ci/images/setup.sh | 49 --- ci/images/start-docker.sh | 4 - ci/pipeline.yml | 290 ------------------ ci/scripts/common.sh | 2 - ci/scripts/generate-changelog.sh | 12 - ci/scripts/promote-version.sh | 18 -- ci/scripts/stage-version.sh | 50 --- ci/tasks/build-ci-image.yml | 29 -- ci/tasks/generate-changelog.yml | 22 -- ci/tasks/promote-version.yml | 25 -- ci/tasks/stage-version.yml | 17 - 29 files changed, 348 insertions(+), 769 deletions(-) create mode 100644 .github/actions/build-and-publish/action.yml create mode 100644 .github/actions/create-github-release/action.yml rename {ci/config => .github/actions/create-github-release}/changelog-generator.yml (77%) create mode 100644 .github/actions/prepare-gradle-build/action.yml create mode 100644 .github/actions/sync-to-maven-central/action.yml create mode 100644 .github/actions/sync-to-maven-central/artifacts.spec create mode 100644 .github/workflows/ci.yml create mode 100644 .github/workflows/release.yml delete mode 100644 ci/README.adoc delete mode 100644 ci/config/release-scripts.yml delete mode 100644 ci/images/README.adoc delete mode 100644 ci/images/ci-image/Dockerfile delete mode 100755 ci/images/docker-lib.sh delete mode 100755 ci/images/get-docker-url.sh delete mode 100755 ci/images/get-jdk-url.sh delete mode 100755 ci/images/setup.sh delete mode 100755 ci/images/start-docker.sh delete mode 100644 ci/pipeline.yml delete mode 100644 ci/scripts/common.sh delete mode 100755 ci/scripts/generate-changelog.sh delete mode 100755 ci/scripts/promote-version.sh delete mode 100755 ci/scripts/stage-version.sh delete mode 100644 ci/tasks/build-ci-image.yml delete mode 100755 ci/tasks/generate-changelog.yml delete mode 100644 ci/tasks/promote-version.yml delete mode 100644 ci/tasks/stage-version.yml diff --git a/.github/actions/build-and-publish/action.yml b/.github/actions/build-and-publish/action.yml new file mode 100644 index 00000000..cd2204e1 --- /dev/null +++ b/.github/actions/build-and-publish/action.yml @@ -0,0 +1,56 @@ +name: 'Build' +description: 'Builds the project, optionally publishing it to a local deployment repository' +inputs: + java-version: + required: false + default: '17' + description: 'The Java version to compile and test with' + java-distribution: + required: false + default: 'liberica' + description: 'The Java distribution to use for the build' + java-toolchain: + required: false + default: 'false' + description: 'Whether a Java toolchain should be used' + publish: + required: false + default: 'false' + description: 'Whether to publish artifacts ready for deployment to Artifactory' + develocity-access-key: + required: false + description: 'The access key for authentication with ge.spring.io' +outputs: + build-scan-url: + description: 'The URL, if any, of the build scan produced by the build' + value: ${{ (inputs.publish == 'true' && steps.publish.outputs.build-scan-url) || steps.build.outputs.build-scan-url }} + version: + description: 'The version that was built' + value: ${{ steps.read-version.outputs.version }} +runs: + using: composite + steps: + - name: Prepare Gradle Build + uses: ./.github/actions/prepare-gradle-build + with: + develocity-access-key: ${{ inputs.develocity-access-key }} + java-version: ${{ inputs.java-version }} + java-distribution: ${{ inputs.java-distribution }} + java-toolchain: ${{ inputs.java-toolchain }} + - name: Build + id: build + if: ${{ inputs.publish == 'false' }} + shell: bash + run: ./gradlew check antora + - name: Publish + id: publish + if: ${{ inputs.publish == 'true' }} + shell: bash + run: ./gradlew -PdeploymentRepository=$(pwd)/deployment-repository build publishAllPublicationsToDeploymentRepository + - name: Read Version From gradle.properties + id: read-version + shell: bash + run: | + version=$(sed -n 's/version=\(.*\)/\1/p' gradle.properties) + echo "Version is $version" + echo "version=$version" >> $GITHUB_OUTPUT \ No newline at end of file diff --git a/.github/actions/create-github-release/action.yml b/.github/actions/create-github-release/action.yml new file mode 100644 index 00000000..9afc1dc6 --- /dev/null +++ b/.github/actions/create-github-release/action.yml @@ -0,0 +1,23 @@ +name: Create GitHub Release +description: Create the release on GitHub with a changelog +inputs: + milestone: + description: 'Name of the GitHub milestone for which a release will be created' + required: true + token: + description: 'Token to use for authentication with GitHub' + required: true +runs: + using: composite + steps: + - name: Generate Changelog + uses: spring-io/github-changelog-generator@185319ad7eaa75b0e8e72e4b6db19c8b2cb8c4c1 #v0.0.11 + with: + milestone: ${{ inputs.milestone }} + token: ${{ inputs.token }} + config-file: .github/actions/create-github-release/changelog-generator.yml + - name: Create GitHub Release + env: + GITHUB_TOKEN: ${{ inputs.token }} + shell: bash + run: gh release create ${{ format('v{0}', inputs.milestone) }} --notes-file changelog.md \ No newline at end of file diff --git a/ci/config/changelog-generator.yml b/.github/actions/create-github-release/changelog-generator.yml similarity index 77% rename from ci/config/changelog-generator.yml rename to .github/actions/create-github-release/changelog-generator.yml index 93713c63..46d8f6f6 100644 --- a/ci/config/changelog-generator.yml +++ b/.github/actions/create-github-release/changelog-generator.yml @@ -4,7 +4,7 @@ changelog: - title: ":star: New Features" labels: - "type: enhancement" - - title: ":beetle: Bug Fixes" + - title: ":lady_beetle: Bug Fixes" labels: - "type: bug" - "type: regression" @@ -15,3 +15,8 @@ changelog: sort: "title" labels: - "type: dependency-upgrade" + contributors: + exclude: + names: + - "bclozel" + - "rstoyanchev" \ No newline at end of file diff --git a/.github/actions/prepare-gradle-build/action.yml b/.github/actions/prepare-gradle-build/action.yml new file mode 100644 index 00000000..e0fa32b2 --- /dev/null +++ b/.github/actions/prepare-gradle-build/action.yml @@ -0,0 +1,49 @@ +name: 'Prepare Gradle Build' +description: 'Prepares a Gradle build. Sets up Java and Gradle and configures Gradle properties' +inputs: + java-version: + required: false + default: '17' + description: 'The Java version to use for the build' + java-distribution: + required: false + default: 'liberica' + description: 'The Java distribution to use for the build' + java-toolchain: + required: false + default: 'false' + description: 'Whether a Java toolchain should be used' + develocity-access-key: + required: false + description: 'The access key for authentication with ge.spring.io' +runs: + using: composite + steps: + - name: Set Up Java + uses: actions/setup-java@v4 + with: + distribution: ${{ inputs.java-distribution }} + java-version: | + ${{ inputs.java-version }} + ${{ inputs.java-toolchain == 'true' && '17' || '' }} + - name: Set Up Gradle + uses: gradle/actions/setup-gradle@dbbdc275be76ac10734476cc723d82dfe7ec6eda # v3.4.2 + with: + cache-read-only: false + develocity-access-key: ${{ inputs.develocity-access-key }} + - name: Configure Gradle Properties + shell: bash + run: | + mkdir -p $HOME/.gradle + echo 'systemProp.user.name=spring-builds+github' >> $HOME/.gradle/gradle.properties + echo 'systemProp.org.gradle.internal.launcher.welcomeMessageEnabled=false' >> $HOME/.gradle/gradle.properties + echo 'org.gradle.daemon=false' >> $HOME/.gradle/gradle.properties + echo 'org.gradle.daemon=4' >> $HOME/.gradle/gradle.properties + - name: Configure Toolchain Properties + if: ${{ inputs.java-toolchain == 'true' }} + shell: bash + run: | + echo toolchainVersion=${{ inputs.java-version }} >> $HOME/.gradle/gradle.properties + echo systemProp.org.gradle.java.installations.auto-detect=false >> $HOME/.gradle/gradle.properties + echo systemProp.org.gradle.java.installations.auto-download=false >> $HOME/.gradle/gradle.properties + echo systemProp.org.gradle.java.installations.paths=${{ format('$JAVA_HOME_{0}_X64', inputs.java-version) }} >> $HOME/.gradle/gradle.properties \ No newline at end of file diff --git a/.github/actions/send-notification/action.yml b/.github/actions/send-notification/action.yml index 0a676092..333ba217 100644 --- a/.github/actions/send-notification/action.yml +++ b/.github/actions/send-notification/action.yml @@ -1,4 +1,4 @@ -name: Send notification +name: Send Notification description: Sends a Google Chat message as a notification of the job's outcome inputs: webhook-url: diff --git a/.github/actions/sync-to-maven-central/action.yml b/.github/actions/sync-to-maven-central/action.yml new file mode 100644 index 00000000..60cf4a48 --- /dev/null +++ b/.github/actions/sync-to-maven-central/action.yml @@ -0,0 +1,50 @@ +name: Sync to Maven Central +description: Syncs a release to Maven Central and waits for it to be available for use +inputs: + jfrog-cli-config-token: + description: 'Config token for the JFrog CLI' + required: true + spring-graphql-version: + description: 'The version of Spring GraphQL that is being synced to Central' + required: true + ossrh-s01-token-username: + description: 'Username for authentication with s01.oss.sonatype.org' + required: true + ossrh-s01-token-password: + description: 'Password for authentication with s01.oss.sonatype.org' + required: true + ossrh-s01-staging-profile: + description: 'Staging profile to use when syncing to Central' + required: true +runs: + using: composite + steps: + - name: Set Up JFrog CLI + uses: jfrog/setup-jfrog-cli@7c95feb32008765e1b4e626b078dfd897c4340ad # v4.1.2 + env: + JF_ENV_SPRING: ${{ inputs.jfrog-cli-config-token }} + - name: Download Release Artifacts + shell: bash + run: jf rt download --spec ${{ format('{0}/artifacts.spec', github.action_path) }} --spec-vars 'buildName=${{ format('spring-graphql-{0}', inputs.spring-graphql-version) }};buildNumber=${{ github.run_number }}' + - name: Sync + uses: spring-io/nexus-sync-action@42477a2230a2f694f9eaa4643fa9e76b99b7ab84 # v0.0.1 + with: + username: ${{ inputs.ossrh-s01-token-username }} + password: ${{ inputs.ossrh-s01-token-password }} + staging-profile-name: ${{ inputs.ossrh-s01-staging-profile }} + create: true + upload: true + close: true + release: true + generate-checksums: true + - name: Await + shell: bash + run: | + url=${{ format('https://repo.maven.apache.org/maven2/org/springframework/graphql/spring-graphql/{0}/spring-graphql-{0}.jar', inputs.spring-graphql-version) }} + echo "Waiting for $url" + until curl --fail --head --silent $url > /dev/null + do + echo "." + sleep 60 + done + echo "$url is available" \ No newline at end of file diff --git a/.github/actions/sync-to-maven-central/artifacts.spec b/.github/actions/sync-to-maven-central/artifacts.spec new file mode 100644 index 00000000..18581eef --- /dev/null +++ b/.github/actions/sync-to-maven-central/artifacts.spec @@ -0,0 +1,20 @@ +{ + "files": [ + { + "aql": { + "items.find": { + "$and": [ + { + "@build.name": "${buildName}", + "@build.number": "${buildNumber}", + "path": { + "$nmatch": "org/springframework/graphql/spring-graphql-docs/*" + } + } + ] + } + }, + "target": "nexus/" + } + ] +} \ No newline at end of file diff --git a/.github/workflows/backport-bot.yml b/.github/workflows/backport-bot.yml index 4e8e757f..29969a23 100644 --- a/.github/workflows/backport-bot.yml +++ b/.github/workflows/backport-bot.yml @@ -18,16 +18,17 @@ jobs: pull-requests: write runs-on: ubuntu-latest steps: - - uses: actions/checkout@v3 - - uses: actions/setup-java@v3 + - name: Check out code + uses: actions/checkout@v4 + - name: Set up Java + uses: actions/setup-java@v4 with: - distribution: 'temurin' - java-version: '17' + distribution: 'liberica' + java-version: 17 - name: Download BackportBot run: wget https://github.com/spring-io/backport-bot/releases/download/latest/backport-bot-0.0.1-SNAPSHOT.jar - name: Backport env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} GITHUB_EVENT: ${{ toJSON(github.event) }} - run: java -jar backport-bot-0.0.1-SNAPSHOT.jar --github.accessToken="$GITHUB_TOKEN" --github.event_name "$GITHUB_EVENT_NAME" --github.event "$GITHUB_EVENT" - + run: java -jar backport-bot-0.0.1-SNAPSHOT.jar --github.accessToken="$GITHUB_TOKEN" --github.event_name "$GITHUB_EVENT_NAME" --github.event "$GITHUB_EVENT" \ No newline at end of file diff --git a/.github/workflows/build-and-deploy-snapshot.yml b/.github/workflows/build-and-deploy-snapshot.yml index 4e3c4aad..00c8e29b 100644 --- a/.github/workflows/build-and-deploy-snapshot.yml +++ b/.github/workflows/build-and-deploy-snapshot.yml @@ -1,43 +1,26 @@ -name: Build and deploy snapshot +name: Build and Deploy Snapshot on: push: branches: - main +permissions: + actions: write concurrency: group: ${{ github.workflow }}-${{ github.ref }} jobs: - build: - if: ${{ github.repository == 'spring-projects/spring-graphql' }} - name: Build and deploy snapshot + build-and-deploy-snapshot: + name: Build and Deploy Snapshot runs-on: ubuntu-latest + if: ${{ github.repository == 'spring-projects/spring-graphql' }} steps: - - name: Set up Java - uses: actions/setup-java@99b8673ff64fbf99d8d325f52d9a5bdedb8483e9 # v4.2.1 + - name: Check Out Code + uses: actions/checkout@v4 + - name: Build and Publish + id: build-and-publish + uses: ./.github/actions/build-and-publish with: - distribution: 'liberica' - java-version: 17 - - name: Check out code - uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4.1.1 - - name: Set up Gradle - uses: gradle/actions/setup-gradle@417ae3ccd767c252f5661f1ace9f835f9654f2b5 # v3.1.0 - with: - cache-read-only: ${{ github.ref != 'refs/heads/main' || !endsWith(github.ref, '.x') }} - - name: Configure Gradle properties - shell: bash - run: | - mkdir -p $HOME/.gradle - echo 'systemProp.user.name=spring-builds+github' >> $HOME/.gradle/gradle.properties - echo 'systemProp.org.gradle.internal.launcher.welcomeMessageEnabled=false' >> $HOME/.gradle/gradle.properties - echo 'org.gradle.daemon=false' >> $HOME/.gradle/gradle.properties - - name: Build and publish - id: build - env: - CI: 'true' - GRADLE_ENTERPRISE_URL: 'https://ge.spring.io' - GRADLE_ENTERPRISE_ACCESS_KEY: ${{ secrets.GRADLE_ENTERPRISE_SECRET_ACCESS_KEY }} - GRADLE_ENTERPRISE_CACHE_USERNAME: ${{ secrets.GRADLE_ENTERPRISE_CACHE_USER }} - GRADLE_ENTERPRISE_CACHE_PASSWORD: ${{ secrets.GRADLE_ENTERPRISE_CACHE_PASSWORD }} - run: ./gradlew -PdeploymentRepository=$(pwd)/deployment-repository build publishAllPublicationsToDeploymentRepository + develocity-access-key: ${{ secrets.GRADLE_ENTERPRISE_SECRET_ACCESS_KEY }} + publish: true - name: Deploy uses: spring-io/artifactory-deploy-action@26bbe925a75f4f863e1e529e85be2d0093cac116 # v0.0.1 with: @@ -51,11 +34,13 @@ jobs: signing-passphrase: ${{ secrets.GPG_PASSPHRASE }} artifact-properties: | /**/spring-graphql-docs-*.zip::zip.name=spring-graphql,zip.type=docs,zip.deployed=false - - name: Send notification + - name: Send Notification uses: ./.github/actions/send-notification if: always() with: webhook-url: ${{ secrets.GOOGLE_CHAT_WEBHOOK_URL }} status: ${{ job.status }} - build-scan-url: ${{ steps.build.outputs.build-scan-url }} - run-name: ${{ format('{0} | Linux | Java 17', github.ref_name) }} \ No newline at end of file + build-scan-url: ${{ steps.build-and-publish.outputs.build-scan-url }} + run-name: ${{ format('{0} | Linux | Java 17', github.ref_name) }} + outputs: + version: ${{ steps.build-and-publish.outputs.version }} \ No newline at end of file diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml new file mode 100644 index 00000000..32c2ef8f --- /dev/null +++ b/.github/workflows/ci.yml @@ -0,0 +1,41 @@ +name: CI +on: + push: + branches: + - main +concurrency: + group: ${{ github.workflow }}-${{ github.ref }} +jobs: + ci: + name: '${{ matrix.os.name}} | Java ${{ matrix.java.version}}' + runs-on: ${{ matrix.os.id }} + if: ${{ github.repository == 'spring-projects/spring-graphql' }} + strategy: + matrix: + os: + - id: ubuntu-latest + name: Linux + java: + - version: 21 + toolchain: true + - version: 22 + toolchain: true + steps: + - name: Check Out Code + uses: actions/checkout@v4 + - name: Build + id: build + uses: ./.github/actions/build-and-publish + with: + java-version: ${{ matrix.java.version }} + java-distribution: ${{ matrix.java.distribution || 'liberica' }} + java-toolchain: ${{ matrix.java.toolchain }} + develocity-access-key: ${{ secrets.GRADLE_ENTERPRISE_SECRET_ACCESS_KEY }} + - name: Send Notification + uses: ./.github/actions/send-notification + if: always() + with: + webhook-url: ${{ secrets.GOOGLE_CHAT_WEBHOOK_URL }} + status: ${{ job.status }} + build-scan-url: ${{ steps.build.outputs.build-scan-url }} + run-name: ${{ format('{0} | {1} | Java {2}', github.ref_name, matrix.os.name, matrix.java.version) }} \ No newline at end of file diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 00000000..6e90a72b --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,77 @@ +name: Release +on: + push: + tags: + - v1.3.[0-9]+ +concurrency: + group: ${{ github.workflow }}-${{ github.ref }} +jobs: + build-and-stage-release: + if: ${{ github.repository == 'spring-projects/spring-graphql' }} + name: Build and Stage Release + runs-on: ubuntu-latest + steps: + - name: Check Out Code + uses: actions/checkout@v4 + - name: Build and Publish + id: build-and-publish + uses: ./.github/actions/build-and-publish + with: + develocity-access-key: ${{ secrets.GRADLE_ENTERPRISE_SECRET_ACCESS_KEY }} + publish: true + - name: Stage Release + uses: spring-io/artifactory-deploy-action@26bbe925a75f4f863e1e529e85be2d0093cac116 # v0.0.1 + with: + build-name: ${{ format('spring-graphql-{0}', steps.build-and-publish.outputs.version)}} + folder: 'deployment-repository' + password: ${{ secrets.ARTIFACTORY_PASSWORD }} + repository: 'libs-staging-local' + signing-key: ${{ secrets.GPG_PRIVATE_KEY }} + signing-passphrase: ${{ secrets.GPG_PASSPHRASE }} + uri: 'https://repo.spring.io' + username: ${{ secrets.ARTIFACTORY_USERNAME }} + outputs: + version: ${{ steps.build-and-publish.outputs.version }} + sync-to-maven-central: + name: Sync to Maven Central + needs: + - build-and-stage-release + runs-on: ubuntu-latest + steps: + - name: Check Out Code + uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4.1.1 + - name: Sync to Maven Central + uses: ./.github/actions/sync-to-maven-central + with: + jfrog-cli-config-token: ${{ secrets.JF_ARTIFACTORY_SPRING }} + ossrh-s01-staging-profile: ${{ secrets.OSSRH_S01_STAGING_PROFILE }} + ossrh-s01-token-password: ${{ secrets.OSSRH_S01_TOKEN_PASSWORD }} + ossrh-s01-token-username: ${{ secrets.OSSRH_S01_TOKEN_USERNAME }} + spring-graphql-version: ${{ needs.build-and-stage-release.outputs.version }} + promote-release: + name: Promote Release + needs: + - build-and-stage-release + - sync-to-maven-central + runs-on: ubuntu-latest + steps: + - name: Set up JFrog CLI + uses: jfrog/setup-jfrog-cli@7c95feb32008765e1b4e626b078dfd897c4340ad # v4.1.2 + env: + JF_ENV_SPRING: ${{ secrets.JF_ARTIFACTORY_SPRING }} + - name: Promote build + run: jfrog rt build-promote ${{ format('spring-graphql-{0}', needs.build-and-stage-release.outputs.version)}} ${{ github.run_number }} libs-release-local + create-github-release: + name: Create GitHub Release + needs: + - build-and-stage-release + - promote-release + runs-on: ubuntu-latest + steps: + - name: Check Out Code + uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4.1.1 + - name: Create GitHub Release + uses: ./.github/actions/create-github-release + with: + milestone: ${{ needs.build-and-stage-release.outputs.version }} + token: ${{ secrets.GH_ACTIONS_REPO_TOKEN }} \ No newline at end of file diff --git a/ci/README.adoc b/ci/README.adoc deleted file mode 100644 index 24641d94..00000000 --- a/ci/README.adoc +++ /dev/null @@ -1,52 +0,0 @@ -== Spring for GraphQL Concourse pipeline - -The Spring for GraphQL project is using https://concourse-ci.org/[Concourse] for its CI build and other automated tasks. -The Spring team has a dedicated Concourse instance available at https://ci.spring.io. - -=== Setting up your development environment - -If you're part of the Spring for GraphQL team on GitHub, you can get access to CI management features. -First, you need to go to https://ci.spring.io and install the client CLI for your platform (see bottom right of the screen). - -You can then login with the instance using: - -[source] ----- -$ fly -t spring-graphql login -n spring-graphql -c https://ci.spring.io ----- - -Once logged in, you should get something like: - -[source] ----- -$ fly ts -name url team expiry -spring-graphql https://ci.spring.io spring-graphql Wed, 25 Mar 2020 17:45:26 UTC ----- - -=== Pipeline configuration and structure -The build pipelines are described in `pipeline.yml` file. -This file is listing Concourse resources, i.e. build inputs and outputs such as container images, artifact repositories, source repositories, notification services, etc. -It also describes jobs (a job is a sequence of inputs, tasks and outputs); jobs are organized by groups. - -The `pipeline.yml` definition contains `((parameters))` which are loaded from the `parameters.yml` file or from our https://www.vaultproject.io/[Vault instance]. - -You'll find in this folder the following resources: -* `pipeline.yml` the build pipeline -* `parameters.yml` the build parameters used for the pipeline -* `images/` holds the container images definitions used in this pipeline -* `scripts/` holds the build scripts that ship within the CI container images -* `tasks` contains the task definitions used in the main `pipeline.yml` -* `config` contains the Spring Boot configuration for the https://github.com/spring-io/github-changelog-generator[changelog generator] and https://github.com/spring-io/concourse-release-scripts[concourse-release-scripts] - -=== Updating the build pipeline - -Updating files on the repository is not enough to update the build pipeline, as changes need to be applied. -The pipeline can be deployed using the following command: - -[source] ----- -$ fly -t spring-graphql set-pipeline -p spring-graphql-1.1.x -c ci/pipeline.yml -l ci/parameters.yml ----- - -NOTE: This assumes that you have Vault configured with the appropriate secrets. \ No newline at end of file diff --git a/ci/config/release-scripts.yml b/ci/config/release-scripts.yml deleted file mode 100644 index e4ac9913..00000000 --- a/ci/config/release-scripts.yml +++ /dev/null @@ -1,10 +0,0 @@ -logging: - level: - io.spring.concourse: DEBUG -spring: - main: - banner-mode: off -sonatype: - exclude: - - 'build-info\.json' - - '.*spring-graphql-docs.*' \ No newline at end of file diff --git a/ci/images/README.adoc b/ci/images/README.adoc deleted file mode 100644 index 92fa3c2e..00000000 --- a/ci/images/README.adoc +++ /dev/null @@ -1,21 +0,0 @@ -== CI Images - -These images are used by CI to run the actual builds. - -To build the image locally run the following from this directory: - ----- -$ docker build --no-cache -f /Dockerfile . ----- - -For example - ----- -$ docker build --no-cache -f ci-image/Dockerfile . ----- - -To test run: - ----- -$ docker run -it --entrypoint /bin/bash ----- diff --git a/ci/images/ci-image/Dockerfile b/ci/images/ci-image/Dockerfile deleted file mode 100644 index d236ee88..00000000 --- a/ci/images/ci-image/Dockerfile +++ /dev/null @@ -1,11 +0,0 @@ -FROM ubuntu:jammy-20240111 - -ADD setup.sh /setup.sh -ADD get-jdk-url.sh /get-jdk-url.sh -ADD get-docker-url.sh /get-docker-url.sh -RUN ./setup.sh java17 - -ENV JAVA_HOME /opt/openjdk -ENV PATH $JAVA_HOME/bin:$PATH -ADD docker-lib.sh /bin/docker-lib.sh -ADD start-docker.sh /bin/start-docker.sh diff --git a/ci/images/docker-lib.sh b/ci/images/docker-lib.sh deleted file mode 100755 index eac9c2ee..00000000 --- a/ci/images/docker-lib.sh +++ /dev/null @@ -1,97 +0,0 @@ -# Based on: https://github.com/concourse/docker-image-resource/blob/master/assets/common.sh - -DOCKER_LOG_FILE=${DOCKER_LOG_FILE:-/tmp/docker.log} -SKIP_PRIVILEGED=${SKIP_PRIVILEGED:-false} -STARTUP_TIMEOUT=${STARTUP_TIMEOUT:-120} - -sanitize_cgroups() { - mkdir -p /sys/fs/cgroup - mountpoint -q /sys/fs/cgroup || \ - mount -t tmpfs -o uid=0,gid=0,mode=0755 cgroup /sys/fs/cgroup - - mount -o remount,rw /sys/fs/cgroup - - sed -e 1d /proc/cgroups | while read sys hierarchy num enabled; do - if [ "$enabled" != "1" ]; then - # subsystem disabled; skip - continue - fi - - grouping="$(cat /proc/self/cgroup | cut -d: -f2 | grep "\\<$sys\\>")" || true - if [ -z "$grouping" ]; then - # subsystem not mounted anywhere; mount it on its own - grouping="$sys" - fi - - mountpoint="/sys/fs/cgroup/$grouping" - - mkdir -p "$mountpoint" - - # clear out existing mount to make sure new one is read-write - if mountpoint -q "$mountpoint"; then - umount "$mountpoint" - fi - - mount -n -t cgroup -o "$grouping" cgroup "$mountpoint" - - if [ "$grouping" != "$sys" ]; then - if [ -L "/sys/fs/cgroup/$sys" ]; then - rm "/sys/fs/cgroup/$sys" - fi - - ln -s "$mountpoint" "/sys/fs/cgroup/$sys" - fi - done - - if ! test -e /sys/fs/cgroup/systemd ; then - mkdir /sys/fs/cgroup/systemd - mount -t cgroup -o none,name=systemd none /sys/fs/cgroup/systemd - fi -} - -start_docker() { - mkdir -p /var/log - mkdir -p /var/run - - if [ "$SKIP_PRIVILEGED" = "false" ]; then - sanitize_cgroups - - # check for /proc/sys being mounted readonly, as systemd does - if grep '/proc/sys\s\+\w\+\s\+ro,' /proc/mounts >/dev/null; then - mount -o remount,rw /proc/sys - fi - fi - - local mtu=$(cat /sys/class/net/$(ip route get 8.8.8.8|awk '{ print $5 }')/mtu) - local server_args="--mtu ${mtu}" - local registry="" - - server_args="${server_args}" - - if [ -n "$1" ]; then - server_args="${server_args} --registry-mirror https://$1" - fi - - try_start() { - dockerd --data-root /scratch/docker ${server_args} >$DOCKER_LOG_FILE 2>&1 & - echo $! > /tmp/docker.pid - - sleep 1 - - echo waiting for docker to come up... - until docker info >/dev/null 2>&1; do - sleep 1 - if ! kill -0 "$(cat /tmp/docker.pid)" 2>/dev/null; then - return 1 - fi - done - } - - export server_args DOCKER_LOG_FILE - declare -fx try_start - - if ! timeout ${STARTUP_TIMEOUT} bash -ce 'while true; do try_start && break; done'; then - echo Docker failed to start within ${STARTUP_TIMEOUT} seconds. - return 1 - fi -} diff --git a/ci/images/get-docker-url.sh b/ci/images/get-docker-url.sh deleted file mode 100755 index f3b07c39..00000000 --- a/ci/images/get-docker-url.sh +++ /dev/null @@ -1,5 +0,0 @@ -#!/bin/bash -set -e - -version="25.0.1" -echo "https://download.docker.com/linux/static/stable/x86_64/docker-$version.tgz"; \ No newline at end of file diff --git a/ci/images/get-jdk-url.sh b/ci/images/get-jdk-url.sh deleted file mode 100755 index 6e16e509..00000000 --- a/ci/images/get-jdk-url.sh +++ /dev/null @@ -1,14 +0,0 @@ -#!/bin/bash -set -e - -case "$1" in - java17) - echo "https://github.com/bell-sw/Liberica/releases/download/17.0.10+13/bellsoft-jdk17.0.10+13-linux-amd64.tar.gz" - ;; - java21) - echo "https://github.com/bell-sw/Liberica/releases/download/21.0.2+14/bellsoft-jdk21.0.2+14-linux-amd64.tar.gz" - ;; - *) - echo $"Unknown java version" - exit 1 -esac diff --git a/ci/images/setup.sh b/ci/images/setup.sh deleted file mode 100755 index 9fa58877..00000000 --- a/ci/images/setup.sh +++ /dev/null @@ -1,49 +0,0 @@ -#!/bin/bash -set -ex - -########################################################### -# UTILS -########################################################### - -export DEBIAN_FRONTEND=noninteractive -apt-get update -apt-get install --no-install-recommends -y tzdata ca-certificates net-tools libxml2-utils git curl libudev1 libxml2-utils iptables iproute2 jq -ln -fs /usr/share/zoneinfo/UTC /etc/localtime -dpkg-reconfigure --frontend noninteractive tzdata - -rm -rf /var/lib/apt/lists/* - -curl https://raw.githubusercontent.com/spring-io/concourse-java-scripts/v0.0.4/concourse-java.sh > /opt/concourse-java.sh - -########################################################### -# JAVA -########################################################### -JDK_URL=$( ./get-jdk-url.sh $1 ) - -mkdir -p /opt/openjdk -cd /opt/openjdk -curl -L ${JDK_URL} | tar zx --strip-components=1 -test -f /opt/openjdk/bin/java -test -f /opt/openjdk/bin/javac - -########################################################### -# DOCKER -########################################################### -cd / -DOCKER_URL=$( ./get-docker-url.sh ) -curl -L ${DOCKER_URL} | tar zx -mv /docker/* /bin/ -chmod +x /bin/docker* - -export ENTRYKIT_VERSION=0.4.0 -curl -L https://github.com/progrium/entrykit/releases/download/v${ENTRYKIT_VERSION}/entrykit_${ENTRYKIT_VERSION}_Linux_x86_64.tgz | tar zx -chmod +x entrykit && \ -mv entrykit /bin/entrykit && \ -entrykit --symlink - -########################################################### -# GRADLE ENTERPRISE -########################################################### -cd / -mkdir ~/.gradle -echo 'systemProp.user.name=concourse' > ~/.gradle/gradle.properties diff --git a/ci/images/start-docker.sh b/ci/images/start-docker.sh deleted file mode 100755 index 292aef3b..00000000 --- a/ci/images/start-docker.sh +++ /dev/null @@ -1,4 +0,0 @@ -#!/usr/bin/env bash - -source /bin/docker-lib.sh -start_docker \ No newline at end of file diff --git a/ci/pipeline.yml b/ci/pipeline.yml deleted file mode 100644 index 482a04b2..00000000 --- a/ci/pipeline.yml +++ /dev/null @@ -1,290 +0,0 @@ -anchors: - docker-hub-task-params: &docker-hub-task-params - DOCKER_HUB_USERNAME: ((docker-hub-username)) - DOCKER_HUB_PASSWORD: ((docker-hub-password)) - registry-image-resource-source: ®istry-image-resource-source - username: ((docker-hub-username)) - password: ((docker-hub-password)) - gradle-enterprise-task-params: &gradle-enterprise-task-params - GRADLE_ENTERPRISE_ACCESS_KEY: ((gradle_enterprise_secret_access_key)) - GRADLE_ENTERPRISE_CACHE_USERNAME: ((gradle_enterprise_cache_user.username)) - GRADLE_ENTERPRISE_CACHE_PASSWORD: ((gradle_enterprise_cache_user.password)) - artifactory-task-params: &artifactory-task-params - ARTIFACTORY_SERVER: ((artifactory-server)) - ARTIFACTORY_USERNAME: ((artifactory-username)) - ARTIFACTORY_PASSWORD: ((artifactory-password)) - sonatype-task-params: &sonatype-task-params - SONATYPE_USERNAME: ((s01-user-token)) - SONATYPE_PASSWORD: ((s01-user-token-password)) - SONATYPE_URL: ((sonatype-url)) - SONATYPE_STAGING_PROFILE: ((sonatype-staging-profile)) - -resource_types: -- name: registry-image - type: registry-image - source: - <<: *registry-image-resource-source - repository: concourse/registry-image-resource - tag: 1.9.0 -- name: artifactory-resource - type: registry-image - source: - <<: *registry-image-resource-source - repository: springio/artifactory-resource - tag: 0.0.18 -- name: github-release - type: registry-image - source: - <<: *registry-image-resource-source - repository: concourse/github-release-resource - tag: 1.9.0 - -resources: -- name: git-repo - type: git - icon: github - source: - uri: ((github-repo)) - username: ((github-username)) - password: ((github-ci-release-token)) - branch: ((branch)) -- name: ci-images-git-repo - type: git - icon: github - source: - uri: ((github-repo)) - branch: ((branch)) - paths: ["ci/images/*"] -- name: ci-image - type: registry-image - icon: docker - source: - <<: *registry-image-resource-source - tag: ((milestone)) - repository: ((docker-hub-organization))/spring-graphql-ci-image -- name: artifactory-repo - type: artifactory-resource - icon: package-variant - source: - uri: ((artifactory-server)) - username: ((artifactory-username)) - password: ((artifactory-password)) - build_name: ((build-name)) -- name: github-pre-release - type: github-release - icon: briefcase-download-outline - source: - owner: spring-projects - repository: spring-graphql - access_token: ((github-ci-release-token)) - pre_release: true - release: false -- name: github-release - type: github-release - icon: briefcase-download-outline - source: - owner: spring-projects - repository: spring-graphql - access_token: ((github-ci-release-token)) - pre_release: false - -jobs: -- name: build-ci-images - plan: - - get: git-repo - - get: ci-images-git-repo - trigger: true - - task: build-ci-image - privileged: true - file: git-repo/ci/tasks/build-ci-image.yml - output_mapping: - image: ci-image - vars: - ci-image-name: ci-image - <<: *registry-image-resource-source - - put: ci-image - params: - image: ci-image/image.tar -- name: stage-milestone - serial: true - plan: - - get: ci-image - - get: git-repo - trigger: false - - task: stage - image: ci-image - file: git-repo/ci/tasks/stage-version.yml - params: - RELEASE_TYPE: M - <<: *gradle-enterprise-task-params - - put: artifactory-repo - params: &artifactory-params - signing_key: ((signing-key)) - signing_passphrase: ((signing-passphrase)) - folder: distribution-repository - build_uri: "https://ci.spring.io/teams/${BUILD_TEAM_NAME}/pipelines/${BUILD_PIPELINE_NAME}/jobs/${BUILD_JOB_NAME}/builds/${BUILD_NAME}" - build_number: "${BUILD_PIPELINE_NAME}-${BUILD_JOB_NAME}-${BUILD_NAME}" - disable_checksum_uploads: true - threads: 8 - artifact_set: - - include: - - "/**/spring-graphql-docs-*.zip" - properties: - "zip.name": "spring-graphql" - "zip.displayname": "Spring for GraphQL" - "zip.deployed": "false" - "zip.type": "docs" - repo: libs-staging-local - - put: git-repo - params: - repository: stage-git-repo -- name: promote-milestone - serial: true - plan: - - get: ci-image - - get: git-repo - trigger: false - - get: artifactory-repo - trigger: false - passed: [stage-milestone] - params: - download_artifacts: false - save_build_info: true - - task: promote - file: git-repo/ci/tasks/promote-version.yml - params: - RELEASE_TYPE: M - <<: *artifactory-task-params - <<: *registry-image-resource-source - - task: generate-changelog - file: git-repo/ci/tasks/generate-changelog.yml - params: - RELEASE_TYPE: M - GITHUB_USERNAME: ((github-username)) - GITHUB_TOKEN: ((github-ci-release-token)) - vars: - <<: *registry-image-resource-source - - put: github-pre-release - params: - name: generated-changelog/tag - tag: generated-changelog/tag - body: generated-changelog/changelog.md -- name: stage-rc - serial: true - plan: - - get: ci-image - - get: git-repo - trigger: false - - task: stage - image: ci-image - file: git-repo/ci/tasks/stage-version.yml - params: - RELEASE_TYPE: RC - <<: *gradle-enterprise-task-params - - put: artifactory-repo - params: - <<: *artifactory-params - repo: libs-staging-local - - put: git-repo - params: - repository: stage-git-repo -- name: promote-rc - serial: true - plan: - - get: ci-image - - get: git-repo - trigger: false - - get: artifactory-repo - trigger: false - passed: [stage-rc] - params: - download_artifacts: false - save_build_info: true - - task: promote - file: git-repo/ci/tasks/promote-version.yml - params: - RELEASE_TYPE: RC - <<: *artifactory-task-params - <<: *registry-image-resource-source - - task: generate-changelog - file: git-repo/ci/tasks/generate-changelog.yml - params: - RELEASE_TYPE: RC - GITHUB_USERNAME: ((github-username)) - GITHUB_TOKEN: ((github-ci-release-token)) - vars: - <<: *registry-image-resource-source - - put: github-pre-release - params: - name: generated-changelog/tag - tag: generated-changelog/tag - body: generated-changelog/changelog.md -- name: stage-release - serial: true - plan: - - get: ci-image - - get: git-repo - trigger: false - - task: stage - image: ci-image - file: git-repo/ci/tasks/stage-version.yml - params: - RELEASE_TYPE: RELEASE - <<: *gradle-enterprise-task-params - - put: artifactory-repo - params: - <<: *artifactory-params - repo: libs-staging-local - - put: git-repo - params: - repository: stage-git-repo -- name: promote-release - serial: true - plan: - - get: ci-image - - get: git-repo - trigger: false - - get: artifactory-repo - trigger: false - passed: [stage-release] - params: - download_artifacts: true - save_build_info: true - - task: promote - file: git-repo/ci/tasks/promote-version.yml - params: - RELEASE_TYPE: RELEASE - <<: *artifactory-task-params - <<: *registry-image-resource-source - <<: *sonatype-task-params -- name: create-github-release - serial: true - plan: - - get: ci-image - - get: git-repo - - get: artifactory-repo - trigger: true - passed: [promote-release] - params: - download_artifacts: false - save_build_info: true - - task: generate-changelog - file: git-repo/ci/tasks/generate-changelog.yml - params: - RELEASE_TYPE: RELEASE - GITHUB_USERNAME: ((github-username)) - GITHUB_TOKEN: ((github-ci-release-token)) - vars: - <<: *registry-image-resource-source - - put: github-release - params: - name: generated-changelog/tag - tag: generated-changelog/tag - body: generated-changelog/changelog.md - - -groups: -- name: "releases" - jobs: [ "stage-milestone", "promote-milestone", "stage-rc", "promote-rc", "stage-release", "promote-release", "create-github-release" ] -- name: "ci-images" - jobs: ["build-ci-images"] diff --git a/ci/scripts/common.sh b/ci/scripts/common.sh deleted file mode 100644 index 1accaa61..00000000 --- a/ci/scripts/common.sh +++ /dev/null @@ -1,2 +0,0 @@ -source /opt/concourse-java.sh -setup_symlinks \ No newline at end of file diff --git a/ci/scripts/generate-changelog.sh b/ci/scripts/generate-changelog.sh deleted file mode 100755 index 16c70919..00000000 --- a/ci/scripts/generate-changelog.sh +++ /dev/null @@ -1,12 +0,0 @@ -#!/bin/bash -set -e - -CONFIG_DIR=git-repo/ci/config -version=$( cat artifactory-repo/build-info.json | jq -r '.buildInfo.modules[0].id' | sed 's/.*:.*:\(.*\)/\1/' ) - -java -jar /github-changelog-generator.jar \ - --spring.config.location=${CONFIG_DIR}/changelog-generator.yml \ - ${version} generated-changelog/changelog.md - -echo ${version} > generated-changelog/version -echo v${version} > generated-changelog/tag \ No newline at end of file diff --git a/ci/scripts/promote-version.sh b/ci/scripts/promote-version.sh deleted file mode 100755 index 2b932f5f..00000000 --- a/ci/scripts/promote-version.sh +++ /dev/null @@ -1,18 +0,0 @@ -#!/bin/bash - -source $(dirname $0)/common.sh -CONFIG_DIR=git-repo/ci/config - -version=$( cat artifactory-repo/build-info.json | jq -r '.buildInfo.modules[0].id' | sed 's/.*:.*:\(.*\)/\1/' ) -export BUILD_INFO_LOCATION=$(pwd)/artifactory-repo/build-info.json - -java -jar /concourse-release-scripts.jar \ - --spring.config.location=${CONFIG_DIR}/release-scripts.yml \ - publishToCentral $RELEASE_TYPE $BUILD_INFO_LOCATION artifactory-repo || { exit 1; } - -java -jar /concourse-release-scripts.jar \ - --spring.config.location=${CONFIG_DIR}/release-scripts.yml \ - promote $RELEASE_TYPE $BUILD_INFO_LOCATION || { exit 1; } - -echo "Promotion complete" -echo $version > version/version diff --git a/ci/scripts/stage-version.sh b/ci/scripts/stage-version.sh deleted file mode 100755 index 73c57755..00000000 --- a/ci/scripts/stage-version.sh +++ /dev/null @@ -1,50 +0,0 @@ -#!/bin/bash -set -e - -source $(dirname $0)/common.sh -repository=$(pwd)/distribution-repository - -pushd git-repo > /dev/null -git fetch --tags --all > /dev/null -popd > /dev/null - -git clone git-repo stage-git-repo > /dev/null - -pushd stage-git-repo > /dev/null - -snapshotVersion=$( awk -F '=' '$1 == "version" { print $2 }' gradle.properties ) -if [[ $RELEASE_TYPE = "M" ]]; then - stageVersion=$( get_next_milestone_release $snapshotVersion) - nextVersion=$snapshotVersion -elif [[ $RELEASE_TYPE = "RC" ]]; then - stageVersion=$( get_next_rc_release $snapshotVersion) - nextVersion=$snapshotVersion -elif [[ $RELEASE_TYPE = "RELEASE" ]]; then - stageVersion=$( get_next_release $snapshotVersion) - nextVersion=$( bump_version_number $snapshotVersion) -else - echo "Unknown release type $RELEASE_TYPE" >&2; exit 1; -fi - -echo "Staging $stageVersion (next version will be $nextVersion)" -sed -i "s/version=$snapshotVersion/version=$stageVersion/" gradle.properties - -git config user.name "Spring Builds" > /dev/null -git config user.email "spring-builds@users.noreply.github.com" > /dev/null -git add gradle.properties > /dev/null -git commit -m"Release v$stageVersion" > /dev/null -git tag -a "v$stageVersion" -m"Release v$stageVersion" > /dev/null - -./gradlew --no-daemon --max-workers=4 -PdeploymentRepository=${repository} build publishAllPublicationsToDeploymentRepository - -git reset --hard HEAD^ > /dev/null -if [[ $nextVersion != $snapshotVersion ]]; then - echo "Setting next development version (v$nextVersion)" - sed -i "s/version=$snapshotVersion/version=$nextVersion/" gradle.properties - git add gradle.properties > /dev/null - git commit -m"Next development version (v$nextVersion)" > /dev/null -fi; - -echo "Staging Complete" - -popd > /dev/null diff --git a/ci/tasks/build-ci-image.yml b/ci/tasks/build-ci-image.yml deleted file mode 100644 index a7744ac4..00000000 --- a/ci/tasks/build-ci-image.yml +++ /dev/null @@ -1,29 +0,0 @@ ---- -platform: linux -image_resource: - type: registry-image - source: - repository: concourse/oci-build-task - tag: 0.11.1 - username: ((docker-hub-username)) - password: ((docker-hub-password)) -inputs: - - name: ci-images-git-repo -outputs: - - name: image -caches: - - path: ci-image-cache -params: - CONTEXT: ci-images-git-repo/ci/images - DOCKERFILE: ci-images-git-repo/ci/images/((ci-image-name))/Dockerfile - DOCKER_HUB_AUTH: ((docker-hub-auth)) -run: - path: /bin/sh - args: - - "-c" - - | - mkdir -p /root/.docker - cat > /root/.docker/config.json <