Publish #107
Workflow file for this run
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: Publish | |
| on: | |
| release: | |
| types: [published] | |
| jobs: | |
| find-artifacts: | |
| name: Find CI artifacts | |
| runs-on: ubuntu-latest | |
| permissions: | |
| actions: read | |
| contents: read | |
| outputs: | |
| ci-run-id: ${{ steps.find.outputs.run-id }} | |
| needs-build: ${{ steps.find.outputs.needs-build }} | |
| steps: | |
| - name: Find successful CI run for release target | |
| id: find | |
| env: | |
| GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
| TARGET: ${{ github.event.release.target_commitish }} | |
| shell: bash | |
| run: | | |
| # Resolve branch name or tag to a commit SHA | |
| SHA=$(gh api "repos/$GITHUB_REPOSITORY/commits/$TARGET" --jq '.sha' 2>/dev/null || echo "$TARGET") | |
| echo "Resolved target '$TARGET' to SHA: $SHA" | |
| # Find the most recent successful CI run for this SHA that has a build artifact | |
| RUN_ID=$(gh api "repos/$GITHUB_REPOSITORY/actions/workflows/ci.yml/runs" \ | |
| -F "head_sha=$SHA" \ | |
| -F "status=success" \ | |
| -F "per_page=10" \ | |
| --jq '.workflow_runs[].id') || { | |
| echo "::error::Failed to query CI workflow runs. If ci.yml was renamed, update the reference in the find-artifacts job in publish.yml." | |
| exit 1 | |
| } | |
| USABLE_RUN_ID="" | |
| for ID in $RUN_ID; do | |
| HAS_ARTIFACT=$(gh api "repos/$GITHUB_REPOSITORY/actions/runs/$ID/artifacts" \ | |
| --jq '[.artifacts[] | select(.name == "build" and .expired == false)] | length') | |
| if [ "$HAS_ARTIFACT" -gt 0 ]; then | |
| USABLE_RUN_ID="$ID" | |
| break | |
| fi | |
| done | |
| if [ -z "$USABLE_RUN_ID" ]; then | |
| echo "No successful CI run with a valid build artifact found for SHA $SHA. A fresh build will be triggered." | |
| echo "run-id=" >> "$GITHUB_OUTPUT" | |
| echo "needs-build=true" >> "$GITHUB_OUTPUT" | |
| else | |
| echo "Found suitable CI run: $USABLE_RUN_ID" | |
| echo "run-id=$USABLE_RUN_ID" >> "$GITHUB_OUTPUT" | |
| echo "needs-build=false" >> "$GITHUB_OUTPUT" | |
| fi | |
| build: | |
| name: Build (no prior CI run found) | |
| needs: find-artifacts | |
| if: ${{ needs.find-artifacts.outputs.needs-build == 'true' }} | |
| uses: ./.github/workflows/ci.yml | |
| with: | |
| force-full-build: true | |
| cd: | |
| name: Publish to npm | |
| needs: | |
| - find-artifacts | |
| - build | |
| # Run if find-artifacts succeeded AND (build succeeded OR build was skipped because artifacts already exist) | |
| if: ${{ !cancelled() && needs.find-artifacts.result == 'success' && (needs.build.result == 'success' || needs.build.result == 'skipped') }} | |
| runs-on: ubuntu-latest | |
| permissions: | |
| actions: read # to download artifacts from the CI run | |
| contents: write # to push the version commit and tag | |
| issues: write # to comment on issues when a fix is released | |
| pull-requests: write # to comment on PRs when a fix is released | |
| env: | |
| NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} | |
| steps: | |
| - name: Debug info | |
| # https://docs.github.com/en/actions/reference/security/secure-use#use-an-intermediate-environment-variable | |
| env: | |
| # `env:` values are printed to the log even without using them in `run:` | |
| RELEASE_TAG_NAME: ${{ github.event.release.tag_name }} | |
| RELEASE_TARGET_COMMITISH: ${{ github.event.release.target_commitish }} | |
| run: | | |
| cat <<EOF | |
| Release tag name: $RELEASE_TAG_NAME | |
| Release target commit-ish: $RELEASE_TARGET_COMMITISH | |
| EOF | |
| - name: Determine NPM tag | |
| shell: bash | |
| env: | |
| TARGET_COMMITISH: ${{ github.event.release.target_commitish }} | |
| IS_PRERELEASE: ${{ github.event.release.prerelease }} | |
| run: | | |
| case "$TARGET_COMMITISH" in | |
| develop | main | master) | |
| if [[ "$IS_PRERELEASE" == true ]]; then | |
| npm_tag=beta | |
| else | |
| npm_tag=latest | |
| fi | |
| ;; | |
| *) | |
| # use the branch name as the npm tag | |
| npm_tag="$TARGET_COMMITISH" | |
| ;; | |
| esac | |
| echo "Determined NPM tag: [$npm_tag]" | |
| echo "NPM_TAG=${npm_tag}" >> "$GITHUB_ENV" | |
| - name: Check NPM tag | |
| run: | | |
| if [ -z "$NPM_TAG" ]; then | |
| echo "Refusing to publish with empty NPM tag." | |
| exit 1 | |
| fi | |
| - name: Config GitHub user | |
| shell: bash | |
| run: | | |
| git config --global user.name 'GitHub Actions' | |
| git config --global user.email 'github-actions@localhost' | |
| - uses: actions/checkout@08c6903cd8c0fde910a37f88322edcfb5dd907a8 # v5 | |
| with: | |
| token: ${{ secrets.PAT_RELEASE_PUSH }} # persists the token for pushing to the repo later | |
| - uses: actions/setup-node@2028fbc5c25fe9cf00d9f06a71cc4710d4507903 # v6 | |
| with: | |
| cache: 'npm' | |
| node-version-file: '.nvmrc' | |
| registry-url: 'https://registry.npmjs.org' | |
| - uses: ./.github/actions/install-dependencies | |
| - name: Download build artifacts (from previous CI run) | |
| if: ${{ needs.build.result == 'skipped' }} | |
| uses: actions/download-artifact@018cc2cf5baa6db3ef3c5f8a56943fffe632ef53 # v6 | |
| with: | |
| name: build | |
| path: packages | |
| run-id: ${{ needs.find-artifacts.outputs.ci-run-id }} | |
| github-token: ${{ secrets.GITHUB_TOKEN }} | |
| - name: Download build artifacts (from fallback build in this run) | |
| if: ${{ needs.build.result == 'success' }} | |
| uses: actions/download-artifact@018cc2cf5baa6db3ef3c5f8a56943fffe632ef53 # v6 | |
| with: | |
| name: build | |
| path: packages | |
| - name: Update the version in the package files | |
| shell: bash | |
| env: | |
| GIT_TAG: ${{ github.event.release.tag_name }} | |
| run: | | |
| NEW_VERSION="${GIT_TAG/v/}" | |
| npm version "$NEW_VERSION" --no-git-tag-version | |
| git add package* && git commit -m "chore(release): $NEW_VERSION [skip ci]" | |
| - name: Publish scratch-svg-renderer | |
| run: npm publish --access=public --tag="$NPM_TAG" --ignore-scripts --workspace=@scratch/scratch-svg-renderer | |
| - name: Publish scratch-render | |
| run: npm publish --access=public --tag="$NPM_TAG" --ignore-scripts --workspace=@scratch/scratch-render | |
| - name: Publish scratch-vm | |
| run: npm publish --access=public --tag="$NPM_TAG" --ignore-scripts --workspace=@scratch/scratch-vm | |
| - name: Publish scratch-gui | |
| run: | | |
| cp ./packages/scratch-gui/package.json ./packages/scratch-gui/package-copy.json | |
| jq 'del(.exports["./standalone"])' ./packages/scratch-gui/package.json | npx sponge ./packages/scratch-gui/package.json | |
| npm publish --access=public --tag="$NPM_TAG" --ignore-scripts --workspace=@scratch/scratch-gui | |
| mv ./packages/scratch-gui/package-copy.json ./packages/scratch-gui/package.json | |
| - name: Publish scratch-gui-standalone | |
| run: | | |
| bash ./scripts/prepare-standalone-gui.sh | |
| npm publish --access=public --tag="$NPM_TAG" --ignore-scripts --workspace=@scratch/scratch-gui-standalone | |
| - name: Publish task-herder | |
| run: npm publish --access=public --tag="$NPM_TAG" --ignore-scripts --workspace=@scratch/task-herder | |
| - name: Publish scratch-media-lib-scripts | |
| run: | | |
| npm run build --workspace @scratch/scratch-media-lib-scripts | |
| npm publish --access=public --tag="${{steps.npm_tag.outputs.npm_tag}}" --workspace=@scratch/scratch-media-lib-scripts | |
| env: | |
| NODE_AUTH_TOKEN: ${{secrets.NPM_TOKEN}} | |
| - name: Push to develop | |
| shell: bash | |
| env: | |
| TAG_NAME: ${{ github.event.release.tag_name }} | |
| run: | | |
| git fetch origin develop | |
| LAST_COMMIT_ID="$(git rev-parse "$TAG_NAME")" | |
| DEVELOP_COMMIT_ID="$(git rev-parse origin/develop)" | |
| if [ "$LAST_COMMIT_ID" = "$DEVELOP_COMMIT_ID" ]; then | |
| git push origin HEAD:develop | |
| else | |
| echo "Not pushing to develop because the tag we're operating on is behind" | |
| fi | |
| - name: Comment on resolved issues and merged PRs | |
| if: ${{ !github.event.release.prerelease }} | |
| uses: apexskier/github-release-commenter@e7813a9625eabd79a875b4bc4046cfcae377ab34 # v1 | |
| with: | |
| GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
| comment-template: | | |
| :tada: This is included in release {release_link}. | |
| # See https://stackoverflow.com/a/24849501 | |
| - name: Change connected commit on release | |
| shell: bash | |
| env: | |
| TAG_NAME: ${{ github.event.release.tag_name }} | |
| run: | | |
| git tag -f "$TAG_NAME" HEAD | |
| git push -f origin "refs/tags/$TAG_NAME" |