name: Reusable Release Workflow on: workflow_call: inputs: snapshot: description: "Run as a snapshot release" required: true type: boolean secrets: DOCKERHUB_USERNAME: required: false DOCKERHUB_TOKEN: required: false HOMEBREW_GITHUB_TOKEN: required: false jobs: goreleaser: permissions: contents: write packages: write runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 with: fetch-depth: 0 - name: Set up QEMU uses: docker/setup-qemu-action@v3 - name: Set up Docker Buildx uses: docker/setup-buildx-action@v3 - name: Set up Go uses: actions/setup-go@v4 with: go-version: "1.25" - name: Setup NodeJS uses: actions/setup-node@v4 with: node-version: "20" - name: Setup pnpm uses: pnpm/action-setup@v4 with: version: 9 - name: Login to Docker Hub if: ${{ !inputs.snapshot }} uses: docker/login-action@v3 with: username: ${{ secrets.DOCKERHUB_USERNAME }} password: ${{ secrets.DOCKERHUB_TOKEN }} - name: Login to GHCR if: ${{ !inputs.snapshot }} uses: docker/login-action@v3 with: registry: ghcr.io username: ${{ github.actor }} password: ${{ secrets.GITHUB_TOKEN }} - name: Run GoReleaser uses: goreleaser/goreleaser-action@v7 with: distribution: goreleaser version: latest args: ${{ inputs.snapshot && 'release --snapshot --clean' || 'release --clean' }} env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} HOMEBREW_GITHUB_TOKEN: ${{ secrets.HOMEBREW_GITHUB_TOKEN }} - name: Upload Build Artifacts uses: actions/upload-artifact@v4 with: name: release-builds path: | dist/*.tar.gz dist/*.zip installer: name: Windows installers needs: [goreleaser] runs-on: windows-latest permissions: contents: write steps: - name: Checkout uses: actions/checkout@v4 with: fetch-depth: 0 - name: Download build artifacts uses: actions/download-artifact@v4 with: name: release-builds - name: Download restic shell: powershell run: | # Get the latest release from GitHub API $latest = Invoke-RestMethod -Uri "https://api.github.com/repos/restic/restic/releases/latest" $tag = $latest.tag_name if ($tag.StartsWith("v")) { $tag = $tag.Substring(1) } Write-Host "Latest restic version: $tag" # Function to download and unzip function Download-Restic { param ( [string]$arch, [string]$resticArch ) $url = "https://github.com/restic/restic/releases/download/v$tag/restic_${tag}_windows_${resticArch}.zip" $output = "restic_${tag}_windows_${resticArch}.zip" Write-Host "Downloading $url..." try { Invoke-WebRequest -Uri $url -OutFile $output Expand-Archive $output -DestinationPath . -Force # Find the extracted exe (it might be in a subdir or just in root of zip) $extracted = Get-ChildItem -Recurse -Filter "restic*.exe" | Where-Object { $_.FullName -like "*${tag}_windows_${resticArch}*" } | Select-Object -First 1 if ($extracted) { Move-Item $extracted.FullName -Destination "restic_${arch}.exe" -Force Write-Host "Successfully prepared restic_${arch}.exe" } else { Write-Error "Could not find extracted executable for $arch" } } catch { Write-Warning "Failed to download or extract for ${arch}: $_" } } Download-Restic -arch "x86_64" -resticArch "amd64" - name: Unzip artifacts and compile Inno Setup installers shell: powershell run: | mkdir windows_installers foreach ($arch in "x86_64") { $src = "backrest_Windows_$arch" Expand-Archive ".\${src}.zip" cp build\windows\* $src cp "restic_${arch}.exe" "${src}\restic.exe" & "c:\Program Files (x86)\Inno Setup 6\ISCC.exe" /DArch=$arch ${src}\installer.iss cp "$src\Output\*" windows_installers } - name: Upload Installers as Artifacts if: ${{ inputs.snapshot }} uses: actions/upload-artifact@v4 with: name: backrest-snapshot-installers path: windows_installers\*.exe - name: Upload Installers to Release if: ${{ !inputs.snapshot && startsWith(github.ref, 'refs/tags/') }} uses: softprops/action-gh-release@v2 with: files: | ./windows_installers/* macos-bundle: name: macOS app bundle (${{ matrix.goarch }}) runs-on: macos-latest permissions: contents: write strategy: matrix: goarch: [amd64, arm64] steps: - uses: actions/checkout@v4 - uses: actions/setup-go@v4 with: go-version: "1.25" - uses: actions/setup-node@v4 with: node-version: "20" - uses: pnpm/action-setup@v4 with: version: 9 - name: Build web UI run: | cd webui && pnpm install && pnpm run build - name: Get version id: version run: | if [[ "$GITHUB_REF" == refs/tags/v* ]]; then echo "version=${GITHUB_REF_NAME#v}" >> "$GITHUB_OUTPUT" else echo "version=0.0.0-snapshot-${GITHUB_SHA::8}" >> "$GITHUB_OUTPUT" fi - name: Build binary env: CGO_ENABLED: "1" GOARCH: ${{ matrix.goarch }} run: | go build -tags tray \ -ldflags "-s -w -X main.version=${{ steps.version.outputs.version }} -X main.commit=${{ github.sha }}" \ -o backrest ./cmd/backrest/ - name: Create app bundle run: ./build/darwin/bundle.sh ./backrest ${{ steps.version.outputs.version }} - name: Compute arch name id: arch run: | if [ "${{ matrix.goarch }}" = "amd64" ]; then echo "name=x86_64" >> "$GITHUB_OUTPUT" else echo "name=${{ matrix.goarch }}" >> "$GITHUB_OUTPUT" fi - name: Package bundle run: | zip -r "backrest_Darwin_${{ steps.arch.outputs.name }}.zip" Backrest.app - name: Upload as artifact if: ${{ inputs.snapshot }} uses: actions/upload-artifact@v4 with: name: backrest-macos-${{ steps.arch.outputs.name }} path: "backrest_Darwin_${{ steps.arch.outputs.name }}.zip" - name: Upload to release if: ${{ !inputs.snapshot && startsWith(github.ref, 'refs/tags/') }} uses: softprops/action-gh-release@v2 with: files: "backrest_Darwin_${{ steps.arch.outputs.name }}.zip"