#!/usr/bin/env groovy
//-------------------------------------------------------------------------------
// Copyright (c) 2020, Arm Limited and Contributors. All rights reserved.
//
// SPDX-License-Identifier: BSD-3-Clause
//
//-------------------------------------------------------------------------------

@Library('trustedfirmware') _
import org.trustedfirmware.Gerrit
import org.trustedfirmware.Summary

def listConfigs(ci_scripts_dir, config_list, filter_group) {
  dir(ci_scripts_dir) {
    echo "Obtaining list of configs."
    echo "Running: python3 ./configs.py -g ${filter_group.replace(" ", " -g ")}"
    def build_config_list_raw = sh(script: """\
python3 ./configs.py -g ${filter_group.replace(" ", " -g ")}
""", returnStdout: true).trim()
    def build_config_list = build_config_list_raw.tokenize('\n')
    config_list.addAll(build_config_list)
  }
}

def buildConfig(ci_scripts_dir, config, filter_group, results) {
  def params = []
  def params_collection = [:]
  def build_config_params
  dir(ci_scripts_dir) {
    echo "Obtaining build configuration for config ${config}"
    echo "Running: python3 ./configs.py -g ${filter_group.replace(" ", " -g ")} ${config}"
    build_config_params = sh(script: """\
python3 ./configs.py -g ${filter_group.replace(" ", " -g ")} ${config}
""", returnStdout: true).trim()
  }
  def lines = build_config_params.tokenize('\n')
  for (String line : lines) {
    def key, value
    (key, value) = line.tokenize('=')
    params += string(name: key, value: value)
    params_collection[key] = value
  }
  params += string(name: 'GERRIT_BRANCH', value: env.GERRIT_BRANCH)
  params += string(name: 'GERRIT_HOST', value: env.GERRIT_HOST)
  params += string(name: 'GERRIT_CHANGE_NUMBER', value: env.GERRIT_CHANGE_NUMBER)
  params += string(name: 'GERRIT_PATCHSET_REVISION', value: env.GERRIT_PATCHSET_REVISION)
  params += string(name: 'GERRIT_REFSPEC', value: env.GERRIT_REFSPEC)
  params += string(name: 'CMSIS_VERSION', value: env.CMSIS_VERSION)
  params += string(name: 'MBEDCRYPTO_VERSION', value: env.MBEDCRYPTO_VERSION)
  params += string(name: 'CODE_REPO', value: env.CODE_REPO)
  return { -> results
    def build_res = build(job: 'tf-m-build-config', parameters: params, propagate: false)
    def build_info = [build_res, config, params_collection]
    results['builds'][build_res.number] = build_info
    def build_url = build_res.getAbsoluteUrl()
    print("${build_res.number}: ${config} ${build_res.result} ${build_url}")
    failure_states = ["FAILURE", "ABORTED", "UNSTABLE", "NOT_BUILT"]
    if (build_res.result in failure_states) {
      error("Build failed at ${build_url}")
    }
    else {
      print("Doing LAVA stuff for ${build_url}")
      params += string(name: 'BUILD_NUMBER', value: "${build_res.number}")
      params += string(name: 'BUILD_URL', value: build_url)
      params += string(name: 'LAVA_URL', value: env.LAVA_URL)
      def lava_res = build(job: 'tf-m-lava-submit', parameters: params, propagate: false)
      if (lava_res.result in failure_states) {
        error("LAVA Create and Submit failed at ${lava_res.getAbsoluteUrl()}")
      }
      else {
        results['lava_jobs'] += lava_res.getDescription()
      }
    }
  }
}

def buildDocs() {
  def params = []
  params += string(name: 'GERRIT_BRANCH', value: env.GERRIT_BRANCH)
  params += string(name: 'GERRIT_HOST', value: env.GERRIT_HOST)
  params += string(name: 'GERRIT_CHANGE_NUMBER', value: env.GERRIT_CHANGE_NUMBER)
  params += string(name: 'GERRIT_PATCHSET_REVISION', value: env.GERRIT_PATCHSET_REVISION)
  params += string(name: 'GERRIT_REFSPEC', value: env.GERRIT_REFSPEC)
  params += string(name: 'CMSIS_VERSION', value: env.CMSIS_VERSION)
  params += string(name: 'MBEDCRYPTO_VERSION', value: env.MBEDCRYPTO_VERSION)
  params += string(name: 'CODE_REPO', value: env.CODE_REPO)
  return {
    def res = build(job: 'tf-m-build-docs', parameters: params, propagate:false)
    print("${res.number}: Docs ${res.result} ${res.getAbsoluteUrl()}")
    if (res.result in ["FAILURE", "ABORTED", "UNSTABLE", "NOT_BUILT"]) {
      error("Build failed at ${res.getAbsoluteUrl()}")
    }
  }
}


