#!/usr/bin/env bash
# Licensed to the Apache Software Foundation (ASF) under one or more
# contributor license agreements.  See the NOTICE file distributed with
# this work for additional information regarding copyright ownership.
# The ASF licenses this file to You under the Apache License, Version 2.0
# (the "License"); you may not use this file except in compliance with
# the License.  You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

#
# SHELLDOC-IGNORE
#
# Override these to match Apache Hadoop's requirements
personality_plugins "all,-ant,-gradle,-scalac,-scaladoc"

## @description  Globals specific to this personality
## @audience     private
## @stability    evolving
function personality_globals
{
  # shellcheck disable=SC2034
  BUILDTOOL=maven
  #shellcheck disable=SC2034
  PATCH_BRANCH_DEFAULT=trunk
  #shellcheck disable=SC2034
  PATCH_NAMING_RULE="https://cwiki.apache.org/confluence/display/HADOOP/How+To+Contribute"
  #shellcheck disable=SC2034
  JIRA_ISSUE_RE='^(HADOOP|YARN|MAPREDUCE|HDFS)-[0-9]+$'
  #shellcheck disable=SC2034
  GITHUB_REPO_DEFAULT="apache/hadoop"

  HADOOP_HOMEBREW_DIR=${HADOOP_HOMEBREW_DIR:-$(brew --prefix 2>/dev/null)}
  if [[ -z "${HADOOP_HOMEBREW_DIR}" ]]; then
    HADOOP_HOMEBREW_DIR=/usr/local
  fi
}

function personality_parse_args
{
  declare i

  for i in "$@"; do
    case ${i} in
      --hadoop-isal-prefix=*)
        delete_parameter "${i}"
        ISAL_HOME=${i#*=}
      ;;
      --hadoop-openssl-prefix=*)
        delete_parameter "${i}"
        OPENSSL_HOME=${i#*=}
      ;;
      --hadoop-snappy-prefix=*)
        delete_parameter "${i}"
        SNAPPY_HOME=${i#*=}
      ;;
    esac
  done
}

## @description  Calculate the actual module ordering
## @audience     private
## @stability    evolving
## @param        ordering
function hadoop_order
{
  declare ordering=$1
  declare hadoopm

  if [[ ${ordering} = normal ]]; then
    hadoopm="${CHANGED_MODULES[*]}"
  elif [[ ${ordering} = union ]]; then
    hadoopm="${CHANGED_UNION_MODULES}"
  elif [[ ${ordering} = mvnsrc ]]; then
    hadoopm="${MAVEN_SRC_MODULES[*]}"
  elif [[ ${ordering} = mvnsrctest ]]; then
    hadoopm="${MAVEN_SRCTEST_MODULES[*]}"
  else
    hadoopm="${ordering}"
  fi
  echo "${hadoopm}"
}

## @description  Determine if it is safe to run parallel tests
## @audience     private
## @stability    evolving
## @param        ordering
function hadoop_test_parallel
{
  if [[ -f "${BASEDIR}/pom.xml" ]]; then
    HADOOP_VERSION=$(grep '<version>' "${BASEDIR}/pom.xml" \
        | head -1 \
        | "${SED}"  -e 's|^ *<version>||' -e 's|</version>.*$||' \
        | cut -f1 -d- )
    export HADOOP_VERSION
  else
    return 1
  fi

  hmajor=${HADOOP_VERSION%%\.*}
  hmajorminor=${HADOOP_VERSION%\.*}
  hminor=${hmajorminor##*\.}
  # ... and just for reference
  #hmicro=${HADOOP_VERSION##*\.}

  # Apache Hadoop v2.8.0 was the first one to really
  # get working parallel unit tests
  if [[ ${hmajor} -lt 3 && ${hminor} -lt 8 ]]; then
    return 1
  fi

  return 0
}

## @description  Install extra modules for unit tests
## @audience     private
## @stability    evolving
## @param        ordering
function hadoop_unittest_prereqs
{
  declare input=$1
  declare mods
  declare need_common=0
  declare building_common=0
  declare module
  declare flags
  declare fn

  # prior to running unit tests, hdfs needs libhadoop.so built
  # if we're building root, then this extra work is moot

  #shellcheck disable=SC2086
  mods=$(hadoop_order ${input})

  for module in ${mods}; do
    if [[ ${module} = hadoop-hdfs-project* ]]; then
      need_common=1
    elif [[ ${module} = hadoop-common-project/hadoop-common
      || ${module} = hadoop-common-project ]]; then
      building_common=1
    elif [[ ${module} = . ]]; then
      return
    fi
  done

  # Windows builds *ALWAYS* need hadoop-common compiled
  case ${OSTYPE} in
    Windows_NT|CYGWIN*|MINGW*|MSYS*)
      need_common=1
    ;;
  esac

  if [[ ${need_common} -eq 1
      && ${building_common} -eq 0 ]]; then
    echo "unit test pre-reqs:"
    module="hadoop-common-project/hadoop-common"
    fn=$(module_file_fragment "${module}")
    flags="$(hadoop_native_flags) $(yarn_ui2_flag)"
    pushd "${BASEDIR}/${module}" >/dev/null || return 1
    # shellcheck disable=SC2086
    echo_and_redirect "${PATCH_DIR}/maven-unit-prereq-${fn}-install.txt" \
      "${MAVEN}" "${MAVEN_ARGS[@]}" install -DskipTests ${flags}
    popd >/dev/null || return 1
  fi
}

