name: Build

on:
  create:
    tags:
      -v*
  push:
    branches:
      - main
  pull_request:
    branches:
      - main

jobs:
  test:
    name: "Tests"
    strategy:
      fail-fast: false
      matrix:
        include:
          - name: Linux GCC
            os: ubuntu-latest
            compiler: gcc
            gcov_executable: gcov

          - name: Linux Clang
            os: ubuntu-latest
            compiler: llvm
            gcov_executable: "llvm-cov gcov"

          - name: MacOS clang
            os: macos-latest
            compiler: llvm
            gcov_executable: "llvm-cov gcov"

          - name: Windows MSVC
            os: windows-latest
            compiler: cl

    runs-on: ${{ matrix.os }}
    steps:
      - name: Get number of CPU cores
        uses: SimenB/github-actions-cpu-cores@v1
        id: cpu-cores

      - name: "Checkout repository"
        uses: actions/checkout@v2

      - name: "Setup Cpp"
        uses: aminya/setup-cpp@v1
        with:
          compiler: ${{ matrix.compiler }}
          vcvarsall: ${{ contains(matrix.os, 'windows' )}}
          cmake: true
          ninja: true
          clangtidy: false
          cppcheck: false
          gcovr: "5.0"
          opencppcoverage: true

      # make sure coverage is only enabled for Debug builds, since it sets -O0
      # to make sure coverage has meaningful results
      - name: "Configure CMake"
        run: >
          cmake -S .
          -B ./build
          -DCMAKE_BUILD_TYPE:STRING=Debug
          -DCMAKE_BUILD_PARALLEL_LEVEL=${{ steps.cpu-cores.outputs.count }}
          -DFTXUI_ENABLE_COVERAGE:BOOL=ON
          -DFTXUI_BUILD_DOCS:BOOL=OFF
          -DFTXUI_BUILD_EXAMPLES:BOOL=ON
          -DFTXUI_BUILD_TESTS:BOOL=ON
          -DFTXUI_BUILD_TESTS_FUZZER:BOOL=OFF
          -DFTXUI_ENABLE_INSTALL:BOOL=ON
          -DFTXUI_DEV_WARNINGS:BOOL=ON ;

      - name: "Build"
        run: >
          cmake
          --build ./build

      - name: Unix - Test and coverage
        if: runner.os != 'Windows'
        working-directory: ./build
        run: >
          ctest -C Debug --rerun-failed --output-on-failure;
          gcovr
          -j ${{env.nproc}}
          --delete
          --root ../
          --exclude "../examples"
          --exclude ".*google.*"
          --exclude ".*test.*"
          --exclude-unreachable-branches
          --exclude-throw-branches
          --sort-uncovered
          --print-summary
          --xml-pretty
          --xml
          coverage.xml
          .
          --gcov-executable '${{ matrix.gcov_executable }}';

      - name: Windows - Test and coverage
        if: runner.os == 'Windows'
        working-directory: ./build
        run: >
          OpenCppCoverage.exe
          --export_type cobertura:coverage.xml
          --cover_children
          --
          ctest -C Debug --rerun-failed --output-on-failure;

      - name: Publish to codecov
        uses: codecov/codecov-action@v3
        with:
          flags: ${{ runner.os }}
          name: ${{ runner.os }}-coverage
          files: ./build/coverage.xml

  # Create a release on new v* tags
  release:
    needs: test
    if: ${{ github.event_name == 'create' && startsWith(github.ref, 'refs/tags/v') }}
    name: "Create release"
    runs-on: ubuntu-latest
    outputs:
      upload_url: ${{ steps.create_release.outputs.upload_url }}
    steps:
      - name: "Create release"
        uses: softprops/action-gh-release@v1
        id: create_release
        with:
          draft: true
        env:
          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  # Build artifact for the release
  package:
    name: "Build packages"
    needs: release
    strategy:
      matrix:
        include:
          - os: ubuntu-latest
            asset_path: build/ftxui*Linux*
          - os: macos-latest
            asset_path: build/ftxui*Darwin*
          - os: windows-latest
            asset_path: build/ftxui*Win64*
    runs-on: ${{ matrix.os }}
    steps:
      - name: Get number of CPU cores
        uses: SimenB/github-actions-cpu-cores@v1
        id: cpu-cores

      - name: "Checkout repository"
        uses: actions/checkout@v2

      - name: "Install cmake"
        uses: lukka/get-cmake@latest

      - name: "Build packages"
        run: >
          mkdir build;
          cd build;
          cmake ..
          -DCMAKE_BUILD_TYPE=Release
          -DCMAKE_BUILD_PARALLEL_LEVEL=${{ steps.cpu-cores.outputs.count }}
          -DFTXUI_BUILD_DOCS=OFF
          -DFTXUI_BUILD_EXAMPLES=OFF
          -DFTXUI_BUILD_TESTS=OFF
          -DFTXUI_BUILD_TESTS_FUZZER=OFF
          -DFTXUI_ENABLE_INSTALL=ON
          -DFTXUI_DEV_WARNINGS=ON ;
          cmake --build . --target package;

      - uses: shogo82148/actions-upload-release-asset@v1
        with:
          upload_url: ${{ needs.release.outputs.upload_url }}
          asset_path: ${{ matrix.asset_path }}
          overwrite: true
  
  documentation:
    if: github.ref == 'refs/heads/main'
    runs-on: ubuntu-latest
    steps:
      - name: "Checkout repository"
        uses: actions/checkout@v2

      - name: "Install cmake"
        uses: lukka/get-cmake@latest

      - name: "Install emsdk"
        uses: mymindstorm/setup-emsdk@v7

      - name: "Install Doxygen/Graphviz"
        run: >
          sudo apt-get update;
          sudo apt-get install doxygen graphviz;

      - name: "Build documentation"
        run: >
          mkdir build;
          cd build;
          emcmake cmake ..
          -DCMAKE_BUILD_TYPE=Release
          -DFTXUI_BUILD_DOCS=ON
          -DFTXUI_BUILD_EXAMPLES=ON
          -DFTXUI_BUILD_TESTS=OFF
          -DFTXUI_BUILD_TESTS_FUZZER=OFF
          -DFTXUI_ENABLE_INSTALL=OFF
          -DFTXUI_DEV_WARNINGS=ON ;
          cmake --build . --target doc;
          cmake --build . ;
          rsync -amv
          --include='*/'
          --include='*.html'
          --include='*.js'
          --include='*.wasm'
          --exclude='*'
          examples
          doc/doxygen/html;

      - name: "Deploy"
        uses: peaceiris/actions-gh-pages@v3
        with:
          github_token: ${{ secrets.GITHUB_TOKEN }}
          publish_dir: build/doc/doxygen/html/
          enable_jekyll: false
          allow_empty_commit: false
          force_orphan: true
          publish_branch: gh-pages