def buildCsv(results) {
  def summary = new Summary();
  def csvContent = summary.getBuildCsv(results)
  node("master") {
    writeCSV file: 'build_results.csv', records: csvContent, format: CSVFormat.EXCEL
    archiveArtifacts 'build_results.csv'
  }
}

def writeSummary(results) {
  def summary = new Summary();
  def buildLinks = summary.getLinks(results)
  node("master") {
    writeFile file: "build_links.html", text: buildLinks
    archiveArtifacts 'build_links.html'
  }
}

def lineInString(string, match) {
  def lines = string.split("\n")
  def result = lines.findAll { it.contains(match) }
  return result[0]
}

def getResult(string, match) {
  line = lineInString(string, match)
  a = line.split(match)[1].split(' ')
  score = a[0]
  if (a.size() > 1)
  {
    fail_text = a[1..-1].join(" ")
    return [score, fail_text]
  }
  return [score, ""]
}

def submitJobsToList(results) {
  def all_jobs = []
  for (String result : results){
    jobs_s = result.split('JOBS: ')
    if (jobs_s.size() > 1) {
      all_jobs += jobs_s[1]
    }
  }
  return(all_jobs)
}

def configs = []
def builds = [:]
def results = [:]

node("docker-amd64-xenial") {
  stage("Init") {
    cleanWs()
    dir("tf-m-ci-scripts") {
      git url: '$CI_SCRIPTS_REPO', branch: '$CI_SCRIPTS_BRANCH', credentialsId: 'GIT_SSH_KEY'
    }
  }
  stage("Configs") {
    // Populate configs
    listConfigs('tf-m-ci-scripts', configs, env.FILTER_GROUP)
    results['builds'] = [:]
    results['lava_jobs'] = []
    for (config in configs) {
      builds[config] = buildConfig("tf-m-ci-scripts", config, env.FILTER_GROUP, results)
    }
    builds["docs"] = buildDocs()
  }
}
stage("Builds") {
  def verify = 1
  try {
    parallel(builds)
  } catch (Exception e) {
    print(e)
    manager.buildFailure()
    verify = -1
  } finally {
    print("Verifying status")
    g = new Gerrit()
    g.verifyStatus(verify, 'tf-m-build', 'build')
    print("Building CSV")
    buildCsv(results['builds'])
    writeSummary(results['builds'])
  }
}
node("docker-amd64-xenial") {
  stage("Tests") {
    dir("tf-m-ci-scripts") {
      git url: '$CI_SCRIPTS_REPO', branch: '$CI_SCRIPTS_BRANCH', credentialsId: 'GIT_SSH_KEY'
    }
    def all_jobs = []
    def success = true
    print("Wait for LAVA results here...")
    try {
      all_jobs = submitJobsToList(results['lava_jobs'])
      if (all_jobs.size() > 0) {
        dir("tf-m-ci-scripts") {
          withCredentials([usernamePassword(credentialsId: 'LAVA_CREDENTIALS', passwordVariable: 'LAVA_TOKEN', usernameVariable: 'LAVA_USER')]) {
            output = sh(script: """./lava_helper/lava_wait_jobs.py --job-ids ${all_jobs.join(",")} \
  --lava-url ${env.LAVA_URL} --lava-user ${LAVA_USER} --lava-token ${LAVA_TOKEN} \
  --artifacts-path lava_artifacts --lava-timeout 7200 \
  """, returnStdout: true).trim()
            archiveArtifacts artifacts: 'test_summary.*', allowEmptyArchive: true
            print(output)
            g = new Gerrit()
            def (boot_result, boot_output) = getResult(output, 'BOOT_RESULT: ')
            if (boot_result) {
              g.verifyStatus(boot_result, "lava_boot", "test")
            }
            def (test_result, test_output) = getResult(output, 'TEST_RESULT: ')
            if (test_result) {
              g.verifyStatus(test_result, "lava_test", "test")
            }
            if (boot_result.toInteger() < 1 || test_result.toInteger() < 1) {
              error("Marking job as failed due to failed boots: ${boot_output} or tests: ${test_output}")
            }
          }
        }
      }
      else {
        print("There were no LAVA jobs to test.")
      }
    }
    catch (Exception e) {
      print("ERROR: ${e}")
      success = false
    } finally {
      archiveArtifacts artifacts: 'tf-m-ci-scripts/lava_artifacts/**', allowEmptyArchive: true
      cleanWs()
      if (!success) {
        error("There was an Error waiting for LAVA jobs")
      }
    }
  }
}
