name: Go Release

on:
  repository_dispatch:
    types: [tag_created]
  push:
    tags:
      - "v*"

jobs:
  test:
    name: Run tests
    runs-on: ubuntu-latest
    permissions:
      contents: read
    steps:
      - name: Checkout code
        uses: actions/checkout@v4
        with:
          fetch-depth: 0

      - name: Set up Go
        uses: actions/setup-go@v4
        with:
          go-version-file: ./go.mod

      - name: Run tests
        run: go test -v ./...

  build:
    name: Build binaries for Windows, macOS, and Linux
    runs-on: ${{ matrix.os }}
    permissions:
      contents: write
    strategy:
      matrix:
        os: [ubuntu-latest, macos-latest, windows-latest]
        arch: [amd64, arm64]
        exclude:
          - os: windows-latest
            arch: arm64

    steps:
      - name: Checkout code
        uses: actions/checkout@v4
        with:
          fetch-depth: 0

      - name: Set up Go
        uses: actions/setup-go@v4
        with:
          go-version-file: ./go.mod

      - name: Determine OS Name
        id: os-name
        run: |
          if [ "${{ matrix.os }}" == "ubuntu-latest" ]; then
            echo "OS=linux" >> $GITHUB_ENV
          elif [ "${{ matrix.os }}" == "macos-latest" ]; then
            echo "OS=darwin" >> $GITHUB_ENV
          else
            echo "OS=windows" >> $GITHUB_ENV
          fi
        shell: bash

      - name: Build binary on Linux and macOS
        if: matrix.os != 'windows-latest'
        env:
          GOOS: ${{ env.OS }}
          GOARCH: ${{ matrix.arch }}
        run: |
          go build -o fabric-${OS}-${{ matrix.arch }} .

      - name: Build binary on Windows
        if: matrix.os == 'windows-latest'
        env:
          GOOS: windows
          GOARCH: ${{ matrix.arch }}
        run: |
          go build -o fabric-windows-${{ matrix.arch }}.exe .

      - name: Upload build artifact
        if: matrix.os != 'windows-latest'
        uses: actions/upload-artifact@v4
        with:
          name: fabric-${OS}-${{ matrix.arch }}
          path: fabric-${OS}-${{ matrix.arch }}

      - name: Upload build artifact
        if: matrix.os == 'windows-latest'
        uses: actions/upload-artifact@v4
        with:
          name: fabric-windows-${{ matrix.arch }}.exe
          path: fabric-windows-${{ matrix.arch }}.exe

      - name: Get latest tag
        if: matrix.os != 'windows-latest'
        id: get_latest_tag
        run: |
          latest_tag=$(git tag --sort=-creatordate | head -n 1)
          echo "latest_tag=$latest_tag" >> $GITHUB_ENV

      - name: Get latest tag
        if: matrix.os == 'windows-latest'
        id: get_latest_tag_windows
        run: |
          $latest_tag = git tag --sort=-creatordate | Select-Object -First 1
          Add-Content -Path $env:GITHUB_ENV -Value "latest_tag=$latest_tag"

      - name: Create release if it doesn't exist
        shell: bash
        env:
          GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
        run: |
          if ! gh release view ${{ env.latest_tag }} >/dev/null 2>&1; then
            gh release create ${{ env.latest_tag }} --title "Release ${{ env.latest_tag }}" --notes "Automated release for ${{ env.latest_tag }}"
          else
            echo "Release ${{ env.latest_tag }} already exists."
          fi

      - name: Upload release artifact
        if: matrix.os == 'windows-latest'
        env:
          GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
        run: |
          gh release upload ${{ env.latest_tag }} fabric-windows-${{ matrix.arch }}.exe

      - name: Upload release artifact
        if: matrix.os != 'windows-latest'
        env:
          GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
        run: |
          gh release upload ${{ env.latest_tag }} fabric-${OS}-${{ matrix.arch }}
