Zip Folders On Release #180
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: Zip Folders On Release | |
| on: | |
| push: | |
| tags: | |
| - "v*" | |
| release: | |
| types: [published] | |
| permissions: | |
| contents: write | |
| jobs: | |
| zip-and-upload: | |
| if: github.event_name != 'release' || github.event.sender.login != 'github-actions[bot]' | |
| runs-on: ubuntu-latest | |
| concurrency: | |
| group: release-${{ github.event_name == 'release' && github.event.release.tag_name || github.ref_name }} | |
| cancel-in-progress: false | |
| env: | |
| TAG_NAME: ${{ github.event_name == 'release' && github.event.release.tag_name || github.ref_name }} | |
| steps: | |
| - name: Checkout repository | |
| uses: actions/checkout@v4 | |
| with: | |
| fetch-depth: 0 | |
| ref: ${{ env.TAG_NAME }} | |
| - name: Prepare release metadata | |
| shell: bash | |
| run: | | |
| set -euo pipefail | |
| VERSION="${TAG_NAME#v}" | |
| export VERSION | |
| echo "VERSION=${VERSION}" >> "$GITHUB_ENV" | |
| echo "Release tag: ${TAG_NAME}" | |
| echo "Normalized version: ${VERSION}" | |
| - name: Update script.json versions | |
| shell: bash | |
| run: | | |
| set -euo pipefail | |
| python3 - <<'PY' | |
| import json | |
| import os | |
| version = os.environ["VERSION"] | |
| updated = 0 | |
| for root, _, files in os.walk("."): | |
| if "script.json" not in files: | |
| continue | |
| path = os.path.join(root, "script.json") | |
| with open(path, "r", encoding="utf-8") as f: | |
| data = json.load(f) | |
| data["version"] = version | |
| with open(path, "w", encoding="utf-8") as f: | |
| json.dump(data, f, ensure_ascii=False, indent=2) | |
| f.write("\n") | |
| updated += 1 | |
| print(f"Updated {path}") | |
| print(f"Updated {updated} script.json file(s).") | |
| PY | |
| - name: Create zip archives for each top-level folder | |
| shell: bash | |
| run: | | |
| set -euo pipefail | |
| mkdir -p dist | |
| for dir in */; do | |
| folder="${dir%/}" | |
| # Skip metadata, build output, and source folders. | |
| if [[ "$folder" == ".github" || "$folder" == "dist" || "$folder" == "src" ]]; then | |
| continue | |
| fi | |
| echo "Zipping $folder -> dist/${folder}.zip" | |
| zip -r "dist/${folder}.zip" "$folder" | |
| done | |
| echo "Generated archives:" | |
| ls -lh dist | |
| - name: Generate release notes | |
| shell: bash | |
| env: | |
| GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
| run: | | |
| set -euo pipefail | |
| mapfile -t TAGS < <(git tag --list 'v*' --sort=-version:refname) | |
| PREVIOUS_TAG="" | |
| for i in "${!TAGS[@]}"; do | |
| if [[ "${TAGS[$i]}" == "$TAG_NAME" ]]; then | |
| NEXT_INDEX=$((i + 1)) | |
| if [[ "$NEXT_INDEX" -lt "${#TAGS[@]}" ]]; then | |
| PREVIOUS_TAG="${TAGS[$NEXT_INDEX]}" | |
| fi | |
| break | |
| fi | |
| done | |
| NOTES_FILE="release-notes.md" | |
| { | |
| echo "## 更新内容" | |
| echo | |
| if [[ -n "$PREVIOUS_TAG" ]]; then | |
| echo "基于 \`$PREVIOUS_TAG\` 到 \`$TAG_NAME\` 的提交:" | |
| echo | |
| else | |
| echo "首个版本,包含以下提交:" | |
| echo | |
| fi | |
| } > "$NOTES_FILE" | |
| if [[ -n "$PREVIOUS_TAG" ]]; then | |
| gh api "repos/${GITHUB_REPOSITORY}/compare/${PREVIOUS_TAG}...${TAG_NAME}" > compare.json | |
| python3 - <<'PY' | |
| import json | |
| import os | |
| repo = os.environ["GITHUB_REPOSITORY"] | |
| notes_file = "release-notes.md" | |
| with open("compare.json", "r", encoding="utf-8") as f: | |
| data = json.load(f) | |
| commits = data.get("commits", []) | |
| with open(notes_file, "a", encoding="utf-8") as f: | |
| if commits: | |
| for commit in commits: | |
| sha = commit["sha"] | |
| short_sha = sha[:7] | |
| message = commit["commit"]["message"].splitlines()[0] | |
| f.write(f"- {message} ([{short_sha}](https://github.com/{repo}/commit/{sha}))\n") | |
| else: | |
| f.write("- No commits found.\n") | |
| PY | |
| else | |
| COMMITS="$(git log --reverse --pretty=format:"- %s ([%h](https://github.com/${GITHUB_REPOSITORY}/commit/%H))" "$TAG_NAME" || true)" | |
| if [[ -n "$COMMITS" ]]; then | |
| printf '%s\n' "$COMMITS" >> "$NOTES_FILE" | |
| else | |
| echo "- No commits found." >> "$NOTES_FILE" | |
| fi | |
| fi | |
| if [[ -n "$PREVIOUS_TAG" ]]; then | |
| { | |
| echo | |
| echo "**完整对比**: https://github.com/${GITHUB_REPOSITORY}/compare/${PREVIOUS_TAG}...${TAG_NAME}" | |
| } >> "$NOTES_FILE" | |
| fi | |
| echo "Release notes preview:" | |
| cat "$NOTES_FILE" | |
| - name: Create or update GitHub release | |
| shell: bash | |
| env: | |
| GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
| run: | | |
| set -euo pipefail | |
| if gh release view "$TAG_NAME" >/dev/null 2>&1; then | |
| gh release edit "$TAG_NAME" --title "$TAG_NAME" --notes-file release-notes.md | |
| gh release upload "$TAG_NAME" dist/*.zip --clobber | |
| else | |
| gh release create "$TAG_NAME" dist/*.zip --title "$TAG_NAME" --notes-file release-notes.md | |
| fi |