import libs = libglaze%lib{glaze}
import eigen = Eigen%lib{Eigen}

define json: file
json{*}: extension = json

define csv: file
csv{*}: extension = csv

define toml: file
toml{*}: extension = toml

define yaml: file
yaml{*}: extension = yml

# Unit tests.
#
exe{*}:
{
  test = true
  install = false
}

# skip: erlang (sys-lib), lib_test (annoying setup), key_transformers_test
#       (broken on MSVC)
# note: this skips nested tests (eg. networking_test/*/) for no other reason
#       than to avoid dealing with every single nuance in the CMake setup.
for [dir_path] d: tests/{*_test*/ \
                          -eetf_test/ \
                          -key_transformers_test/ \
                          -lib_test/ \
                        } \
                  tests/{ \
                          *_conformance/ \
                          *_parsing/ \
                          *_performance/ \
                          *_repe/ \
                          *_formats/ \
                        }
{
  n = $string($leaf($d))
  for t: tests/$n/cxx{*}
  {
    tn = $name($t)
    # Name targets '<subdir>-<name>' unless identical
    if ("$n" != "$tn")
      e = $n-$tn
    else
      e = $n
    exe{$e}: ut/hxx{ut} tests/$n/hxx{*} tests/$n/cxx{$tn} \
                 tests/$n/{json csv toml yaml}{**} $libs testscript

    # Don't build (and test/run) benchmarks by default.
    enabled = (!$contains($n, 'performance'))

    # Note:
    # MSVC remained severely broken over multiple compiler versions and most
    # issues aren't fully resolved until CL 19.50 (VS 18.2.1) and glaze v7.Y.Z.
    switch $e: path.match
    {
      case 'json_test'
      {
        enabled = ($cxx.target.system != 'win32-msvc')
      }
      case 'json_test-json_variant_support_test'
      {
        enabled = ($cxx.id != 'msvc')
      }
      case 'istream_buffer_test'
      {
        # See: https://github.com/stephenberry/glaze/pull/2304
        enabled = ($build.host.class != 'windows')
      }
      case '*rpc_test'
      {
        # Fails on most CI machines (compiler bug).
        enabled = false
      }
      case 'threading_test'
      {
        # Sporadic access violation.
        enabled = ($cxx.target.system != 'win32-msvc')
      }
    }
    ./: exe{$e}: include = $enabled
  }
}

# roundtrip
for [string] f : json beve # toml
{
  n = roundtrip
  t = $(n)-$(f)_test
  ./: exe{$t}: ut/hxx{ut} tests/$n/json{**} tests/$n/obj{$t} testscript
  tests/$n/obj{$t}: ut/hxx{ut} tests/$n/hxx{*} tests/$n/cxx{*} $libs
  {
    cxx.poptions += "-I$src_base" "-DGLZ_TEST_FORMAT=glz::$string.ucase($f)"
  }
  tests/$n/obj{$t}: ut/hxx{ut} tests/$n/hxx{*} tests/$n/cxx{*} $libs
}

# Build options.
#
cxx.poptions += "-I$src_base"

for [dir_path] d : {tests/*_test/}
{
  td = [path] $path.posix_representation($src_base/$d)
  n = $name($d)
  tests/$n/obj{**}: \
    cxx.poptions += \
      "-DGLZ_TEST_DIRECTORY=\"$path.posix_string($td)\""
}

# eigen_test
exe{eigen_test}: $eigen

# tests requiring certain compiler features
if ($cxx.id != 'msvc')
{
  for [dir_path] d : tests/{ \
                       buffer_pool_test \
                       exceptions_test \
                       json_test \
                       json_performance \
                       inplace_vector \
                       int_parsing \
                       networking_tests \
                       threading_test \
                     }
  {
    tests/$name($d)/obj{**}: cxx.coptions += -fexceptions
  }
}

# Common build options.
#
# See: ../../upstream/tests/CMakeLists.txt
switch $cxx.id: path.match, $cxx.target.system: path.match
{
  case 'gcc' | 'clang*'
  {
    # See: https://github.com/microsoft/STL/issues/4349
    if($cxx.target.system != 'win32-msvc')
      cxx.coptions += -fno-rtti

    cxx.coptions += \
      -fno-exceptions \
      -Wno-missing-braces
  }
  case 'gcc', 'mingw32'
  {
    cxx.coptions += \
      -Wa,-mbig-obj
  }
  case 'msvc' | 'msvc-clang', 'win32-msvc'
  {
    cxx.coptions += \
      /permissive- \
      /bigobj \
      /GR- \
      /wd4244 \
      /wd4459 \
      /wd4805 \
      /Zc:lambda \
      /Zc:preprocessor
  }
}

if ($cxx.target.system == 'win32-msvc')
{
  cxx.coptions += \
    -DNOMINMAX \
    -D_CRT_SECURE_NO_WARNINGS \
    -D_SILENCE_ALL_CXX20_DEPRECATION_WARNINGS \
    -DWIN32_LEAN_AND_MEAN
}