## @description  Calculate the flags/settings for yarn-ui v2 build
## @description  based upon the OS
## @audience     private
## @stability    evolving
function yarn_ui2_flag
{

  if [[ ${BUILD_NATIVE} != true ]]; then
    return
  fi

  # Now it only tested on Linux/OSX, don't enable the profile on
  # windows until it get verified
  case ${OSTYPE} in
    Linux)
      # shellcheck disable=SC2086
      echo -Pyarn-ui
    ;;
    Darwin)
      echo -Pyarn-ui
    ;;
    *)
      # Do nothing
    ;;
  esac
}

## @description  Calculate the flags/settings for native code
## @description  based upon the OS
## @audience     private
## @stability    evolving
function hadoop_native_flags
{
  if [[ ${BUILD_NATIVE} != true ]]; then
    return
  fi

  declare -a args

  # Based upon HADOOP-11937
  #
  # Some notes:
  #
  # - getting fuse to compile on anything but Linux
  #   is always tricky.
  # - Darwin assumes homebrew is in use.
  # - HADOOP-12027 required for bzip2 on OS X.
  # - bzip2 is broken in lots of places
  #   (the shared library is considered experimental)
  #   e.g, HADOOP-12027 for OS X. so no -Drequire.bzip2
  #

  args=("-Drequire.test.libhadoop")

  if [[ -d "${ISAL_HOME}/include" ]]; then
    args=("${args[@]}" "-Disal.prefix=${ISAL_HOME}")
  fi

  if [[ -d "${OPENSSL_HOME}/include" ]]; then
    args=("${args[@]}" "-Dopenssl.prefix=${OPENSSL_HOME}")
  elif [[ -d "${HADOOP_HOMEBREW_DIR}/opt/openssl/" ]]; then
    args=("${args[@]}" "-Dopenssl.prefix=${HADOOP_HOMEBREW_DIR}/opt/openssl/")
  fi

  if [[ -d "${SNAPPY_HOME}/include" ]]; then
    args=("${args[@]}" "-Dsnappy.prefix=${SNAPPY_HOME}")
  elif [[ -d "${HADOOP_HOMEBREW_DIR}/include/snappy.h" ]]; then
    args=("${args[@]}" "-Dsnappy.prefix=${HADOOP_HOMEBREW_DIR}/opt/snappy")
  fi

  case ${OSTYPE} in
    Linux)
      # shellcheck disable=SC2086
      echo \
        -Pnative \
        -Drequire.fuse \
        -Drequire.openssl \
        -Drequire.snappy \
        -Drequire.valgrind \
        -Drequire.zstd \
        "${args[@]}"
    ;;
    Darwin)
      echo \
        "${args[@]}" \
        -Pnative \
        -Drequire.snappy  \
        -Drequire.openssl
    ;;
    Windows_NT|CYGWIN*|MINGW*|MSYS*)
      echo \
        "${args[@]}" \
        -Drequire.snappy -Drequire.openssl -Pnative-win
    ;;
    *)
      echo \
        "${args[@]}"
    ;;
  esac
}

