From c8b3a4111713bdff5f0b5ed31577faa5a4e860ac Mon Sep 17 00:00:00 2001 From: Andrey Antukh Date: Tue, 14 Oct 2025 19:02:05 +0200 Subject: [PATCH] :paperclip: Backport all github workflows from develop --- .github/PULL_REQUEST_TEMPLATE.md | 1 + .github/workflows/build-bundle.yml | 16 +--- .github/workflows/build-develop.yml | 11 ++- .github/workflows/build-docker-devenv.yml | 36 ++++++++ .github/workflows/build-docker.yml | 101 ++++++++++++++++++++++ .github/workflows/build-staging.yml | 11 ++- .github/workflows/build-tag.yml | 19 +++- .github/workflows/commit-checker.yml | 2 +- .github/workflows/release.yml | 95 ++++++++++++++++++++ 9 files changed, 273 insertions(+), 19 deletions(-) create mode 100644 .github/workflows/build-docker-devenv.yml create mode 100644 .github/workflows/build-docker.yml create mode 100644 .github/workflows/release.yml diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md index 70b6bb00df..58ed9335f4 100644 --- a/.github/PULL_REQUEST_TEMPLATE.md +++ b/.github/PULL_REQUEST_TEMPLATE.md @@ -13,6 +13,7 @@ - [ ] Add a detailed explanation of how to reproduce the issue and/or verify the fix, if applicable. - [ ] Include screenshots or videos, if applicable. - [ ] Add or modify existing integration tests in case of bugs or new features, if applicable. +- [ ] Refactor any modified SCSS files following the refactor guide. - [ ] Check CI passes successfully. - [ ] Update the `CHANGES.md` file, referencing the related GitHub issue, if applicable. diff --git a/.github/workflows/build-bundle.yml b/.github/workflows/build-bundle.yml index ab7f007f4e..764cc980c0 100644 --- a/.github/workflows/build-bundle.yml +++ b/.github/workflows/build-bundle.yml @@ -1,11 +1,11 @@ -name: Build and Upload Penpot Bundle +name: Bundles Builder on: # Create bundle from manual action workflow_dispatch: inputs: gh_ref: - description: 'Name of the branch' + description: 'Name of the branch or ref' type: string required: true default: 'develop' @@ -22,7 +22,7 @@ on: workflow_call: inputs: gh_ref: - description: 'Name of the branch' + description: 'Name of the branch or ref' type: string required: true default: 'develop' @@ -56,10 +56,9 @@ jobs: - name: Extract some useful variables id: vars run: | - echo "commit_hash=$(git rev-parse --short HEAD)" >> $GITHUB_OUTPUT echo "gh_ref=${{ inputs.gh_ref || github.ref_name }}" >> $GITHUB_OUTPUT - - name: Run manage.sh build-bundle from host + - name: Build bundle env: BUILD_WASM: ${{ inputs.build_wasm }} BUILD_STORYBOOK: ${{ inputs.build_storybook }} @@ -76,13 +75,6 @@ jobs: zip -r zips/penpot.zip penpot - name: Upload Penpot bundle to S3 - if: github.ref_type == 'branch' - run: | - aws s3 cp zips/penpot.zip s3://${{ secrets.S3_BUCKET }}/penpot-${{ steps.vars.outputs.gh_ref }}-latest.zip - aws s3 cp zips/penpot.zip s3://${{ secrets.S3_BUCKET }}/penpot-${{ steps.vars.outputs.commit_hash }}.zip - - - name: Upload Penpot bundle to S3 - if: github.ref_type == 'tag' run: | aws s3 cp zips/penpot.zip s3://${{ secrets.S3_BUCKET }}/penpot-${{ steps.vars.outputs.gh_ref }}.zip diff --git a/.github/workflows/build-develop.yml b/.github/workflows/build-develop.yml index 098db1290f..aecf9a37eb 100644 --- a/.github/workflows/build-develop.yml +++ b/.github/workflows/build-develop.yml @@ -1,14 +1,21 @@ -name: DEVELOP - Build and Upload Penpot Bundle +name: _DEVELOP on: schedule: - cron: '16 5-20 * * 1-5' jobs: - build-develop-bundle: + build-bundle: uses: ./.github/workflows/build-bundle.yml secrets: inherit with: gh_ref: "develop" build_wasm: "yes" build_storybook: "yes" + + build-docker: + needs: build-bundle + uses: ./.github/workflows/build-docker.yml + secrets: inherit + with: + gh_ref: "develop" diff --git a/.github/workflows/build-docker-devenv.yml b/.github/workflows/build-docker-devenv.yml new file mode 100644 index 0000000000..3d5bae1d12 --- /dev/null +++ b/.github/workflows/build-docker-devenv.yml @@ -0,0 +1,36 @@ +name: DevEnv Docker Image Builder + +on: + workflow_dispatch: + +jobs: + build-and-push: + name: Build and push DevEnv Docker image + environment: release-admins + runs-on: ubuntu-24.04 + + steps: + - name: Checkout code + uses: actions/checkout@v4 + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + + - name: Login to Docker Registry + uses: docker/login-action@v3 + with: + username: ${{ secrets.PUB_DOCKER_USERNAME }} + password: ${{ secrets.PUB_DOCKER_PASSWORD }} + + - name: Build and push DevEnv Docker image + uses: docker/build-push-action@v6 + env: + DOCKER_IMAGE: 'penpotapp/devenv' + with: + context: ./docker/devenv/ + file: ./docker/devenv/Dockerfile + platforms: linux/amd64,linux/arm64 + push: true + tags: ${{ env.DOCKER_IMAGE }}:latest + cache-from: type=registry,ref=${{ env.DOCKER_IMAGE }}:buildcache + cache-to: type=registry,ref=${{ env.DOCKER_IMAGE }}:buildcache,mode=max diff --git a/.github/workflows/build-docker.yml b/.github/workflows/build-docker.yml new file mode 100644 index 0000000000..4665e618a9 --- /dev/null +++ b/.github/workflows/build-docker.yml @@ -0,0 +1,101 @@ +name: Docker Images Builder + +on: + workflow_dispatch: + inputs: + gh_ref: + description: 'Name of the branch or ref' + type: string + required: true + default: 'develop' + workflow_call: + inputs: + gh_ref: + description: 'Name of the branch or ref' + type: string + required: true + default: 'develop' + +jobs: + build-and-push: + name: Build and Push Penpot Docker Images + runs-on: ubuntu-24.04-arm + + steps: + - name: Checkout code + uses: actions/checkout@v4 + with: + fetch-depth: 0 + ref: ${{ inputs.gh_ref }} + + - name: Extract some useful variables + id: vars + run: | + echo "gh_ref=${{ inputs.gh_ref || github.ref_name }}" >> $GITHUB_OUTPUT + + - name: Download Penpot Bundles + env: + FILE_NAME: penpot-${{ steps.vars.outputs.gh_ref }}.zip + AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }} + AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }} + AWS_DEFAULT_REGION: ${{ secrets.AWS_REGION }} + run: | + pushd docker/images + aws s3 cp s3://${{ secrets.S3_BUCKET }}/$FILE_NAME . + unzip $FILE_NAME > /dev/null + mv penpot/backend bundle-backend + mv penpot/frontend bundle-frontend + mv penpot/exporter bundle-exporter + popd + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + + - name: Login to Docker Registry + uses: docker/login-action@v3 + with: + registry: ${{ secrets.DOCKER_REGISTRY }} + username: ${{ secrets.DOCKER_USERNAME }} + password: ${{ secrets.DOCKER_PASSWORD }} + + - name: Build and push Backend Docker image + uses: docker/build-push-action@v6 + env: + DOCKER_IMAGE: 'backend' + BUNDLE_PATH: './bundle-backend' + with: + context: ./docker/images/ + file: ./docker/images/Dockerfile.backend + platforms: linux/amd64,linux/arm64 + push: true + tags: ${{ secrets.DOCKER_REGISTRY }}/${{ env.DOCKER_IMAGE }}:${{ steps.vars.outputs.gh_ref }} + cache-from: type=registry,ref=${{ secrets.DOCKER_REGISTRY }}/${{ env.DOCKER_IMAGE }}:buildcache + cache-to: type=registry,ref=${{ secrets.DOCKER_REGISTRY }}/${{ env.DOCKER_IMAGE }}:buildcache,mode=max + + - name: Build and push Frontend Docker image + uses: docker/build-push-action@v6 + env: + DOCKER_IMAGE: 'frontend' + BUNDLE_PATH: './bundle-frontend' + with: + context: ./docker/images/ + file: ./docker/images/Dockerfile.frontend + platforms: linux/amd64,linux/arm64 + push: true + tags: ${{ secrets.DOCKER_REGISTRY }}/${{ env.DOCKER_IMAGE }}:${{ steps.vars.outputs.gh_ref }} + cache-from: type=registry,ref=${{ secrets.DOCKER_REGISTRY }}/${{ env.DOCKER_IMAGE }}:buildcache + cache-to: type=registry,ref=${{ secrets.DOCKER_REGISTRY }}/${{ env.DOCKER_IMAGE }}:buildcache,mode=max + + - name: Build and push Exporter Docker image + uses: docker/build-push-action@v6 + env: + DOCKER_IMAGE: 'exporter' + BUNDLE_PATH: './bundle-exporter' + with: + context: ./docker/images/ + file: ./docker/images/Dockerfile.exporter + platforms: linux/amd64,linux/arm64 + push: true + tags: ${{ secrets.DOCKER_REGISTRY }}/${{ env.DOCKER_IMAGE }}:${{ steps.vars.outputs.gh_ref }} + cache-from: type=registry,ref=${{ secrets.DOCKER_REGISTRY }}/${{ env.DOCKER_IMAGE }}:buildcache + cache-to: type=registry,ref=${{ secrets.DOCKER_REGISTRY }}/${{ env.DOCKER_IMAGE }}:buildcache,mode=max diff --git a/.github/workflows/build-staging.yml b/.github/workflows/build-staging.yml index 5c81e8ca60..1c5d48d02e 100644 --- a/.github/workflows/build-staging.yml +++ b/.github/workflows/build-staging.yml @@ -1,14 +1,21 @@ -name: STAGING - Build and Upload Penpot Bundle +name: _STAGING on: schedule: - cron: '36 5-20 * * 1-5' jobs: - build-staging-bundle: + build-bundle: uses: ./.github/workflows/build-bundle.yml secrets: inherit with: gh_ref: "staging" build_wasm: "yes" build_storybook: "yes" + + build-docker: + needs: build-bundle + uses: ./.github/workflows/build-docker.yml + secrets: inherit + with: + gh_ref: "staging" diff --git a/.github/workflows/build-tag.yml b/.github/workflows/build-tag.yml index f64819160b..9f5bc8a512 100644 --- a/.github/workflows/build-tag.yml +++ b/.github/workflows/build-tag.yml @@ -1,4 +1,4 @@ -name: TAG - Build and Upload Penpot Bundle +name: _TAG on: push: @@ -6,10 +6,25 @@ on: - '*' jobs: - build-tag-bundle: + build-bundle: uses: ./.github/workflows/build-bundle.yml secrets: inherit with: gh_ref: ${{ github.ref_name }} build_wasm: "no" build_storybook: "yes" + + build-docker: + needs: build-bundle + uses: ./.github/workflows/build-docker.yml + secrets: inherit + with: + gh_ref: ${{ github.ref_name }} + + publish-final-tag: + if: ${{ !contains(github.ref_name, '-RC') && !contains(github.ref_name, '-alpha') && !contains(github.ref_name, '-beta') && contains(github.ref_name, '.') }} + needs: build-docker + uses: ./.github/workflows/release.yml + secrets: inherit + with: + gh_ref: ${{ github.ref_name }} diff --git a/.github/workflows/commit-checker.yml b/.github/workflows/commit-checker.yml index a5f51b7c38..7918c23395 100644 --- a/.github/workflows/commit-checker.yml +++ b/.github/workflows/commit-checker.yml @@ -26,7 +26,7 @@ jobs: - name: Check Commit Type uses: gsactions/commit-message-checker@v2 with: - pattern: '^(Merge|Revert|:(lipstick|globe_with_meridians|wrench|books|arrow_up|arrow_down|zap|ambulance|construction|boom|fire|whale|bug|sparkles|paperclip|tada|recycle|rewind):)\s[A-Z].*[^.]$' + pattern: '^(Merge|Revert|:(lipstick|globe_with_meridians|wrench|books|arrow_up|arrow_down|zap|ambulance|construction|boom|fire|whale|bug|sparkles|paperclip|tada|recycle|rewind):)\s["A-Z].*[^.]$' flags: 'gm' error: 'Commit should match CONTRIBUTING.md guideline' checkAllCommitMessages: 'true' # optional: this checks all commits associated with a pull request diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 0000000000..206bbadbb0 --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,95 @@ +name: Release Publisher + +on: + workflow_dispatch: + inputs: + gh_ref: + description: 'Tag to release' + type: string + required: true + workflow_call: + inputs: + gh_ref: + description: 'Tag to release' + type: string + required: true + +permissions: + contents: write + +jobs: + release: + environment: release-admins + runs-on: ubuntu-24.04 + outputs: + version: ${{ steps.vars.outputs.gh_ref }} + release_notes: ${{ steps.extract_release_notes.outputs.release_notes }} + steps: + - name: Extract some useful variables + id: vars + run: | + echo "gh_ref=${{ inputs.gh_ref || github.ref_name }}" >> $GITHUB_OUTPUT + + - name: Checkout code + uses: actions/checkout@v4 + with: + fetch-depth: 0 + ref: ${{ steps.vars.outputs.gh_ref }} + + # --- Publicly release the docker images --- + - name: Login to private registry + uses: docker/login-action@v3 + with: + registry: ${{ secrets.DOCKER_REGISTRY }} + username: ${{ secrets.DOCKER_USERNAME }} + password: ${{ secrets.DOCKER_PASSWORD }} + + - name: Login to DockerHub + uses: docker/login-action@v3 + with: + username: ${{ secrets.PUB_DOCKER_USERNAME }} + password: ${{ secrets.PUB_DOCKER_PASSWORD }} + + - name: Publish docker images to DockerHub + env: + TAG: ${{ steps.vars.outputs.gh_ref }} + REGISTRY: ${{ secrets.DOCKER_REGISTRY }} + HUB: ${{ secrets.PUB_DOCKER_HUB }} + run: | + IMAGES=("frontend" "backend" "exporter") + EXTRA_TAGS=("main" "latest") + + for image in "${IMAGES[@]}"; do + docker pull "$REGISTRY/penpotapp/$image:$TAG" + docker tag "$REGISTRY/penpotapp/$image:$TAG" "penpotapp/$image:$TAG" + docker push "penpotapp/$image:$TAG" + + for tag in "${EXTRA_TAGS[@]}"; do + docker tag "$REGISTRY/penpotapp/$image:$TAG" "penpotapp/$image:$tag" + docker push "penpotapp/$image:$tag" + done + done + + # --- Release notes extraction --- + - name: Extract release notes from CHANGES.md + id: extract_release_notes + env: + TAG: ${{ steps.vars.outputs.gh_ref }} + run: | + RELEASE_NOTES=$(awk "/^## $TAG$/{flag=1; next} /^## /{flag=0} flag" CHANGES.md | awk '{$1=$1};1') + if [ -z "$RELEASE_NOTES" ]; then + RELEASE_NOTES="No changes for $TAG according to CHANGES.md" + fi + echo "release_notes<> $GITHUB_OUTPUT + echo "$RELEASE_NOTES" >> $GITHUB_OUTPUT + echo "EOF" >> $GITHUB_OUTPUT + + # --- Create GitHub release --- + - name: Create GitHub release + uses: softprops/action-gh-release@v1 + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + with: + tag_name: ${{ steps.vars.outputs.gh_ref }} + name: ${{ steps.vars.outputs.gh_ref }} + body: ${{ steps.extract_release_notes.outputs.release_notes }}