Revert: ci: adjust cache key #28
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: Build Selene | |
| on: | |
| push: | |
| tags: | |
| - 'v*' | |
| workflow_dispatch: | |
| concurrency: | |
| group: ${{ github.workflow }}-${{ github.ref }} | |
| cancel-in-progress: true | |
| permissions: | |
| contents: write | |
| actions: write | |
| jobs: | |
| build: | |
| strategy: | |
| matrix: | |
| include: | |
| # Android | |
| - name: android | |
| os: ubuntu-latest | |
| build-args: "--android-only" | |
| # macOS / iOS | |
| - name: macos_ios | |
| os: macos-latest | |
| build-args: "--apple-only" | |
| # Windows | |
| - name: windows-amd64 | |
| os: windows-latest | |
| runs-on: ${{ matrix.os }} | |
| env: | |
| NDK_VERSION: '29.0.14033849' | |
| NDK_VERSION_DEPS: '27.0.12077973' | |
| name: Build ${{ matrix.name }} | |
| outputs: | |
| version: ${{ steps.get_version.outputs.version }} | |
| steps: | |
| - name: Clone repository | |
| run: | | |
| git clone https://${{ secrets.PULL_TOKEN }}@${{ secrets.REPO_URL }}.git . | |
| shell: bash | |
| - name: Get version from pubspec.yaml | |
| id: get_version | |
| run: | | |
| if [ "$RUNNER_OS" == "Windows" ]; then | |
| VERSION=$(powershell -Command "(Get-Content pubspec.yaml | Select-String '^version:' | ForEach-Object {\$_ -replace 'version: ', ''}).trim()") | |
| else | |
| VERSION=$(grep '^version:' pubspec.yaml | sed 's/version: //' | tr -d ' ') | |
| fi | |
| VERSION=$(echo "$VERSION" | cut -d'+' -f1) | |
| echo "version=$VERSION" >> $GITHUB_OUTPUT | |
| echo "Extracted version: $VERSION" | |
| shell: bash | |
| - name: Setup Flutter | |
| uses: subosito/flutter-action@v2 | |
| with: | |
| cache: true | |
| - name: Install Java | |
| if: matrix.name == 'android' | |
| uses: actions/setup-java@v5 | |
| with: | |
| distribution: 'zulu' | |
| java-version: 21 | |
| - name: Setup Android SDK | |
| if: matrix.name == 'android' | |
| uses: android-actions/setup-android@v3 | |
| - name: Cache Gradle | |
| if: matrix.name == 'android' | |
| uses: actions/cache@v4 | |
| with: | |
| path: | | |
| ~/.gradle/caches | |
| ~/.gradle/wrapper | |
| android/.gradle | |
| key: ${{ runner.os }}-gradle-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }} | |
| restore-keys: | | |
| ${{ runner.os }}-gradle- | |
| - name: Cache NDK | |
| if: matrix.name == 'android' | |
| id: cache-ndk | |
| uses: actions/cache@v4 | |
| with: | |
| path: | | |
| ${{ env.ANDROID_HOME }}/ndk/${{ env.NDK_VERSION }} | |
| ${{ env.ANDROID_HOME }}/ndk/${{ env.NDK_VERSION_DEPS }} | |
| key: ${{ runner.os }}-ndk-${{ env.NDK_VERSION }}-${{ env.NDK_VERSION_DEPS }} | |
| - name: Install NDK | |
| if: matrix.name == 'android' && steps.cache-ndk.outputs.cache-hit != 'true' | |
| run: | | |
| echo "y" | sdkmanager --install "ndk;${{ env.NDK_VERSION }}" | |
| echo "y" | sdkmanager --install "ndk;${{ env.NDK_VERSION_DEPS }}" | |
| - name: Write sign info | |
| if: matrix.name == 'android' | |
| run: | | |
| if [ ! -z "${{ secrets.SIGNING_KEY }}" ]; then | |
| echo "Writing signing configuration..." | |
| echo ${{ secrets.SIGNING_KEY }} | base64 --decode > ${{ github.workspace }}/key.jks | |
| cat > android/key.properties << EOF | |
| storePassword=${{ secrets.KEY_STORE_PASSWORD }} | |
| keyPassword=${{ secrets.KEY_PASSWORD }} | |
| keyAlias=${{ secrets.ALIAS }} | |
| storeFile=${{ github.workspace }}/key.jks | |
| EOF | |
| echo "Signing configuration written successfully" | |
| cat android/key.properties | |
| else | |
| echo "WARNING: SIGNING_KEY secret is not set!" | |
| fi | |
| shell: bash | |
| - name: Build with build.sh (Android/macOS/iOS) | |
| if: matrix.name != 'windows-amd64' | |
| continue-on-error: true | |
| run: | | |
| chmod +x build.sh | |
| ./build.sh ${{ matrix.build-args }} | |
| shell: bash | |
| - name: Build on Windows | |
| if: matrix.name == 'windows-amd64' | |
| continue-on-error: true | |
| shell: pwsh | |
| run: | | |
| $version = "${{ steps.get_version.outputs.version }}" | |
| Write-Host "Building version: $version" -ForegroundColor Green | |
| flutter pub get | |
| New-Item -ItemType Directory -Force -Path dist | Out-Null | |
| Write-Host "Building Windows..." -ForegroundColor Blue | |
| flutter build windows --release | |
| Compress-Archive -Path build/windows/x64/runner/Release/* -DestinationPath "dist/selene-$version-windows-x64-portable.zip" -Force | |
| Write-Host "Windows build complete" -ForegroundColor Green | |
| - name: Upload artifacts | |
| uses: actions/upload-artifact@v4 | |
| continue-on-error: true | |
| with: | |
| name: ${{ matrix.name }}-release-artifacts | |
| path: dist/* | |
| create-release: | |
| needs: build | |
| runs-on: ubuntu-latest | |
| name: Create Release | |
| if: startsWith(github.ref, 'refs/tags/') | |
| env: | |
| TZ: Asia/Shanghai | |
| steps: | |
| - uses: actions/checkout@v4 | |
| - name: Download all artifacts | |
| uses: actions/download-artifact@v4 | |
| with: | |
| path: all-artifacts | |
| - name: Prepare release artifacts | |
| run: | | |
| mkdir -p release-files | |
| find all-artifacts -type f -exec cp {} release-files/ \; | |
| ls -lh release-files/ | |
| - name: Get version from tag | |
| id: tag_version | |
| run: | | |
| VERSION="${GITHUB_REF#refs/tags/}" | |
| echo "version=$VERSION" >> $GITHUB_OUTPUT | |
| echo "Release version: $VERSION" | |
| - name: Create Release | |
| uses: softprops/action-gh-release@v1 | |
| with: | |
| tag_name: ${{ steps.tag_version.outputs.version }} | |
| name: Selene ${{ steps.tag_version.outputs.version }} | |
| files: release-files/* | |
| draft: false | |
| prerelease: false | |
| fail_on_unmatched_files: false | |
| env: | |
| GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
| - name: Get Release Notes | |
| id: release_notes | |
| run: | | |
| RELEASE_INFO=$(curl -s -H "Authorization: token ${{ secrets.GITHUB_TOKEN }}" \ | |
| "https://api.github.com/repos/${{ github.repository }}/releases/tags/${{ steps.tag_version.outputs.version }}") | |
| RELEASE_BODY=$(echo "$RELEASE_INFO" | python3 -c "import sys, json; data=json.load(sys.stdin); print(data.get('body', '') if 'body' in data else '')") | |
| { | |
| echo 'notes<<EOF' | |
| echo "$RELEASE_BODY" | |
| echo EOF | |
| } >> $GITHUB_OUTPUT | |
| echo "Release notes length: ${#RELEASE_BODY}" | |
| - name: Send Telegram notification | |
| if: success() | |
| env: | |
| CHANNEL_ID: ${{ secrets.TELEGRAM_CHAT_ID }} | |
| BOT_TOKEN: ${{ secrets.TELEGRAM_BOT_TOKEN }} | |
| run: | | |
| if [ ! -d "release-files" ] || [ -z "$(ls -A release-files)" ]; then | |
| echo "No release files found" | |
| exit 0 | |
| fi | |
| VERSION="${{ steps.tag_version.outputs.version }}" | |
| RELEASE_URL="https://github.com/${{ github.repository }}/releases/tag/${VERSION}" | |
| TIMESTAMP=$(date '+%Y-%m-%d %H:%M:%S') | |
| RELEASE_NOTES=$(cat << 'NOTES_EOF' | |
| ${{ steps.release_notes.outputs.notes }} | |
| NOTES_EOF | |
| ) | |
| echo "开始上传文件到 Telegram..." | |
| FILE_IDS=() | |
| MESSAGE_IDS=() | |
| for file in release-files/*; do | |
| if [ -f "$file" ]; then | |
| filename=$(basename "$file") | |
| if [[ ! "$filename" =~ \.(apk|ipa)$ ]]; then | |
| echo "跳过文件: $filename" | |
| continue | |
| fi | |
| RESPONSE=$(curl -s -X POST "https://api.telegram.org/bot${BOT_TOKEN}/sendDocument" \ | |
| -F "chat_id=${CHANNEL_ID}" \ | |
| -F "document=@${file}") | |
| FILE_ID=$(echo "$RESPONSE" | python3 -c "import sys, json; data=json.load(sys.stdin); print(data['result']['document']['file_id'] if 'result' in data else '')" 2>/dev/null) | |
| MESSAGE_ID=$(echo "$RESPONSE" | python3 -c "import sys, json; data=json.load(sys.stdin); print(data['result']['message_id'] if 'result' in data else '')" 2>/dev/null) | |
| if [ ! -z "$FILE_ID" ]; then | |
| FILE_IDS+=("$FILE_ID") | |
| MESSAGE_IDS+=("$MESSAGE_ID") | |
| fi | |
| sleep 1 | |
| fi | |
| done | |
| if [ ${#FILE_IDS[@]} -gt 0 ]; then | |
| echo "准备发送 media group..." | |
| FILE_IDS_JSON=$(printf '%s\n' "${FILE_IDS[@]}" | jq -R . | jq -s .) | |
| export FILE_IDS_JSON VERSION RELEASE_URL TIMESTAMP RELEASE_NOTES | |
| python3 << 'PYEOF' > media.json | |
| import json | |
| import os | |
| file_ids = json.loads(os.environ['FILE_IDS_JSON']) | |
| version = os.environ['VERSION'] | |
| release_url = os.environ['RELEASE_URL'] | |
| timestamp = os.environ['TIMESTAMP'] | |
| release_notes = os.environ.get('RELEASE_NOTES', '').strip() | |
| message = f"""🎉 *Selene 新版本发布*""" | |
| if release_notes: | |
| if len(release_notes) > 800: | |
| release_notes = release_notes[:800] + "..." | |
| message += f"\n\n📝 *更新说明*:\n{release_notes}" | |
| message += f""" | |
| 📦 版本: `{version}` | |
| 🔗 GitHub: [点击查看]({release_url}) | |
| 💡 Windows 及 MacOS 包请自行前往 Releases 处下载 | |
| 🕐 发布于: {timestamp}""" | |
| media = [] | |
| for idx, file_id in enumerate(file_ids): | |
| item = { | |
| "type": "document", | |
| "media": file_id | |
| } | |
| if idx == len(file_ids) - 1: | |
| item["caption"] = message | |
| item["parse_mode"] = "Markdown" | |
| media.append(item) | |
| print(json.dumps(media)) | |
| PYEOF | |
| curl -s -X POST "https://api.telegram.org/bot${BOT_TOKEN}/sendMediaGroup" \ | |
| -H "Content-Type: application/json" \ | |
| -d "{\"chat_id\":\"${CHANNEL_ID}\",\"media\":$(cat media.json)}" | |
| for msg_id in "${MESSAGE_IDS[@]}"; do | |
| curl -s -X POST "https://api.telegram.org/bot${BOT_TOKEN}/deleteMessage" \ | |
| -d "chat_id=${CHANNEL_ID}" \ | |
| -d "message_id=${msg_id}" > /dev/null | |
| done | |
| fi | |
| cleanup: | |
| runs-on: ubuntu-latest | |
| needs: build | |
| steps: | |
| - name: Delete workflow runs | |
| uses: Mattraks/delete-workflow-runs@main | |
| with: | |
| token: ${{ secrets.GITHUB_TOKEN }} | |
| repository: ${{ github.repository }} | |
| retain_days: 0 | |
| keep_minimum_runs: 2 |