name: "Unstable Build"

on:
  schedule:
    # Weekly unstable trigger on Monday at 05:00 GMT
    - cron: '0 5 * * 1'
  workflow_dispatch:
    # Manual trigger

env:
  SDK_VERSION: "9.0.x"

permissions:
  contents: read

jobs:
  Docker:
    runs-on: ubuntu-24.04
    continue-on-error: false  # true in prod, false for testing
    steps:
      - name: "Set dated version for unstable builds"
        id: version
        run: |-
          echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H')" >> $GITHUB_ENV
          echo "JELLYFIN_RELEASE_TYPE=unstable" >> $GITHUB_ENV
          echo "DEBUG_FLAG=--debug" >>$GITHUB_ENV

      - name: "Install dependencies"
        run: |-
          sudo apt-get update
          sudo apt-get install --yes python3-git python3-yaml

      - name: "Checkout repository"
        uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1

      - name: "Prepare repository"
        run: |-
          ./checkout.py master

      - name: "Run builder for Docker containers"
        env:
          DOCKER_USERNAME: ${{ secrets.DOCKER_USERNAME }}
          DOCKER_TOKEN: ${{ secrets.DOCKER_TOKEN }}
          GHCR_USERNAME: ${{ secrets.GHCR_USERNAME }}
          GHCR_TOKEN: ${{ secrets.GHCR_TOKEN }}
        run: |-
          sudo --preserve-env ./build.py ${{ env.JELLYFIN_VERSION }} docker ${{ env.DEBUG_FLAG }}

  Debian:
    runs-on: ubuntu-24.04
    strategy:
      fail-fast: false
      matrix:
        release:
          - bullseye
          - bookworm
          - trixie
        arch:
          - amd64
          - arm64
    continue-on-error: false  # true in prod, false for testing
    steps:
      - name: "Set dated version for unstable builds"
        id: version
        run: |-
          echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H')" >> $GITHUB_ENV
          echo "JELLYFIN_RELEASE_TYPE=unstable" >> $GITHUB_ENV
          echo "DEBUG_FLAG=--debug" >>$GITHUB_ENV

      - name: "Install dependencies"
        run: |-
          sudo apt-get update
          sudo apt-get install --yes python3-git python3-yaml debsigs devscripts

      - name: "Checkout repository"
        uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1

      - name: "Prepare repository"
        run: |-
          ./checkout.py master

      - name: "Run builder for ${{ matrix.version }} ${{ matrix.arch }}"
        run: |-
          sudo --preserve-env ./build.py ${{ env.JELLYFIN_VERSION }} debian ${{ matrix.arch }} ${{ matrix.release }} ${{ env.DEBUG_FLAG }}
          sudo chown --recursive $USER out/debian

      - name: "Import repository signing GPG key"
        run: |
          echo -n "${{ secrets.DEBIAN_SIGNING_KEY }}" | base64 --decode | gpg --batch --yes --import

      - name: "Sign Debian package and source files"
        run: |
          for file in out/debian/*.deb; do
              debsigs --sign=origin --default-key=${{ secrets.DEBIAN_SIGNING_KEY_ID }} ${file}
          done
          debsign -k ${{ secrets.DEBIAN_SIGNING_KEY_ID }} out/debian/*.changes

      - name: "Remove repository signing GPG key"
        run: |
          gpg --batch --yes --delete-secret-keys ${{ secrets.DEBIAN_SIGNING_KEY_ID }}

      - name: "Upload artifacts to repository server"
        uses: appleboy/scp-action@ff85246acaad7bdce478db94a363cd2bf7c90345 # v1.0.0
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          source: "out/debian/*"
          strip_components: 2
          target: "/srv/incoming/server/${{ env.JELLYFIN_VERSION }}/debian/${{ matrix.release }}/${{ matrix.arch }}"

      - name: "Import artifacts into reprepro"
        uses: appleboy/ssh-action@91f3272fc5907f4699dcf59761eb622a07342f5a # v1.2.3
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          debug: false
          script: |
            set -o xtrace
            COMPONENT="unstable"
            # Only include the architecture-dependent deb here, as the others are done only for amd64
            sudo reprepro --waitforlock 30 --basedir /srv/debian --component ${COMPONENT} includedeb ${{ matrix.release }} /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/debian/${{ matrix.release }}/${{ matrix.arch }}/*_${{ matrix.arch }}.deb || exit 1
            if [[ ${{ matrix.arch }} == "amd64" ]]; then
                # Only include the architecture-independent packages for amd64; the other architectures are the same and conflict
                sudo reprepro --waitforlock 30 --basedir /srv/debian --component ${COMPONENT} includedeb ${{ matrix.release }} /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/debian/${{ matrix.release }}/${{ matrix.arch }}/*_all.deb || exit 1
                # Only include the source DSC for amd64; the other architectures are the same and conflict
                sudo reprepro --waitforlock 30 --basedir /srv/debian --component ${COMPONENT} includedsc ${{ matrix.release }} /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/debian/${{ matrix.release }}/${{ matrix.arch }}/*.dsc || exit 1
            fi

            # Only keep ${NKEEP} (3) unstables; we have to do this manually since reprepro doesn't have granularity for this at the component level
            NKEEP=3
            # Get whatever the oldest version is; since these are dated, a simple numerical sort works
            LIST="$( sudo reprepro -b /srv/debian -C unstable list ${{ matrix.release }} | awk '{ print $NF }' | sort -rn | uniq )"
            COUNT=$( wc -l <<<"${LIST}" )
            if [[ ${COUNT} -gt ${NKEEP} ]]; then
                # Get anything that isn't in the latest ${NKEEP} entries
                OBSOLETE=( $( sed "1,${NKEEP}d" <<<"${LIST}" ) )
                for VERSION in ${OBSOLETE[@]}; do
                    for PACKAGE in jellyfin jellyfin-server jellyfin-web; do
                        for SCRAP_VERSION in $( sudo reprepro --waitforlock 30 --basedir /srv/debian --component ${COMPONENT} list ${{ matrix.release }} | grep "${PACKAGE} " | grep "${VERSION}" | sort | uniq ); do
                            sudo reprepro --waitforlock 30 --basedir /srv/debian --component ${COMPONENT} remove ${{ matrix.release }} ${PACKAGE}=${SCRAP_VERSION}
                        done
                    done
                done
            fi

      - name: "Move artifacts into repository"
        uses: appleboy/ssh-action@91f3272fc5907f4699dcf59761eb622a07342f5a # v1.2.3
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          debug: false
          script: |
            export BASEDIR="/srv/repository/main/server/debian"
            sudo mkdir -p ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }} || exit 1
            sudo mv -t ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }}/ /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/debian/${{ matrix.release }}/${{ matrix.arch }}/* || exit 1
            sudo rm ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || true
            sudo ln -sf ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }} ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || exit 1

  Ubuntu:
    runs-on: ubuntu-24.04
    strategy:
      fail-fast: false
      matrix:
        release:
          - focal
          - jammy
          - noble
        arch:
          - amd64
          - arm64
    continue-on-error: false  # true in prod, false for testing
    steps:
      - name: "Set dated version for unstable builds"
        id: version
        run: |-
          echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H')" >> $GITHUB_ENV
          echo "JELLYFIN_RELEASE_TYPE=unstable" >> $GITHUB_ENV
          echo "DEBUG_FLAG=--debug" >>$GITHUB_ENV

      - name: "Install dependencies"
        run: |-
          sudo apt-get update
          sudo apt-get install --yes python3-git python3-yaml debsigs devscripts

      - name: "Checkout repository"
        uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1

      - name: "Prepare repository"
        run: |-
          ./checkout.py master

      - name: "Run builder for ${{ matrix.version }} ${{ matrix.arch }}"
        run: |-
          sudo --preserve-env ./build.py ${{ env.JELLYFIN_VERSION }} ubuntu ${{ matrix.arch }} ${{ matrix.release }} ${{ env.DEBUG_FLAG }}
          sudo chown --recursive $USER out/ubuntu

      - name: "Import repository signing GPG key"
        run: |
          echo -n "${{ secrets.DEBIAN_SIGNING_KEY }}" | base64 --decode | gpg --batch --yes --import

      - name: "Sign Ubuntu package and source files"
        run: |
          for file in out/ubuntu/*.deb; do
              debsigs --sign=origin --default-key=${{ secrets.DEBIAN_SIGNING_KEY_ID }} ${file}
          done
          debsign -k ${{ secrets.DEBIAN_SIGNING_KEY_ID }} out/ubuntu/*.changes

      - name: "Remove repository signing GPG key"
        run: |
          gpg --batch --yes --delete-secret-keys ${{ secrets.DEBIAN_SIGNING_KEY_ID }}

      - name: "Upload artifacts to repository server"
        uses: appleboy/scp-action@ff85246acaad7bdce478db94a363cd2bf7c90345 # v1.0.0
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          source: "out/ubuntu/*"
          strip_components: 2
          target: "/srv/incoming/server/${{ env.JELLYFIN_VERSION }}/ubuntu/${{ matrix.release }}/${{ matrix.arch }}"

      - name: "Import artifacts into reprepro"
        uses: appleboy/ssh-action@91f3272fc5907f4699dcf59761eb622a07342f5a # v1.2.3
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          debug: false
          script: |
            set -o xtrace
            COMPONENT="unstable"
            # Only include the architecture-dependent deb here, as the others are done only for amd64
            sudo reprepro --waitforlock 30 --basedir /srv/ubuntu --component ${COMPONENT} includedeb ${{ matrix.release }} /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/ubuntu/${{ matrix.release }}/${{ matrix.arch }}/*_${{ matrix.arch }}.deb || exit 1
            if [[ ${{ matrix.arch }} == "amd64" ]]; then
                # Only include the architecture-independent packages for amd64; the other architectures are the same and conflict
                sudo reprepro --waitforlock 30 --basedir /srv/ubuntu --component ${COMPONENT} includedeb ${{ matrix.release }} /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/ubuntu/${{ matrix.release }}/${{ matrix.arch }}/*_all.deb || exit 1
                # Only include the source DSC for amd64; the other architectures are the same and conflict
                sudo reprepro --waitforlock 30 --basedir /srv/ubuntu --component ${COMPONENT} includedsc ${{ matrix.release }} /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/ubuntu/${{ matrix.release }}/${{ matrix.arch }}/*.dsc || exit 1
            fi

            # Only keep ${NKEEP} (4) unstables; we have to do this manually since reprepro doesn't have granularity for this at the component level
            NKEEP=3
            # Get whatever the oldest version is; since these are dated, a simple numerical sort works
            LIST="$( sudo reprepro -b /srv/ubuntu -C unstable list ${{ matrix.release }} | awk '{ print $NF }' | sort -rn | uniq )"
            COUNT=$( wc -l <<<"${LIST}" )
            if [[ ${COUNT} -gt ${NKEEP} ]]; then
                # Get anything that isn't in the latest ${NKEEP} entries
                OBSOLETE=( $( sed "1,${NKEEP}d" <<<"${LIST}" ) )
                for VERSION in ${OBSOLETE[@]}; do
                    for PACKAGE in jellyfin jellyfin-server jellyfin-web; do
                        for SCRAP_VERSION in $( sudo reprepro --waitforlock 30 --basedir /srv/ubuntu --component ${COMPONENT} list ${{ matrix.release }} | grep "${PACKAGE} " | grep "${VERSION}" | sort | uniq ); do
                            sudo reprepro --waitforlock 30 --basedir /srv/ubuntu --component ${COMPONENT} remove ${{ matrix.release }} ${PACKAGE}=${SCRAP_VERSION}
                        done
                    done
                done
            fi

      - name: "Move artifacts into repository"
        uses: appleboy/ssh-action@91f3272fc5907f4699dcf59761eb622a07342f5a # v1.2.3
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          debug: false
          script: |
            export BASEDIR="/srv/repository/main/server/ubuntu"
            sudo mkdir -p ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }} || exit 1
            sudo mv -t ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }}/ /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/ubuntu/${{ matrix.release }}/${{ matrix.arch }}/* || exit 1
            sudo rm ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || true
            sudo ln -sf ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }} ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || exit 1
            if [[ ${{ env.JELLYFIN_RELEASE_TYPE }} == "stable" ]]; then
                sudo rm ${BASEDIR}/latest || true
                sudo ln -sf ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }} ${BASEDIR}/latest || exit 1
            fi

  Linux:
    runs-on: ubuntu-24.04
    strategy:
      fail-fast: false
      matrix:
        arch:
          - amd64
          - amd64-musl
          - arm64
          - arm64-musl
    continue-on-error: false  # true in prod, false for testing
    steps:
      - name: "Set dated version for unstable builds"
        id: version
        run: |-
          echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H')" >> $GITHUB_ENV
          echo "JELLYFIN_RELEASE_TYPE=unstable" >> $GITHUB_ENV
          echo "DEBUG_FLAG=--debug" >>$GITHUB_ENV

      - name: "Install dependencies"
        run: |-
          sudo apt-get update
          sudo apt-get install --yes python3-git python3-yaml

      - name: "Checkout repository"
        uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1

      - name: "Prepare repository"
        run: |-
          ./checkout.py ${{ inputs.version || 'master' }}

      - name: "Run builder for ${{ matrix.arch }}"
        run: |-
          sudo --preserve-env ./build.py ${{ env.JELLYFIN_VERSION }} linux ${{ matrix.arch }} ${{ env.DEBUG_FLAG }}

      - name: "Upload artifacts to repository server"
        uses: appleboy/scp-action@ff85246acaad7bdce478db94a363cd2bf7c90345 # v1.0.0
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          source: "out/linux/*"
          strip_components: 2
          target: "/srv/incoming/server/${{ env.JELLYFIN_VERSION }}/linux/${{ matrix.arch }}"

      - name: "Move artifacts into repository"
        uses: appleboy/ssh-action@91f3272fc5907f4699dcf59761eb622a07342f5a # v1.2.3
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          debug: false
          script: |
            set -e
            export BASEDIR="/srv/repository/main/server/linux"
            sudo mkdir -p ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }} || exit 1
            sudo mv -t ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }}/ /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/linux/${{ matrix.release }}/${{ matrix.arch }}/* || exit 1
            sudo rm ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || true
            sudo ln -sf ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }} ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || exit 1

  Windows:
    runs-on: ubuntu-24.04
    strategy:
      fail-fast: false
      matrix:
        arch:
          - amd64
          - arm64
    outputs:
      JELLYFIN_VERSION: ${{ steps.version.outputs.JELLYFIN_VERSION }}
      JELLYFIN_RELEASE_TYPE: ${{ steps.version.outputs.JELLYFIN_RELEASE_TYPE }}
    continue-on-error: false  # true in prod, false for testing
    steps:
      - name: "Set dated version for unstable builds"
        id: version
        run: |-
          echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H')" >> $GITHUB_ENV
          echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H')" >> $GITHUB_OUTPUT
          echo "JELLYFIN_RELEASE_TYPE=unstable" >> $GITHUB_ENV
          echo "JELLYFIN_RELEASE_TYPE=unstable" >> $GITHUB_OUTPUT
          echo "DEBUG_FLAG=--debug" >>$GITHUB_ENV

      - name: "Install dependencies"
        run: |-
          sudo apt-get update
          sudo apt-get install --yes python3-git python3-yaml

      - name: "Checkout repository"
        uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1

      - name: "Prepare repository"
        run: |-
          ./checkout.py ${{ inputs.version || 'master' }}

      - name: "Run builder for ${{ matrix.arch }}"
        run: |-
          sudo --preserve-env ./build.py ${{ env.JELLYFIN_VERSION }} windows ${{ matrix.arch }} ${{ env.DEBUG_FLAG }}

      - name: "Upload artifacts to repository server"
        uses: appleboy/scp-action@ff85246acaad7bdce478db94a363cd2bf7c90345 # v1.0.0
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          source: "out/windows/*"
          strip_components: 2
          target: "/srv/incoming/server/${{ env.JELLYFIN_VERSION }}/windows/${{ matrix.arch }}"

      - name: "Move artifacts into repository"
        uses: appleboy/ssh-action@91f3272fc5907f4699dcf59761eb622a07342f5a # v1.2.3
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          debug: false
          script: |
            set -e
            export BASEDIR="/srv/repository/main/server/windows"
            sudo mkdir -p ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }} || exit 1
            sudo mv -t ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }}/ /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/windows/${{ matrix.release }}/${{ matrix.arch }}/* || exit 1
            sudo rm ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || true
            sudo ln -sf ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }} ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || exit 1

      - name: "Store artifacts for next stage"
        uses: actions/upload-artifact@330a01c490aca151604b8cf639adc76d48f6c5d4 # v5
        with:
          name: windows-artifacts
          retention-days: 1
          if-no-files-found: ignore  # Ignore for arm64 build, as no file will be found
          path: out/windows/jellyfin_*-amd64.zip

  WindowsInstaller:
    needs:
      - Windows
    runs-on: windows-latest
    strategy:
      fail-fast: false
      matrix:
        arch:
          - amd64
    continue-on-error: false  # true in prod, false for testing
    env:
      DOTNET_CLI_TELEMETRY_OPTOUT: 1
    steps:
      - name: "Set dated version for unstable builds"
        id: version
        shell: pwsh
        run: |
          $version = "${{ needs.Windows.outputs.JELLYFIN_VERSION }}"
          $cleanVersion = $version
          echo "JELLYFIN_VERSION=$cleanVersion" | Out-File -FilePath $env:GITHUB_ENV -Append

      - name: "Checkout repository"
        uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1

      - name: "Install dependencies"
        run: |-
          python -m pip install --upgrade gitpython

      - name: "Install NSIS"
        uses: negrutiu/nsis-install@f3339c88dba6fd08910d5275a943f8f746d94876 # v2
        with:
          distro: official

      - name: "Prepare repository"
        run: |-
          python checkout.py master

      - name: "Fetch artifacts from previous stage"
        uses: actions/download-artifact@018cc2cf5baa6db3ef3c5f8a56943fffe632ef53 # v6
        with:
          name: windows-artifacts
          path: ./jellyfin-server-windows

      - name: "Clone UX repository"
        uses: actions/checkout@08c6903cd8c0fde910a37f88322edcfb5dd907a8 # v5
        with:
          repository: jellyfin/jellyfin-ux
          path: .\jellyfin-server-windows\jellyfin-ux

      - name: "Extract Jellyfin server archive"
        working-directory: ./jellyfin-server-windows
        run: |
          New-Item -ItemType Directory -Path jellyfin
          Expand-Archive -Path 'jellyfin_*-amd64.zip' -DestinationPath jellyfin -Force
          Copy-Item ".\Support Files\LICENSE" -Destination $(Resolve-Path .\jellyfin\jellyfin)

      - name: "Add NSSM"
        working-directory: ./jellyfin-server-windows
        run: |
          Invoke-WebRequest 'https://repo.jellyfin.org/files/other/nssm.zip' -OutFile 'nssm.zip'
          Expand-Archive 'nssm.zip'
          Copy-Item ".\nssm\nssm.exe" -Destination $(Resolve-Path .\jellyfin\jellyfin)
        
      - name: "Publish tray"
        working-directory: ./jellyfin-server-windows
        run: |
          New-Item -Path .\jellyfin\jellyfin\jellyfin-windows-tray -ItemType Directory
          dotnet publish -c Release -r win-x64 -f net472 --no-self-contained --output $(Resolve-Path .\jellyfin\jellyfin\jellyfin-windows-tray)

      - name: "Build installer"
        working-directory: ./jellyfin-server-windows
        run: |
          $env:InstallLocation = $(Resolve-Path .\jellyfin\jellyfin)
          makensis /Dx64 /DUXPATH=$(Resolve-Path .\jellyfin-ux) $(Join-Path -Path $(Resolve-Path .\nsis) -ChildPath jellyfin.nsi)

      - name: "Rename installer"
        working-directory: ./jellyfin-server-windows/nsis
        run: |
          Rename-Item -Path .\jellyfin_*_windows-x64.exe -NewName ("jellyfin_${{ env.JELLYFIN_VERSION }}_windows-x64.exe")
        
      - name: "Store artifacts for next stage"
        uses: actions/upload-artifact@330a01c490aca151604b8cf639adc76d48f6c5d4 # v5
        with:
          name: windows-installer-artifacts
          retention-days: 1
          if-no-files-found: error
          path: ./jellyfin-server-windows/nsis/jellyfin_${{ env.JELLYFIN_VERSION }}_windows-x64.exe

  WindowsInstallerUpload:
    needs:
      - Windows
      - WindowsInstaller
    runs-on: ubuntu-24.04
    strategy:
      fail-fast: false
      matrix:
        arch:
          - amd64
    continue-on-error: false  # true in prod, false for testing
    steps:
      - name: "Set version from previous job"
        id: version
        run: |-
          echo "JELLYFIN_VERSION=${{ needs.Windows.outputs.JELLYFIN_VERSION }}" >> $GITHUB_ENV
          echo "JELLYFIN_RELEASE_TYPE=${{ needs.Windows.outputs.JELLYFIN_RELEASE_TYPE }}" >> $GITHUB_ENV

      - name: "Fetch artifact from previous stage"
        uses: actions/download-artifact@018cc2cf5baa6db3ef3c5f8a56943fffe632ef53 # v6
        with:
          name: windows-installer-artifacts

      - name: "Upload artifacts to repository server"
        uses: appleboy/scp-action@ff85246acaad7bdce478db94a363cd2bf7c90345 # v1.0.0
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          source: "*.exe"
          target: "/srv/incoming/server/${{ env.JELLYFIN_VERSION }}/windows/${{ matrix.arch }}"

      - name: "Move artifacts into repository"
        uses: appleboy/ssh-action@91f3272fc5907f4699dcf59761eb622a07342f5a # v1.2.3
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          debug: false
          script: |
            set -e
            export BASEDIR="/srv/repository/main/server/windows"
            sudo mv -t ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }}/ /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/windows/${{ matrix.arch }}/*.exe

  MacOS:
    runs-on: ubuntu-24.04
    strategy:
      fail-fast: false
      matrix:
        arch:
          - amd64
          - arm64
    continue-on-error: false  # true in prod, false for testing
    steps:
      - name: "Set dated version for unstable builds"
        id: version
        run: |-
          echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H')" >> $GITHUB_ENV
          echo "JELLYFIN_RELEASE_TYPE=unstable" >> $GITHUB_ENV
          echo "DEBUG_FLAG=--debug" >>$GITHUB_ENV

      - name: "Install dependencies"
        run: |-
          sudo apt-get update
          sudo apt-get install --yes python3-git python3-yaml

      - name: "Checkout repository"
        uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1

      - name: "Prepare repository"
        run: |-
          ./checkout.py master

      - name: "Run builder for ${{ matrix.version }} ${{ matrix.arch }}"
        run: |-
          sudo --preserve-env ./build.py ${{ env.JELLYFIN_VERSION }} macos ${{ matrix.arch }} ${{ env.DEBUG_FLAG }}

      - name: "Upload artifacts to repository server"
        uses: appleboy/scp-action@ff85246acaad7bdce478db94a363cd2bf7c90345 # v1.0.0
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          source: "out/macos/*"
          strip_components: 2
          target: "/srv/incoming/server/${{ env.JELLYFIN_VERSION }}/macos/${{ matrix.arch }}"

      - name: "Move artifacts into repository"
        uses: appleboy/ssh-action@91f3272fc5907f4699dcf59761eb622a07342f5a # v1.2.3
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          debug: false
          script: |
            set -e
            export BASEDIR="/srv/repository/main/server/macos"
            sudo mkdir -p ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }} || exit 1
            sudo mv -t ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/${{ matrix.arch }}/ /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/macos/${{ matrix.release }}/${{ matrix.arch }}/* || exit 1
            sudo rm ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || true
            sudo ln -sf ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }} ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || exit 1

  Portable:
    runs-on: ubuntu-24.04
    continue-on-error: false  # true in prod, false for testing
    steps:
      - name: "Set dated version for unstable builds"
        id: version
        run: |-
          echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H')" >> $GITHUB_ENV
          echo "JELLYFIN_RELEASE_TYPE=unstable" >> $GITHUB_ENV
          echo "DEBUG_FLAG=--debug" >>$GITHUB_ENV

      - name: "Install dependencies"
        run: |-
          sudo apt-get update
          sudo apt-get install --yes python3-git python3-yaml

      - name: "Checkout repository"
        uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1

      - name: "Prepare repository"
        run: |-
          ./checkout.py ${{ inputs.version || 'master' }}

      - name: "Run builder for Portable" 
        run: |-
          sudo --preserve-env ./build.py ${{ env.JELLYFIN_VERSION }} portable ${{ env.DEBUG_FLAG }}

      - name: "Upload artifacts to repository server"
        uses: appleboy/scp-action@ff85246acaad7bdce478db94a363cd2bf7c90345 # v1.0.0
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          source: "out/portable/*"
          strip_components: 2
          target: "/srv/incoming/server/${{ env.JELLYFIN_VERSION }}/portable"

      - name: "Move artifacts into repository"
        uses: appleboy/ssh-action@91f3272fc5907f4699dcf59761eb622a07342f5a # v1.2.3
        with:
          host: "${{ secrets.REPO_HOST }}"
          username: "${{ secrets.REPO_USER }}"
          key: "${{ secrets.REPO_KEY }}"
          debug: false
          script: |
            set -e
            export BASEDIR="/srv/repository/main/server/portable"
            sudo mkdir -p ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/any || exit 1
            sudo mv -t ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }}/any/ /srv/incoming/server/${{ env.JELLYFIN_VERSION }}/portable/${{ matrix.release }}/* || exit 1
            sudo rm ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || true
            sudo ln -sf ${BASEDIR}/${{ env.JELLYFIN_RELEASE_TYPE }}/${{ env.JELLYFIN_VERSION }} ${BASEDIR}/latest-${{ env.JELLYFIN_RELEASE_TYPE }} || exit 1

  Nuget:
    runs-on: ubuntu-24.04
    steps:
      - name: "Set dated version for unstable builds"
        id: version
        run: |-
          echo "JELLYFIN_VERSION=$(date +'%Y%m%d%H')" >> $GITHUB_ENV
          echo "JELLYFIN_RELEASE_TYPE=unstable" >> $GITHUB_ENV
          echo "DEBUG_FLAG=--debug" >>$GITHUB_ENV

      - name: "Install dependencies"
        run: |-
          sudo apt-get update
          sudo apt-get install --yes python3-git python3-yaml

      - name: "Setup .NET"
        uses: actions/setup-dotnet@2016bd2012dba4e32de620c46fe006a3ac9f0602 # v5.0.1
        with:
          dotnet-version: ${{ env.SDK_VERSION }}

      - name: "Checkout repository"
        uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5.0.1

      - name: "Prepare repository"
        run: |-
          ./checkout.py master

      - name: "Run builder for Nuget"
        env:
          NUGET_STABLE_KEY: ${{ secrets.NUGET_STABLE_KEY }}
          NUGET_UNSTABLE_KEY: ${{ secrets.NUGET_UNSTABLE_KEY }}
        run: |-
          ./build.py ${{ env.JELLYFIN_VERSION }} nuget
