diff --git a/.github/workflows/build-desktop-dev.yml b/.github/workflows/build-desktop-dev.yml new file mode 100644 index 00000000..2d631ec1 --- /dev/null +++ b/.github/workflows/build-desktop-dev.yml @@ -0,0 +1,201 @@ +name: Build Desktop (Dev) + +# 开发阶段构建 — 不创建 Release,只上传 Artifacts 供下载测试 +on: + workflow_dispatch: + inputs: + platforms: + description: 'Build platforms' + required: true + default: 'all' + type: choice + options: + - all + - macos-arm64 + - macos-x64 + - windows-x64 + - linux-x64 + - linux-arm64 + +permissions: + contents: read + +concurrency: + group: build-desktop-dev-${{ github.ref }} + cancel-in-progress: true + +jobs: + # ── 动态生成构建矩阵 ────────────────────────────────────── + prepare: + runs-on: ubuntu-latest + outputs: + matrix: ${{ steps.set-matrix.outputs.matrix }} + steps: + - id: set-matrix + run: | + ALL='[ + {"platform":"macos-latest","rust_target":"aarch64-apple-darwin","tauri_args":"--target aarch64-apple-darwin","bundles":"app,dmg","label":"macOS-ARM64","artifact_name":"desktop-macos-arm64","artifact_glob":"*.dmg"}, + {"platform":"macos-latest","rust_target":"x86_64-apple-darwin","tauri_args":"--target x86_64-apple-darwin","bundles":"app,dmg","label":"macOS-x64","artifact_name":"desktop-macos-x64","artifact_glob":"*.dmg"}, + {"platform":"windows-latest","rust_target":"x86_64-pc-windows-msvc","tauri_args":"","bundles":"nsis,msi","label":"Windows-x64","artifact_name":"desktop-windows-x64","artifact_glob":"*.exe"}, + {"platform":"ubuntu-22.04","rust_target":"x86_64-unknown-linux-gnu","tauri_args":"","bundles":"deb,appimage","label":"Linux-x64","artifact_name":"desktop-linux-x64","artifact_glob":"*.deb"}, + {"platform":"ubuntu-22.04-arm","rust_target":"aarch64-unknown-linux-gnu","tauri_args":"","bundles":"deb,appimage","label":"Linux-ARM64","artifact_name":"desktop-linux-arm64","artifact_glob":"*.deb"} + ]' + + SELECTED="${{ inputs.platforms }}" + if [ "$SELECTED" = "all" ]; then + echo "matrix={\"include\":$ALL}" >> "$GITHUB_OUTPUT" + else + echo "$ALL" | jq -c --arg sel "$SELECTED" \ + '{include: [.[] | select( + ($sel == "macos-arm64" and .label == "macOS-ARM64") or + ($sel == "macos-x64" and .label == "macOS-x64") or + ($sel == "windows-x64" and .label == "Windows-x64") or + ($sel == "linux-x64" and .label == "Linux-x64") or + ($sel == "linux-arm64" and .label == "Linux-ARM64") + )]}' >> "$GITHUB_OUTPUT" + fi + + # ── 构建 ──────────────────────────────────────────────────── + build: + needs: prepare + strategy: + fail-fast: false + matrix: ${{ fromJson(needs.prepare.outputs.matrix) }} + + runs-on: ${{ matrix.platform }} + name: Build (${{ matrix.label }}) + + steps: + - name: Checkout + uses: actions/checkout@v4 + + # ── 系统依赖 (Linux) ───────────────────────────────────── + - name: Install Linux dependencies + if: contains(matrix.platform, 'ubuntu') + run: | + sudo apt-get update + sudo apt-get install -y \ + build-essential curl wget file \ + libxdo-dev libssl-dev \ + libwebkit2gtk-4.1-dev \ + libayatana-appindicator3-dev \ + librsvg2-dev patchelf + + # ── Bun ────────────────────────────────────────────────── + - name: Setup Bun + uses: oven-sh/setup-bun@v2 + with: + bun-version: latest + + # ── Node.js ────────────────────────────────────────────── + - name: Setup Node.js + uses: actions/setup-node@v4 + with: + node-version: 20 + + # ── Rust ───────────────────────────────────────────────── + - name: Setup Rust + uses: dtolnay/rust-toolchain@stable + with: + targets: ${{ matrix.rust_target }} + + - name: Rust cache + uses: swatinem/rust-cache@v2 + with: + workspaces: 'desktop/src-tauri -> target' + shared-key: ${{ matrix.rust_target }} + + # ── 安装依赖 ───────────────────────────────────────────── + - name: Install root dependencies + run: bun install + + - name: Install desktop dependencies + working-directory: desktop + run: bun install + + # ── 构建 sidecars ──────────────────────────────────────── + - name: Build sidecars + working-directory: desktop + env: + TAURI_ENV_TARGET_TRIPLE: ${{ matrix.rust_target }} + run: bun run build:sidecars + + # ── 构建 Tauri (无签名、无 updater) ────────────────────── + - name: Build Tauri app + working-directory: desktop + env: + TAURI_ENV_TARGET_TRIPLE: ${{ matrix.rust_target }} + run: | + # 开发构建: 禁用 updater artifacts (不需要签名密钥) + echo '{"bundle":{"createUpdaterArtifacts":false}}' > /tmp/dev-build.json + + ARGS=(bunx tauri build --bundles ${{ matrix.bundles }} --ci --config /tmp/dev-build.json) + + if [ -n "${{ matrix.tauri_args }}" ]; then + ARGS+=(${{ matrix.tauri_args }}) + fi + + "${ARGS[@]}" + shell: bash + + # ── 收集产物 ───────────────────────────────────────────── + - name: Collect artifacts + id: collect + shell: bash + run: | + BUNDLE_DIR="desktop/src-tauri/target/${{ matrix.rust_target }}/release/bundle" + FALLBACK_DIR="desktop/src-tauri/target/release/bundle" + + # 优先使用带 target 的路径 + if [ -d "$BUNDLE_DIR" ]; then + SEARCH_DIR="$BUNDLE_DIR" + else + SEARCH_DIR="$FALLBACK_DIR" + fi + + STAGING="desktop/build-artifacts/ci-${{ matrix.artifact_name }}" + mkdir -p "$STAGING" + + echo "Searching for artifacts in: $SEARCH_DIR" + if [ -d "$SEARCH_DIR" ]; then + find "$SEARCH_DIR" -type f \( \ + -name "*.dmg" -o -name "*.app" -o \ + -name "*.exe" -o -name "*.msi" -o \ + -name "*.deb" -o -name "*.AppImage" -o \ + -name "*.zip" \ + \) | while read -r f; do + echo " Copying: $(basename "$f")" + cp "$f" "$STAGING/" + done + fi + + echo "staging_dir=$STAGING" >> "$GITHUB_OUTPUT" + echo "=== Collected artifacts ===" + ls -lh "$STAGING/" 2>/dev/null || echo "(empty)" + + # ── 上传为 GitHub Artifact ─────────────────────────────── + - name: Upload artifacts + uses: actions/upload-artifact@v4 + with: + name: ${{ matrix.artifact_name }} + path: ${{ steps.collect.outputs.staging_dir }} + retention-days: 7 + if-no-files-found: warn + + # ── 构建完成汇总 ──────────────────────────────────────────── + summary: + needs: build + runs-on: ubuntu-latest + if: always() + steps: + - name: Build summary + run: | + echo "## Desktop Dev Build Summary" >> $GITHUB_STEP_SUMMARY + echo "" >> $GITHUB_STEP_SUMMARY + echo "| Platform | Status |" >> $GITHUB_STEP_SUMMARY + echo "|----------|--------|" >> $GITHUB_STEP_SUMMARY + echo "Branch: \`${{ github.ref_name }}\`" >> $GITHUB_STEP_SUMMARY + echo "Commit: \`${{ github.sha }}\`" >> $GITHUB_STEP_SUMMARY + echo "" >> $GITHUB_STEP_SUMMARY + echo "📦 Artifacts are available for download from the **Artifacts** section above." >> $GITHUB_STEP_SUMMARY + echo "Artifacts will be retained for **7 days**." >> $GITHUB_STEP_SUMMARY