## @description  Queue up modules for this personality
## @audience     private
## @stability    evolving
## @param        repostatus
## @param        testtype
function personality_modules
{
  declare repostatus=$1
  declare testtype=$2
  declare extra=""
  declare ordering="normal"
  declare needflags=false
  declare foundbats=false
  declare flags
  declare fn
  declare i
  declare hadoopm

  yetus_debug "Personality: ${repostatus} ${testtype}"

  clear_personality_queue

  case ${testtype} in
    asflicense)
      # this is very fast and provides the full path if we do it from
      # the root of the source
      personality_enqueue_module .
      return
    ;;
    checkstyle)
      ordering="union"
      extra="-DskipTests"
    ;;
    compile)
      ordering="union"
      extra="-DskipTests"
      needflags=true

      # if something in common changed, we build the whole world
      if [[ "${CHANGED_MODULES[*]}" =~ hadoop-common ]]; then
        yetus_debug "hadoop personality: javac + hadoop-common = ordering set to . "
        ordering="."
      fi
    ;;
    distclean)
      ordering="."
      extra="-DskipTests"
    ;;
    javadoc)
      if [[ "${CHANGED_MODULES[*]}" =~ \. ]]; then
        ordering=.
      fi

      if [[ "${repostatus}" = patch && "${BUILDMODE}" = patch ]]; then
        echo "javadoc pre-reqs:"
        for i in hadoop-project \
          hadoop-common-project/hadoop-annotations; do
            fn=$(module_file_fragment "${i}")
            pushd "${BASEDIR}/${i}" >/dev/null || return 1
            echo "cd ${i}"
            echo_and_redirect "${PATCH_DIR}/maven-${fn}-install.txt" \
              "${MAVEN}" "${MAVEN_ARGS[@]}" install
            popd >/dev/null || return 1
        done
      fi
      extra="-Pdocs -DskipTests"
    ;;
    mvneclipse)
      if [[ "${CHANGED_MODULES[*]}" =~ \. ]]; then
        ordering=.
      fi
    ;;
    mvninstall)
      extra="-DskipTests"
      if [[ "${repostatus}" = branch || "${BUILDMODE}" = full ]]; then
        ordering=.
      fi
    ;;
    mvnsite)
      if [[ "${CHANGED_MODULES[*]}" =~ \. ]]; then
        ordering=.
      fi
    ;;
    unit)
      if [[ "${BUILDMODE}" = full ]]; then
        ordering=mvnsrc
      elif [[ "${CHANGED_MODULES[*]}" =~ \. ]]; then
        ordering=.
      fi

      if [[ ${TEST_PARALLEL} = "true" ]] ; then
        if hadoop_test_parallel; then
          extra="-Pparallel-tests"
          if [[ -n ${TEST_THREADS:-} ]]; then
            extra="${extra} -DtestsThreadCount=${TEST_THREADS}"
          fi
        fi
      fi
      needflags=true
      hadoop_unittest_prereqs "${ordering}"

      if ! verify_needed_test javac; then
        yetus_debug "hadoop: javac not requested"
        if ! verify_needed_test native; then
          yetus_debug "hadoop: native not requested"
          yetus_debug "hadoop: adding -DskipTests to unit test"
          extra="-DskipTests"
        fi
      fi

      for i in "${CHANGED_FILES[@]}"; do
        if [[ "${i}" =~ \.bats ]]; then
          foundbats=true
        fi
      done

      if ! verify_needed_test shellcheck && [[ ${foundbats} = false ]]; then
        yetus_debug "hadoop: NO shell code change detected; disabling shelltest profile"
        extra="${extra} -P!shelltest"
      else
        extra="${extra} -Pshelltest"
      fi
    ;;
    *)
      extra="-DskipTests"
    ;;
  esac

  if [[ ${needflags} = true ]]; then
    flags="$(hadoop_native_flags) $(yarn_ui2_flag)"
    extra="${extra} ${flags}"
  fi

  extra="-Ptest-patch ${extra}"
  for module in $(hadoop_order ${ordering}); do
    # shellcheck disable=SC2086
    personality_enqueue_module ${module} ${extra}
  done
}

