---
name: Build Desktop

on:
  pull_request:
    branches-ignore:
      - 'l10n_master'
      - 'cf-pages'
    paths:
      - 'apps/desktop/**'
      - '*'
      - '!*.md'
      - '!*.txt'
      - '.github/workflows/build-desktop.yml'
  push:
    branches:
      - 'master'
      - 'rc'
      - 'hotfix-rc/**'
    paths:
      - 'apps/desktop/**'
      - 'libs/**'
      - '*'
      - '!*.md'
      - '!*.txt'
      - '.github/workflows/build-desktop.yml'
  workflow_dispatch:
    inputs: {}

defaults:
  run:
    shell: bash

jobs:
  cloc:
    name: CLOC
    runs-on: ubuntu-20.04
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Set up cloc
        run: |
          sudo apt-get update
          sudo apt-get -y install cloc

      - name: Print lines of code
        run: cloc --include-lang TypeScript,JavaScript,HTML,Sass,CSS --vcs git

  electron-verify:
    name: Verify Electron Version
    runs-on: ubuntu-20.04
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Verify
        run: |
          PACKAGE_VERSION=$(jq -r .devDependencies.electron package.json)
          ELECTRON_BUILDER_VERSION=$(jq -r .electronVersion ./apps/desktop/electron-builder.json)

          if [[ "$PACKAGE_VERSION" == "$ELECTRON_BUILDER_VERSION"  ]]; then
            echo "Versions matches"
          else
            echo "Version missmatch, package.json: $PACKAGE_VERSION, electron-builder.json: $ELECTRON_BUILDER_VERSION"
            exit 1
          fi

  setup:
    name: Setup
    runs-on: ubuntu-20.04
    outputs:
      package_version: ${{ steps.retrieve-version.outputs.package_version }}
      release_channel: ${{ steps.release-channel.outputs.channel }}
      build_number: ${{ steps.increment-version.outputs.build_number }}
      rc_branch_exists: ${{ steps.branch-check.outputs.rc_branch_exists }}
      hotfix_branch_exists: ${{ steps.branch-check.outputs.hotfix_branch_exists }}
    defaults:
      run:
        working-directory: apps/desktop
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Get Package Version
        id: retrieve-version
        run: |
          PKG_VERSION=$(jq -r .version src/package.json)
          echo "::set-output name=package_version::$PKG_VERSION"

      - name: Increment Version
        id: increment-version
        run: |
          BUILD_NUMBER=$(expr 3000 + $GITHUB_RUN_NUMBER)
          echo "Setting build number to $BUILD_NUMBER"
          echo "::set-output name=build_number::$BUILD_NUMBER"

      - name: Get Version Channel
        id: release-channel
        run: |
          case "${{ steps.retrieve-version.outputs.package_version }}" in
            *"alpha"*)
              echo "::set-output name=channel::alpha"
              echo "[!] We do not yet support 'alpha'"
              exit 1
              ;;
            *"beta"*)
              echo "::set-output name=channel::beta"
              ;;
            *)
              echo "::set-output name=channel::latest"
              ;;
          esac

      - name: Check if special branches exist
        id: branch-check
        run: |
          if [[ $(git ls-remote --heads origin rc) ]]; then
            echo "::set-output name=rc_branch_exists::1"
          else
            echo "::set-output name=rc_branch_exists::0"
          fi

          if [[ $(git ls-remote --heads origin hotfix-rc) ]]; then
            echo "::set-output name=hotfix_branch_exists::1"
          else
            echo "::set-output name=hotfix_branch_exists::0"
          fi


  linux:
    name: Linux Build
    runs-on: ubuntu-20.04
    needs: setup
    env:
      _PACKAGE_VERSION: ${{ needs.setup.outputs.package_version }}
    defaults:
      run:
        working-directory: apps/desktop
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Set up Node
        uses: actions/setup-node@9ced9a43a244f3ac94f13bfd896db8c8f30da67a  # v3.0.0
        with:
          cache: 'npm'
          cache-dependency-path: '**/package-lock.json'
          node-version: '16'

      - name: Set Node options
        run: echo "NODE_OPTIONS=--max_old_space_size=4096" >> $GITHUB_ENV

      - name: Install node-gyp
        run: |
          npm install -g node-gyp
          node-gyp install $(node -v)

      - name: Set up environment
        run: |
          sudo apt-get update
          sudo apt-get -y install pkg-config libxss-dev libsecret-1-dev rpm

      - name: Set up Snap
        run: sudo snap install snapcraft --classic

      - name: Print environment
        run: |
          node --version
          npm --version
          snap --version
          snapcraft --version || echo 'snapcraft unavailable'

      - name: Install Node dependencies
        run: npm ci
        working-directory: ./

      - name: Build application
        run: npm run dist:lin

      - name: Upload .deb artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-amd64.deb
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-amd64.deb
          if-no-files-found: error

      - name: Upload .rpm artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-x86_64.rpm
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-x86_64.rpm
          if-no-files-found: error

      - name: Upload .freebsd artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-x64.freebsd
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-x64.freebsd
          if-no-files-found: error

      - name: Upload .snap artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: bitwarden_${{ env._PACKAGE_VERSION }}_amd64.snap
          path: apps/desktop/dist/bitwarden_${{ env._PACKAGE_VERSION }}_amd64.snap
          if-no-files-found: error

      - name: Upload .AppImage artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-x86_64.AppImage
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-x86_64.AppImage
          if-no-files-found: error

      - name: Upload auto-update artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: ${{ needs.setup.outputs.release_channel }}-linux.yml
          path: apps/desktop/dist/${{ needs.setup.outputs.release_channel }}-linux.yml
          if-no-files-found: error


  windows:
    name: Windows Build
    runs-on: windows-2019
    needs: setup
    defaults:
      run:
        shell: pwsh
        working-directory: apps/desktop
    env:
      _PACKAGE_VERSION: ${{ needs.setup.outputs.package_version }}
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Set up Node
        uses: actions/setup-node@9ced9a43a244f3ac94f13bfd896db8c8f30da67a  # v3.0.0
        with:
          cache: 'npm'
          cache-dependency-path: '**/package-lock.json'
          node-version: '16'

      - name: Set Node options
        run: echo "NODE_OPTIONS=--max_old_space_size=4096" | Out-File -FilePath $env:GITHUB_ENV -Encoding utf8 -Append

      - name: Install node-gyp
        run: |
          npm install -g node-gyp
          node-gyp install $(node -v)

      - name: Install AST
        uses: bitwarden/gh-actions/install-ast@f135c42c8596cb535c5bcb7523c0b2eef89709ac

      - name: Set up environment
        run: choco install checksum --no-progress

      - name: Print environment
        run: |
          node --version
          npm --version
          choco --version

      - name: Login to Azure
        uses: Azure/login@1f63701bf3e6892515f1b7ce2d2bf1708b46beaf
        with:
          creds: ${{ secrets.AZURE_PROD_KV_CREDENTIALS }}

      - name: Retrieve secrets
        id: retrieve-secrets
        uses: Azure/get-keyvault-secrets@b5c723b9ac7870c022b8c35befe620b7009b336f
        with:
          keyvault: "bitwarden-prod-kv"
          secrets: "code-signing-vault-url,
                    code-signing-client-id,
                    code-signing-tenant-id,
                    code-signing-client-secret,
                    code-signing-cert-name"

      - name: Install Node dependencies
        run: npm ci
        working-directory: ./

      - name: Build & Sign (dev)
        env:
          ELECTRON_BUILDER_SIGN: 1
          SIGNING_VAULT_URL: ${{ steps.retrieve-secrets.outputs.code-signing-vault-url }}
          SIGNING_CLIENT_ID: ${{ steps.retrieve-secrets.outputs.code-signing-client-id }}
          SIGNING_TENANT_ID: ${{ steps.retrieve-secrets.outputs.code-signing-tenant-id }}
          SIGNING_CLIENT_SECRET: ${{ steps.retrieve-secrets.outputs.code-signing-client-secret }}
          SIGNING_CERT_NAME: ${{ steps.retrieve-secrets.outputs.code-signing-cert-name }}
        run: |
          npm run build
          npm run pack:win

      - name: Rename appx files for store
        run: |
          Copy-Item "./dist/Bitwarden-${{ env._PACKAGE_VERSION }}-ia32.appx" `
            -Destination "./dist/Bitwarden-${{ env._PACKAGE_VERSION }}-ia32-store.appx"
          Copy-Item "./dist/Bitwarden-${{ env._PACKAGE_VERSION }}-x64.appx" `
            -Destination "./dist/Bitwarden-${{ env._PACKAGE_VERSION }}-x64-store.appx"
          Copy-Item "./dist/Bitwarden-${{ env._PACKAGE_VERSION }}-arm64.appx" `
            -Destination "./dist/Bitwarden-${{ env._PACKAGE_VERSION }}-arm64-store.appx"

      - name: Package for Chocolatey
        run: |
          Copy-Item -Path ./stores/chocolatey -Destination ./dist/chocolatey -Recurse
          Copy-Item -Path ./dist/nsis-web/Bitwarden-Installer-${{ env._PACKAGE_VERSION }}.exe `
          -Destination ./dist/chocolatey

          $checksum = checksum -t sha256 ./dist/chocolatey/Bitwarden-Installer-${{ env._PACKAGE_VERSION }}.exe
          $chocoInstall = "./dist/chocolatey/tools/chocolateyinstall.ps1"
          (Get-Content $chocoInstall).replace('__version__', "$env:_PACKAGE_VERSION").replace('__checksum__', $checksum) | Set-Content $chocoInstall
          choco pack ./dist/chocolatey/bitwarden.nuspec --version "$env:_PACKAGE_VERSION" --out ./dist/chocolatey

      - name: Fix NSIS artifact names for auto-updater
        run: |
          Rename-Item -Path .\dist\nsis-web\Bitwarden-${{ env._PACKAGE_VERSION }}-ia32.nsis.7z `
            -NewName bitwarden-${{ env._PACKAGE_VERSION }}-ia32.nsis.7z
          Rename-Item -Path .\dist\nsis-web\Bitwarden-${{ env._PACKAGE_VERSION }}-x64.nsis.7z `
            -NewName bitwarden-${{ env._PACKAGE_VERSION }}-x64.nsis.7z
          Rename-Item -Path .\dist\nsis-web\Bitwarden-${{ env._PACKAGE_VERSION }}-arm64.nsis.7z `
            -NewName bitwarden-${{ env._PACKAGE_VERSION }}-arm64.nsis.7z

      - name: Upload portable exe artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-Portable-${{ env._PACKAGE_VERSION }}.exe
          path: apps/desktop/dist/Bitwarden-Portable-${{ env._PACKAGE_VERSION }}.exe
          if-no-files-found: error

      - name: Upload installer exe artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-Installer-${{ env._PACKAGE_VERSION }}.exe
          path: apps/desktop/dist/nsis-web/Bitwarden-Installer-${{ env._PACKAGE_VERSION }}.exe
          if-no-files-found: error

      - name: Upload appx ia32 artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-ia32.appx
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-ia32.appx
          if-no-files-found: error

      - name: Upload store appx ia32 artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-ia32-store.appx
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-ia32-store.appx
          if-no-files-found: error

      - name: Upload NSIS ia32 artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: bitwarden-${{ env._PACKAGE_VERSION }}-ia32.nsis.7z
          path: apps/desktop/dist/nsis-web/bitwarden-${{ env._PACKAGE_VERSION }}-ia32.nsis.7z
          if-no-files-found: error

      - name: Upload appx x64 artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-x64.appx
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-x64.appx
          if-no-files-found: error

      - name: Upload store appx x64 artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-x64-store.appx
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-x64-store.appx
          if-no-files-found: error

      - name: Upload NSIS x64 artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: bitwarden-${{ env._PACKAGE_VERSION }}-x64.nsis.7z
          path: apps/desktop/dist/nsis-web/bitwarden-${{ env._PACKAGE_VERSION }}-x64.nsis.7z
          if-no-files-found: error

      - name: Upload appx ARM64 artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-arm64.appx
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-arm64.appx
          if-no-files-found: error

      - name: Upload store appx ARM64 artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-arm64-store.appx
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-arm64-store.appx
          if-no-files-found: error

      - name: Upload NSIS ARM64 artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: bitwarden-${{ env._PACKAGE_VERSION }}-arm64.nsis.7z
          path: apps/desktop/dist/nsis-web/bitwarden-${{ env._PACKAGE_VERSION }}-arm64.nsis.7z
          if-no-files-found: error

      - name: Upload nupkg artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: bitwarden.${{ env._PACKAGE_VERSION }}.nupkg
          path: apps/desktop/dist/chocolatey/bitwarden.${{ env._PACKAGE_VERSION }}.nupkg
          if-no-files-found: error

      - name: Upload auto-update artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: ${{ needs.setup.outputs.release_channel }}.yml
          path: apps/desktop/dist/nsis-web/${{ needs.setup.outputs.release_channel }}.yml
          if-no-files-found: error


  macos-build:
    name: MacOS Build
    runs-on: macos-11
    needs: setup
    env:
      _PACKAGE_VERSION: ${{ needs.setup.outputs.package_version }}
    defaults:
      run:
        working-directory: apps/desktop
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Set up Node
        uses: actions/setup-node@9ced9a43a244f3ac94f13bfd896db8c8f30da67a  # v3.0.0
        with:
          cache: 'npm'
          cache-dependency-path: '**/package-lock.json'
          node-version: '16'

      - name: Set Node options
        run: echo "NODE_OPTIONS=--max_old_space_size=4096" >> $GITHUB_ENV

      - name: Install node-gyp
        run: |
          npm install -g node-gyp
          node-gyp install $(node -v)

      - name: Print environment
        run: |
          node --version
          npm --version
          echo "GitHub ref: $GITHUB_REF"
          echo "GitHub event: $GITHUB_EVENT"

      - name: Cache Build
        id: build-cache
        uses: actions/cache@937d24475381cd9c75ae6db12cb4e79714b926ed
        with:
          path: apps/desktop/build
          key: ${{ runner.os }}-${{ github.run_id }}-build

      - name: Cache Safari
        id: safari-cache
        uses: actions/cache@937d24475381cd9c75ae6db12cb4e79714b926ed
        with:
          path: apps/browser/dist/Safari
          key: ${{ runner.os }}-${{ github.run_id }}-safari-extension

      - name: Decrypt secrets
        env:
          DECRYPT_FILE_PASSWORD: ${{ secrets.DECRYPT_FILE_PASSWORD }}
        run: |
          mkdir -p $HOME/secrets
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/bitwarden-desktop-key.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/bitwarden-desktop-key.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/appstore-app-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/appstore-app-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/appstore-installer-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/appstore-installer-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/devid-app-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/devid-app-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/devid-installer-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/devid-installer-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/macdev-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/macdev-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/bitwarden_desktop_appstore.provisionprofile" \
            "$GITHUB_WORKSPACE/.github/secrets/bitwarden_desktop_appstore.provisionprofile.gpg"

      - name: Set up keychain
        env:
          KEYCHAIN_PASSWORD: ${{ secrets.KEYCHAIN_PASSWORD }}
          DESKTOP_KEY_PASSWORD: ${{ secrets.DESKTOP_KEY_PASSWORD }}
          DEVID_CERT_PASSWORD: ${{ secrets.DEVID_CERT_PASSWORD }}
          APPSTORE_CERT_PASSWORD: ${{ secrets.APPSTORE_CERT_PASSWORD }}
          MACDEV_CERT_PASSWORD: ${{ secrets.MACDEV_CERT_PASSWORD }}
          APPLE_ID_PASSWORD: ${{ secrets.APPLE_ID_PASSWORD }}
        run: |
          security create-keychain -p $KEYCHAIN_PASSWORD build.keychain
          security default-keychain -s build.keychain
          security unlock-keychain -p $KEYCHAIN_PASSWORD build.keychain
          security set-keychain-settings -lut 1200 build.keychain
          security import "$HOME/secrets/bitwarden-desktop-key.p12" -k build.keychain -P $DESKTOP_KEY_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/devid-app-cert.p12" -k build.keychain -P $DEVID_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/devid-installer-cert.p12" -k build.keychain -P $DEVID_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/appstore-app-cert.p12" -k build.keychain -P $APPSTORE_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/appstore-installer-cert.p12" -k build.keychain -P $APPSTORE_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/macdev-cert.p12" -k build.keychain -P $MACDEV_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security set-key-partition-list -S apple-tool:,apple:,codesign: -s -k $KEYCHAIN_PASSWORD build.keychain

      - name: Set up provisioning profiles
        run: |
          cp $HOME/secrets/bitwarden_desktop_appstore.provisionprofile \
            $GITHUB_WORKSPACE/apps/desktop/bitwarden_desktop_appstore.provisionprofile

      - name: Increment version
        shell: pwsh
        env:
          BUILD_NUMBER: ${{ needs.setup.outputs.build_number }}
        run: |
          $package = Get-Content -Raw -Path electron-builder.json | ConvertFrom-Json
          $package | Add-Member -MemberType NoteProperty -Name buildVersion -Value "$env:BUILD_NUMBER"
          $package | ConvertTo-Json -Depth 32 | Set-Content -Path electron-builder.json

      - name: Install Node dependencies
        run: npm ci
        working-directory: ./

      - name: Build application (dev)
        run: npm run build


  macos-package-github:
    name: MacOS Package GitHub Release Assets
    runs-on: macos-11
    needs:
      - setup
      - macos-build
    env:
      _PACKAGE_VERSION: ${{ needs.setup.outputs.package_version }}
    defaults:
      run:
        working-directory: apps/desktop
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Set up Node
        uses: actions/setup-node@9ced9a43a244f3ac94f13bfd896db8c8f30da67a  # v3.0.0
        with:
          cache: 'npm'
          cache-dependency-path: '**/package-lock.json'
          node-version: '16'

      - name: Set Node options
        run: echo "NODE_OPTIONS=--max_old_space_size=4096" >> $GITHUB_ENV

      - name: Install node-gyp
        run: |
          npm install -g node-gyp
          node-gyp install $(node -v)

      - name: Print environment
        run: |
          node --version
          npm --version
          echo "GitHub ref: $GITHUB_REF"
          echo "GitHub event: $GITHUB_EVENT"

      - name: Get Build Cache
        id: build-cache
        uses: actions/cache@937d24475381cd9c75ae6db12cb4e79714b926ed
        with:
          path: apps/desktop/build
          key: ${{ runner.os }}-${{ github.run_id }}-build

      - name: Setup Safari Cache
        id: safari-cache
        uses: actions/cache@937d24475381cd9c75ae6db12cb4e79714b926ed
        with:
          path: apps/browser/dist/Safari
          key: ${{ runner.os }}-${{ github.run_id }}-safari-extension

      - name: Decrypt secrets
        env:
          DECRYPT_FILE_PASSWORD: ${{ secrets.DECRYPT_FILE_PASSWORD }}
        run: |
          mkdir -p $HOME/secrets
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/bitwarden-desktop-key.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/bitwarden-desktop-key.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/appstore-app-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/appstore-app-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/appstore-installer-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/appstore-installer-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/devid-app-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/devid-app-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/devid-installer-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/devid-installer-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/macdev-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/macdev-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/bitwarden_desktop_appstore.provisionprofile" \
            "$GITHUB_WORKSPACE/.github/secrets/bitwarden_desktop_appstore.provisionprofile.gpg"

      - name: Set up keychain
        env:
          KEYCHAIN_PASSWORD: ${{ secrets.KEYCHAIN_PASSWORD }}
          DESKTOP_KEY_PASSWORD: ${{ secrets.DESKTOP_KEY_PASSWORD }}
          DEVID_CERT_PASSWORD: ${{ secrets.DEVID_CERT_PASSWORD }}
          APPSTORE_CERT_PASSWORD: ${{ secrets.APPSTORE_CERT_PASSWORD }}
          MACDEV_CERT_PASSWORD: ${{ secrets.MACDEV_CERT_PASSWORD }}
          APPLE_ID_PASSWORD: ${{ secrets.APPLE_ID_PASSWORD }}
        run: |
          security create-keychain -p $KEYCHAIN_PASSWORD build.keychain
          security default-keychain -s build.keychain
          security unlock-keychain -p $KEYCHAIN_PASSWORD build.keychain
          security set-keychain-settings -lut 1200 build.keychain
          security import "$HOME/secrets/bitwarden-desktop-key.p12" -k build.keychain -P $DESKTOP_KEY_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/devid-app-cert.p12" -k build.keychain -P $DEVID_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/devid-installer-cert.p12" -k build.keychain -P $DEVID_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/appstore-app-cert.p12" -k build.keychain -P $APPSTORE_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/appstore-installer-cert.p12" -k build.keychain -P $APPSTORE_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/macdev-cert.p12" -k build.keychain -P $MACDEV_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security set-key-partition-list -S apple-tool:,apple:,codesign: -s -k $KEYCHAIN_PASSWORD build.keychain

      - name: Set up provisioning profiles
        run: |
          cp $HOME/secrets/bitwarden_desktop_appstore.provisionprofile \
            $GITHUB_WORKSPACE/apps/desktop/bitwarden_desktop_appstore.provisionprofile

      - name: Increment version
        shell: pwsh
        env:
          BUILD_NUMBER: ${{ needs.setup.outputs.build_number }}
        run: |
          $package = Get-Content -Raw -Path electron-builder.json | ConvertFrom-Json
          $package | Add-Member -MemberType NoteProperty -Name buildVersion -Value "$env:BUILD_NUMBER"
          $package | ConvertTo-Json -Depth 32 | Set-Content -Path electron-builder.json

      - name: Install Node dependencies
        run: npm ci
        working-directory: ./

      - name: Build
        if: steps.build-cache.outputs.cache-hit != 'true'
        run: npm run build

      - name: Extract branch name
        if: contains(github.ref, 'hotfix-rc')
        id: extract_branch
        shell: bash
        run: echo "##[set-output name=branch;]$(echo ${GITHUB_REF#refs/heads/})"

      - name: Download artifact from hotfix-rc
        if: contains(github.ref, 'hotfix-rc')
        uses: dawidd6/action-download-artifact@b2abf1705491048a2d7074f7d90513044fd25d39  # v2.19.0
        with:
          workflow: build-browser.yml
          workflow_conclusion: success
          branch: ${{ steps.extract_branch.outputs.branch }}
          path: ${{ github.workspace }}/browser-build-artifacts

      - name: Download artifact from rc
        if: github.ref == 'refs/heads/rc'
        uses: dawidd6/action-download-artifact@b2abf1705491048a2d7074f7d90513044fd25d39  # v2.19.0
        with:
          workflow: build-browser.yml
          workflow_conclusion: success
          branch: rc
          path: ${{ github.workspace }}/browser-build-artifacts

      - name: Download artifact from master
        if: ${{ github.ref != 'refs/heads/rc' && !contains(github.ref, 'hotfix-rc') }}
        uses: dawidd6/action-download-artifact@b2abf1705491048a2d7074f7d90513044fd25d39  # v2.19.0
        with:
          workflow: build-browser.yml
          workflow_conclusion: success
          branch: master
          path: ${{ github.workspace }}/browser-build-artifacts

      - name: Unzip Safari artifact
        run: |
          SAFARI_DIR=$(find $GITHUB_WORKSPACE/browser-build-artifacts -name 'dist-safari-*.zip')
          echo $SAFARI_DIR
          unzip $SAFARI_DIR/dist-safari.zip -d $GITHUB_WORKSPACE/browser-build-artifacts

      - name: Load Safari extension for .dmg
        run: |
          mkdir PlugIns
          cp -r $GITHUB_WORKSPACE/browser-build-artifacts/Safari/dmg/build/Release/safari.appex PlugIns/safari.appex

      - name: Build application (dist)
        env:
          APPLE_ID_USERNAME: ${{ secrets.APPLE_ID_USERNAME }}
          APPLE_ID_PASSWORD: ${{ secrets.APPLE_ID_PASSWORD }}
        run: npm run pack:mac

      - name: Upload .zip artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-universal-mac.zip
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-universal-mac.zip
          if-no-files-found: error

      - name: Upload .dmg artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-universal.dmg
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-universal.dmg
          if-no-files-found: error

      - name: Upload .dmg blockmap artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-universal.dmg.blockmap
          path: apps/desktop/dist/Bitwarden-${{ env._PACKAGE_VERSION }}-universal.dmg.blockmap
          if-no-files-found: error

      - name: Upload auto-update artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: ${{ needs.setup.outputs.release_channel }}-mac.yml
          path: apps/desktop/dist/${{ needs.setup.outputs.release_channel }}-mac.yml
          if-no-files-found: error


  macos-package-mas:
    name: MacOS Package Prod Release Asset
    runs-on: macos-11
    needs:
      - setup
      - macos-build
    env:
      _PACKAGE_VERSION: ${{ needs.setup.outputs.package_version }}
    defaults:
      run:
        working-directory: apps/desktop
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Set up Node
        uses: actions/setup-node@9ced9a43a244f3ac94f13bfd896db8c8f30da67a  # v3.0.0
        with:
          cache: 'npm'
          cache-dependency-path: '**/package-lock.json'
          node-version: '16'

      - name: Set Node options
        run: echo "NODE_OPTIONS=--max_old_space_size=4096" >> $GITHUB_ENV

      - name: Install node-gyp
        run: |
          npm install -g node-gyp
          node-gyp install $(node -v)

      - name: Print environment
        run: |
          node --version
          npm --version
          echo "GitHub ref: $GITHUB_REF"
          echo "GitHub event: $GITHUB_EVENT"

      - name: Get Build Cache
        id: build-cache
        uses: actions/cache@937d24475381cd9c75ae6db12cb4e79714b926ed
        with:
          path: apps/desktop/build
          key: ${{ runner.os }}-${{ github.run_id }}-build

      - name: Setup Safari Cache
        id: safari-cache
        uses: actions/cache@937d24475381cd9c75ae6db12cb4e79714b926ed
        with:
          path: apps/browser/dist/Safari
          key: ${{ runner.os }}-${{ github.run_id }}-safari-extension

      - name: Decrypt secrets
        env:
          DECRYPT_FILE_PASSWORD: ${{ secrets.DECRYPT_FILE_PASSWORD }}
        run: |
          mkdir -p $HOME/secrets
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/bitwarden-desktop-key.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/bitwarden-desktop-key.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/appstore-app-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/appstore-app-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/appstore-installer-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/appstore-installer-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/devid-app-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/devid-app-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/devid-installer-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/devid-installer-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/macdev-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/macdev-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/bitwarden_desktop_appstore.provisionprofile" \
            "$GITHUB_WORKSPACE/.github/secrets/bitwarden_desktop_appstore.provisionprofile.gpg"

      - name: Set up keychain
        env:
          KEYCHAIN_PASSWORD: ${{ secrets.KEYCHAIN_PASSWORD }}
          DESKTOP_KEY_PASSWORD: ${{ secrets.DESKTOP_KEY_PASSWORD }}
          DEVID_CERT_PASSWORD: ${{ secrets.DEVID_CERT_PASSWORD }}
          APPSTORE_CERT_PASSWORD: ${{ secrets.APPSTORE_CERT_PASSWORD }}
          MACDEV_CERT_PASSWORD: ${{ secrets.MACDEV_CERT_PASSWORD }}
          APPLE_ID_PASSWORD: ${{ secrets.APPLE_ID_PASSWORD }}
        run: |
          security create-keychain -p $KEYCHAIN_PASSWORD build.keychain
          security default-keychain -s build.keychain
          security unlock-keychain -p $KEYCHAIN_PASSWORD build.keychain
          security set-keychain-settings -lut 1200 build.keychain
          security import "$HOME/secrets/bitwarden-desktop-key.p12" -k build.keychain -P $DESKTOP_KEY_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/devid-app-cert.p12" -k build.keychain -P $DEVID_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/devid-installer-cert.p12" -k build.keychain -P $DEVID_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/appstore-app-cert.p12" -k build.keychain -P $APPSTORE_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/appstore-installer-cert.p12" -k build.keychain -P $APPSTORE_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/macdev-cert.p12" -k build.keychain -P $MACDEV_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security set-key-partition-list -S apple-tool:,apple:,codesign: -s -k $KEYCHAIN_PASSWORD build.keychain

      - name: Set up provisioning profiles
        run: |
          cp $HOME/secrets/bitwarden_desktop_appstore.provisionprofile \
            $GITHUB_WORKSPACE/apps/desktop/bitwarden_desktop_appstore.provisionprofile

      - name: Increment version
        shell: pwsh
        env:
          BUILD_NUMBER: ${{ needs.setup.outputs.build_number }}
        run: |
          $package = Get-Content -Raw -Path electron-builder.json | ConvertFrom-Json
          $package | Add-Member -MemberType NoteProperty -Name buildVersion -Value "$env:BUILD_NUMBER"
          $package | ConvertTo-Json -Depth 32 | Set-Content -Path electron-builder.json

      - name: Install Node dependencies
        run: npm ci
        working-directory: ./

      - name: Build
        if: steps.build-cache.outputs.cache-hit != 'true'
        run: npm run build

      - name: Extract branch name
        if: contains(github.ref, 'hotfix-rc')
        id: extract_branch
        shell: bash
        run: echo "##[set-output name=branch;]$(echo ${GITHUB_REF#refs/heads/})"

      - name: Download artifact from hotfix-rc
        if: contains(github.ref, 'hotfix-rc')
        uses: dawidd6/action-download-artifact@b2abf1705491048a2d7074f7d90513044fd25d39  # v2.19.0
        with:
          workflow: build-browser.yml
          workflow_conclusion: success
          branch: ${{ steps.extract_branch.outputs.branch }}
          path: ${{ github.workspace }}/browser-build-artifacts

      - name: Download artifact from rc
        if: github.ref == 'refs/heads/rc'
        uses: dawidd6/action-download-artifact@b2abf1705491048a2d7074f7d90513044fd25d39  # v2.19.0
        with:
          workflow: build-browser.yml
          workflow_conclusion: success
          branch: rc
          path: ${{ github.workspace }}/browser-build-artifacts

      - name: Download artifact from master
        if: ${{ github.ref != 'refs/heads/rc' && !contains(github.ref, 'hotfix-rc') }}
        uses: dawidd6/action-download-artifact@b2abf1705491048a2d7074f7d90513044fd25d39  # v2.19.0
        with:
          workflow: build-browser.yml
          workflow_conclusion: success
          branch: master
          path: ${{ github.workspace }}/browser-build-artifacts

      - name: Unzip Safari artifact
        run: |
          SAFARI_DIR=$(find $GITHUB_WORKSPACE/browser-build-artifacts -name 'dist-safari-*.zip')
          echo $SAFARI_DIR
          unzip $SAFARI_DIR/dist-safari.zip -d $GITHUB_WORKSPACE/browser-build-artifacts

      - name: Load Safari extension for App Store
        run: |
          mkdir PlugIns
          cp -r $GITHUB_WORKSPACE/browser-build-artifacts/Safari/mas/build/Release/safari.appex PlugIns/safari.appex

      - name: Build application for App Store
        run: npm run pack:mac:mas
        env:
          APPLE_ID_USERNAME: ${{ secrets.APPLE_ID_USERNAME }}
          APPLE_ID_PASSWORD: ${{ secrets.APPLE_ID_PASSWORD }}

      - name: Upload .pkg artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-universal.pkg
          path: apps/desktop/dist/mas-universal/Bitwarden-${{ env._PACKAGE_VERSION }}-universal.pkg
          if-no-files-found: error

      - name: Deploy to TestFlight
        env:
          APPLE_ID_USERNAME: ${{ secrets.APPLE_ID_USERNAME }}
          APPLE_ID_PASSWORD: ${{ secrets.APPLE_ID_PASSWORD }}
        if: |
            (github.ref == 'refs/heads/master'
              && needs.setup.outputs.rc_branch_exists == 0
              && needs.setup.outputs.hotfix_branch_exists == 0)
            || (github.ref == 'refs/heads/rc' && needs.setup.outputs.hotfix_branch_exists == 0)
            || github.ref == 'refs/heads/hotfix-rc'
        run: npm run upload:mas


  macos-package-dev:
    name: MacOS Package Dev Release Asset
    if: false  # We need to look into how code signing works for dev
    runs-on: macos-11
    needs:
      - setup
      - macos-build
    env:
      _PACKAGE_VERSION: ${{ needs.setup.outputs.package_version }}
    defaults:
      run:
        working-directory: apps/desktop
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Set up Node
        uses: actions/setup-node@9ced9a43a244f3ac94f13bfd896db8c8f30da67a  # v3.0.0
        with:
          cache: 'npm'
          cache-dependency-path: '**/package-lock.json'
          node-version: '16'

      - name: Set Node options
        run: echo "NODE_OPTIONS=--max_old_space_size=4096" >> $GITHUB_ENV

      - name: Install node-gyp
        run: |
          npm install -g node-gyp
          node-gyp install $(node -v)

      - name: Print environment
        run: |
          node --version
          npm --version
          echo "GitHub ref: $GITHUB_REF"
          echo "GitHub event: $GITHUB_EVENT"

      - name: Get Build Cache
        id: build-cache
        uses: actions/cache@937d24475381cd9c75ae6db12cb4e79714b926ed
        with:
          path: apps/desktop/build
          key: ${{ runner.os }}-${{ github.run_id }}-build

      - name: Setup Safari Cache
        id: safari-cache
        uses: actions/cache@937d24475381cd9c75ae6db12cb4e79714b926ed
        with:
          path: apps/browser/dist/Safari
          key: ${{ runner.os }}-${{ github.run_id }}-safari-extension

      - name: Decrypt secrets
        env:
          DECRYPT_FILE_PASSWORD: ${{ secrets.DECRYPT_FILE_PASSWORD }}
        run: |
          mkdir -p $HOME/secrets
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/bitwarden-desktop-key.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/bitwarden-desktop-key.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/appstore-app-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/appstore-app-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/appstore-installer-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/appstore-installer-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/devid-app-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/devid-app-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/devid-installer-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/devid-installer-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/macdev-cert.p12" \
            "$GITHUB_WORKSPACE/.github/secrets/macdev-cert.p12.gpg"
          gpg --quiet --batch --yes --decrypt --passphrase="$DECRYPT_FILE_PASSWORD" \
            --output "$HOME/secrets/bitwarden_desktop_appstore.provisionprofile" \
            "$GITHUB_WORKSPACE/.github/secrets/bitwarden_desktop_appstore.provisionprofile.gpg"

      - name: Set up keychain
        env:
          KEYCHAIN_PASSWORD: ${{ secrets.KEYCHAIN_PASSWORD }}
          DESKTOP_KEY_PASSWORD: ${{ secrets.DESKTOP_KEY_PASSWORD }}
          DEVID_CERT_PASSWORD: ${{ secrets.DEVID_CERT_PASSWORD }}
          APPSTORE_CERT_PASSWORD: ${{ secrets.APPSTORE_CERT_PASSWORD }}
          MACDEV_CERT_PASSWORD: ${{ secrets.MACDEV_CERT_PASSWORD }}
          APPLE_ID_PASSWORD: ${{ secrets.APPLE_ID_PASSWORD }}
        run: |
          security create-keychain -p $KEYCHAIN_PASSWORD build.keychain
          security default-keychain -s build.keychain
          security unlock-keychain -p $KEYCHAIN_PASSWORD build.keychain
          security set-keychain-settings -lut 1200 build.keychain
          security import "$HOME/secrets/bitwarden-desktop-key.p12" -k build.keychain -P $DESKTOP_KEY_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/devid-app-cert.p12" -k build.keychain -P $DEVID_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/devid-installer-cert.p12" -k build.keychain -P $DEVID_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/appstore-app-cert.p12" -k build.keychain -P $APPSTORE_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/appstore-installer-cert.p12" -k build.keychain -P $APPSTORE_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security import "$HOME/secrets/macdev-cert.p12" -k build.keychain -P $MACDEV_CERT_PASSWORD \
            -T /usr/bin/codesign -T /usr/bin/security -T /usr/bin/productbuild
          security set-key-partition-list -S apple-tool:,apple:,codesign: -s -k $KEYCHAIN_PASSWORD build.keychain

      - name: Set up provisioning profiles
        run: |
          cp $HOME/secrets/bitwarden_desktop_appstore.provisionprofile \
            $GITHUB_WORKSPACE/apps/desktop/bitwarden_desktop_appstore.provisionprofile

      - name: Increment version
        shell: pwsh
        env:
          BUILD_NUMBER: ${{ needs.setup.outputs.build_number }}
        run: |
          $package = Get-Content -Raw -Path electron-builder.json | ConvertFrom-Json
          $package | Add-Member -MemberType NoteProperty -Name buildVersion -Value "$env:BUILD_NUMBER"
          $package | ConvertTo-Json -Depth 32 | Set-Content -Path electron-builder.json

      - name: Install Node dependencies
        run: npm ci
        working-directory: ./

      - name: Build
        if: steps.build-cache.outputs.cache-hit != 'true'
        run: npm run build

      - name: Download artifact from rc
        if: github.ref == 'refs/heads/rc'
        uses: dawidd6/action-download-artifact@b2abf1705491048a2d7074f7d90513044fd25d39  # v2.19.0
        with:
          workflow: build-browser.yml
          workflow_conclusion: success
          branch: rc
          path: ${{ github.workspace }}/browser-build-artifacts

      - name: Download artifact from master
        if: github.ref != 'refs/heads/rc'
        uses: dawidd6/action-download-artifact@b2abf1705491048a2d7074f7d90513044fd25d39  # v2.19.0
        with:
          workflow: build-browser.yml
          workflow_conclusion: success
          branch: master
          path: ${{ github.workspace }}/browser-build-artifacts

      - name: Unzip Safari artifact
        run: |
          SAFARI_DIR=$(find $GITHUB_WORKSPACE/browser-build-artifacts -name 'dist-safari-*.zip')
          echo $SAFARI_DIR
          unzip $SAFARI_DIR/dist-safari.zip -d $GITHUB_WORKSPACE/browser-build-artifacts

      - name: Load Safari extension for App Store
        run: |
          mkdir PlugIns
          cp -r $GITHUB_WORKSPACE/browser-build-artifacts/Safari/masdev/build/Release/safari.appex PlugIns/safari.appex

      - name: Build dev application for App Store
        run: npm run pack:mac:masdev
        env:
          APPLE_ID_USERNAME: ${{ secrets.APPLE_ID_USERNAME }}
          APPLE_ID_PASSWORD: ${{ secrets.APPLE_ID_PASSWORD }}

      - name: Zip masdev asset
        working-directory: ./dist/mas-dev-universal
        run: zip -r Bitwarden-${{ env.PACKAGE_VERSION }}-masdev-universal.zip Bitwarden.app

      - name: Upload masdev artifact
        uses: actions/upload-artifact@6673cd052c4cd6fcf4b4e6e60ea986c889389535
        with:
          name: Bitwarden-${{ env._PACKAGE_VERSION }}-masdev-universal.zip
          path: apps/desktop/dist/mas-universal/Bitwarden-${{ env._PACKAGE_VERSION }}-masdev-universal.zip
          if-no-files-found: error


  crowdin-push:
    name: Crowdin Push
    if: github.ref == 'refs/heads/master'
    needs:
      - linux
      - windows
      - macos-package-github
      - macos-package-mas
    runs-on: ubuntu-20.04
    steps:
      - name: Checkout repo
        uses: actions/checkout@a12a3943b4bdde767164f792f33f40b04645d846

      - name: Login to Azure
        uses: Azure/login@1f63701bf3e6892515f1b7ce2d2bf1708b46beaf
        with:
          creds: ${{ secrets.AZURE_PROD_KV_CREDENTIALS }}

      - name: Retrieve secrets
        id: retrieve-secrets
        uses: Azure/get-keyvault-secrets@b5c723b9ac7870c022b8c35befe620b7009b336f
        with:
          keyvault: "bitwarden-prod-kv"
          secrets: "crowdin-api-token"

      - name: Upload Sources
        uses: crowdin/github-action@ecd7eb0ef6f3cfa16293c79e9cbc4bc5b5fd9c49  # v1.4.9
        env:
          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
          CROWDIN_API_TOKEN: ${{ steps.retrieve-secrets.outputs.crowdin-api-token }}
          CROWDIN_PROJECT_ID: "299360"
        with:
          config: apps/desktop/crowdin.yml
          crowdin_branch_name: master
          upload_sources: true
          upload_translations: false


  check-failures:
    name: Check for failures
    if: always()
    runs-on: ubuntu-20.04
    needs:
      - cloc
      - electron-verify
      - setup
      - linux
      - windows
      - macos-build
      - macos-package-github
      - macos-package-mas
      - crowdin-push
    steps:
      - name: Check if any job failed
        if: ${{ (github.ref == 'refs/heads/master') || (github.ref == 'refs/heads/rc') }}
        env:
          CLOC_STATUS: ${{ needs.cloc.result }}
          ELECTRON_VERIFY_STATUS: ${{ needs.electron-verify.result }}
          SETUP_STATUS: ${{ needs.setup.result }}
          LINUX_STATUS: ${{ needs.linux.result }}
          WINDOWS_STATUS: ${{ needs.windows.result }}
          MACOS_BUILD_STATUS: ${{ needs.macos-build.result }}
          MACOS_PKG_GITHUB_STATUS: ${{ needs.macos-package-github.result }}
          MACOS_PKG_MAS_STATUS: ${{ needs.macos-package-mas.result }}
          CROWDIN_PUSH_STATUS: ${{ needs.crowdin-push.result }}
        run: |
          if [ "$CLOC_STATUS" = "failure" ]; then
              exit 1
          elif [ "$ELECTRON_VERIFY_STATUS" = "failure" ]; then
              exit 1
          elif [ "$SETUP_STATUS" = "failure" ]; then
              exit 1
          elif [ "$LINUX_STATUS" = "failure" ]; then
              exit 1
          elif [ "$WINDOWS_STATUS" = "failure" ]; then
              exit 1
          elif [ "$MACOS_BUILD_STATUS" = "failure" ]; then
              exit 1
          elif [ "$MACOS_PKG_GITHUB_STATUS" = "failure" ]; then
              exit 1
          elif [ "$MACOS_PKG_MAS_STATUS" = "failure" ]; then
              exit 1
          elif [ "$CROWDIN_PUSH_STATUS" = "failure" ]; then
              exit 1
          fi

      - name: Login to Azure - Prod Subscription
        uses: Azure/login@1f63701bf3e6892515f1b7ce2d2bf1708b46beaf
        if: failure()
        with:
          creds: ${{ secrets.AZURE_PROD_KV_CREDENTIALS }}

      - name: Retrieve secrets
        id: retrieve-secrets
        uses: Azure/get-keyvault-secrets@b5c723b9ac7870c022b8c35befe620b7009b336f
        if: failure()
        with:
          keyvault: "bitwarden-prod-kv"
          secrets: "devops-alerts-slack-webhook-url"

      - name: Notify Slack on failure
        uses: act10ns/slack@da3191ebe2e67f49b46880b4633f5591a96d1d33
        if: failure()
        env:
          SLACK_WEBHOOK_URL: ${{ steps.retrieve-secrets.outputs.devops-alerts-slack-webhook-url }}
        with:
          status: ${{ job.status }}