## @description  Add tests based upon personality needs
## @audience     private
## @stability    evolving
## @param        filename
function personality_file_tests
{
  declare filename=$1

  yetus_debug "Using Hadoop-specific personality_file_tests"

  if [[ ${filename} =~ src/main/webapp ]]; then
    yetus_debug "tests/webapp: ${filename}"
    add_test shadedclient
  elif [[ ${filename} =~ \.sh
       || ${filename} =~ \.cmd
       || ${filename} =~ src/scripts
       || ${filename} =~ src/test/scripts
       || ${filename} =~ src/main/bin
       || ${filename} =~ shellprofile\.d
       || ${filename} =~ src/main/conf
       ]]; then
    yetus_debug "tests/shell: ${filename}"
    add_test mvnsite
    add_test unit
  elif [[ ${filename} =~ \.md$
       || ${filename} =~ \.md\.vm$
       || ${filename} =~ src/site
       ]]; then
    yetus_debug "tests/site: ${filename}"
    add_test mvnsite
  elif [[ ${filename} =~ \.c$
       || ${filename} =~ \.cc$
       || ${filename} =~ \.h$
       || ${filename} =~ \.hh$
       || ${filename} =~ \.proto$
       || ${filename} =~ \.cmake$
       || ${filename} =~ CMakeLists.txt
       ]]; then
    yetus_debug "tests/units: ${filename}"
    add_test compile
    add_test cc
    add_test mvnsite
    add_test javac
    add_test unit
  elif [[ ${filename} =~ build.xml$
       || ${filename} =~ pom.xml$
       || ${filename} =~ \.java$
       || ${filename} =~ src/main
       ]]; then
      yetus_debug "tests/javadoc+units: ${filename}"
      add_test compile
      add_test javac
      add_test javadoc
      add_test mvninstall
      add_test mvnsite
      add_test unit
      add_test shadedclient
  fi

  # if we change anything in here, e.g. the test scripts
  # then run the client artifact tests
  if [[ ${filename} =~ hadoop-client-modules ]]; then
    add_test shadedclient
  fi

  if [[ ${filename} =~ src/test ]]; then
    yetus_debug "tests: src/test"
    add_test unit
  fi

  if [[ ${filename} =~ \.java$ ]]; then
    add_test findbugs
  fi
}

## @description  Image to print on success
## @audience     private
## @stability    evolving
function hadoop_console_success
{
  printf "IF9fX19fX19fX18gCjwgU3VjY2VzcyEgPgogLS0tLS0tLS0tLSAKIFwgICAg";
  printf "IC9cICBfX18gIC9cCiAgXCAgIC8vIFwvICAgXC8gXFwKICAgICAoKCAgICBP";
  printf "IE8gICAgKSkKICAgICAgXFwgLyAgICAgXCAvLwogICAgICAgXC8gIHwgfCAg";
  printf "XC8gCiAgICAgICAgfCAgfCB8ICB8ICAKICAgICAgICB8ICB8IHwgIHwgIAog";
  printf "ICAgICAgIHwgICBvICAgfCAgCiAgICAgICAgfCB8ICAgfCB8ICAKICAgICAg";
  printf "ICB8bXwgICB8bXwgIAo"
}

###################################################
# Hadoop project specific check of IT for shaded artifacts

add_test_type shadedclient

## @description check for test modules and add test/plugins as needed
## @audience private
## @stability evolving
function shadedclient_initialize
{
  maven_add_install shadedclient
}

## @description build client facing shaded artifacts and test them
## @audience private
## @stability evolving
## @param repostatus
function shadedclient_rebuild
{
  declare repostatus=$1
  declare logfile="${PATCH_DIR}/${repostatus}-shadedclient.txt"
  declare module
  declare -a modules=()

  if [[ ${OSTYPE} = Windows_NT ||
        ${OSTYPE} =~ ^CYGWIN.* ||
        ${OSTYPE} =~ ^MINGW32.* ||
        ${OSTYPE} =~ ^MSYS.* ]]; then
    echo "hadoop personality: building on windows, skipping check of client artifacts."
    return 0
  fi

  yetus_debug "hadoop personality: seeing if we need the test of client artifacts."
  for module in hadoop-client-modules/hadoop-client-check-invariants \
                hadoop-client-modules/hadoop-client-check-test-invariants \
                hadoop-client-modules/hadoop-client-integration-tests; do
    if [ -d "${module}" ]; then
      yetus_debug "hadoop personality: test module '${module}' is present."
      modules+=(-pl "${module}")
    fi
  done
  if [ ${#modules[@]} -eq 0 ]; then
    echo "hadoop personality: no test modules present, skipping check of client artifacts."
    return 0
  fi

  big_console_header "Checking client artifacts on ${repostatus}"

  echo_and_redirect "${logfile}" \
    "${MAVEN}" "${MAVEN_ARGS[@]}" verify -fae --batch-mode -am \
      "${modules[@]}" \
      -Dtest=NoUnitTests -Dmaven.javadoc.skip=true -Dcheckstyle.skip=true -Dfindbugs.skip=true

  count=$("${GREP}" -c '\[ERROR\]' "${logfile}")
  if [[ ${count} -gt 0 ]]; then
    add_vote_table -1 shadedclient "${repostatus} has errors when building and testing our client artifacts."
    return 1
  fi

  add_vote_table +1 shadedclient "${repostatus} has no errors when building and testing our client artifacts."
  return 0
}
