/*
 * 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.
 */
import groovy.json.JsonOutput
import java.net.URI

buildscript {
  repositories {
    mavenCentral()
  }
}

apply plugin: 'java'
apply plugin: 'groovy'

def PACKAGES_GROUP = 'package'

final String VERBOSE = "verbose"
final String DEPS_BUILD = "buildwithdeps"
final boolean buildDependencies = false || System.getProperty(DEPS_BUILD) == 'true'
final String BOM = System.getProperty('bomfile') ?: "$rootDir/bigtop.bom"
def final config  = new ConfigSlurper().parse(new URL("file:$BOM"))

config.bigtop.builddir = projectDir.absolutePath + "/build"
config.bigtop.outputdir = projectDir.absolutePath + "/output"
config.bigtop.distdir = projectDir.absolutePath + "/dist"
config.bigtop.dldir = projectDir.absolutePath + "/dl"

def bomVersions = []

def final BASE_DIR = projectDir.absolutePath
def final REPO_DIR = "$BASE_DIR/bigtop-repos"
def final BUILD_DIR = config.bigtop.builddir
def final OUTPUT_DIR = config.bigtop.outputdir
def final DIST_DIR = config.bigtop.distdir
def final DL_DIR = config.bigtop.dldir

// List of tasks derived from the BOM file is used to preserve the natural order
def bomTasks = []

// Package building and logic around it

def touchTargetFile = { fileName ->
  // to comply with make build
  ant.touch(file:fileName,mkdirs:true)
}
def ifExists = { url ->
  if (url == null) return
  URLConnection uCon = new URL(url).openConnection()
  try {
    return (uCon as HttpURLConnection).responseCode == 200
  } catch(Exception e) {
    return false
  }
}    
def safeDelete = { fileName ->
  exec {
    workingDir '.'
    commandLine 'rm', '-rf', fileName
  }
}
def getDate() {
  new Date().format('E, dd MMM yyyy HH:mm:ss Z')
}
/**
 * To avoid breaking the compat with existing packages let's use the old style names
 */
def toOldStyleName = { newname ->
  newname.toUpperCase().replaceAll("\\-", "_")
}
def setDefaults = { comp ->
  // The closure parameter is a component in the config.bigtop.components
  if (!comp.pkg) {
    comp.pkg = comp.name
  }
  if (!comp.version.pkg) {
    comp.version.pkg = comp.version.base
  }
}
def devNull = new OutputStream() {
  @Override
  public void write(int b) {}
}
def nativePackaging = {
  def result = exec {
    commandLine "/bin/bash", "-c",
    """dpkg-query -S /bin/sh && exit 1
       rpm -qf /bin/sh && exit 2
       exit 0
    """
    ignoreExitValue true
    errorOutput devNull
    standardOutput devNull
  }
  [false, [pkg:"deb", repo:"apt"], [pkg:"rpm", repo:"yum"]][result.getExitValue()]
}.call()

def generateDistributionsFile = { file ->
  def writer = new File(file);
  writer.text ="""Origin: Bigtop
Label: Bigtop
Suite: stable
Codename: bigtop
Version: ${config.bigtop.version}
Architectures: amd64 ppc64el arm64 source
Components: contrib
Description: Bigtop
""";
}

task "packages-help" (description: "All package build related tasks information", group: PACKAGES_GROUP) doLast {
  config.bigtop.components.each { label, comp ->
    println (comp.name + "\n\t[" + tasks.findAll { alltask -> alltask.name.startsWith(comp.name)}*.name.join(", ") + "]")
  }
}

task "bom-json" (description: "List the components of the stack in json format") doLast {
  def componentObjects = config.bigtop.components.sort().collect {
    setDefaults(it.value)
    [
      name: [
        project: it.value.name,
        pkg: it.value.pkg,
        relNotes: it.value.relNotes,
      ],
      tarball: [
        destination: it.value.tarball.destination,
        source: it.value.tarball.source,
      ],
      url: [
        site: it.value.url.site,
        archive: it.value.url.archive,
      ],
      version: [
        base: it.value.version.base,
        pkg: it.value.version.pkg,
        release: it.value.version.release,
      ],
      git: [
         repo: it.value.git.repo,
         ref: it.value.git.ref,
         dir: it.value.git.dir,
      ]
    ]
  }
  def fullDefinition = [
    version: config.bigtop.version,
    components: componentObjects
  ]
  def json = JsonOutput.toJson(fullDefinition)
  println JsonOutput.prettyPrint(json)
}

task "all-components" (description: "List the components of the stack") doLast {
  println "${project.name} ${config.bigtop.version} stack includes the following components"
  config.bigtop.components.sort().each { label, comp ->
    println sprintf ('\t%1$s %2$s', comp.name.padRight(20), comp.version.base.padLeft(15))
  }
}

def genTasks = { target ->
  Task t = task "${target}-download" (dependsOn: "${target}_vardefines",
      description: "Download $target artifacts",
      group: PACKAGES_GROUP) doLast {

    def final TARBALL_SRC = config.bigtop.components[target].tarball.source
    def final TARBALL_DST = config.bigtop.components[target].tarball.destination
    def final DOWNLOAD_DST = config.bigtop.components[target].downloaddst
    def final DOWNLOAD_URL = config.bigtop.components[target].downloadurl

    def final GIT_REPO = project.hasProperty('git_repo') ? project.property('git_repo') : config.bigtop.components[target].git.repo
    def final GIT_REF = project.hasProperty('git_ref') ? project.property('git_ref') : config.bigtop.components[target].git.ref
    def final GIT_DIR = project.hasProperty('git_dir') ? project.property('git_dir') : config.bigtop.components[target].git.dir
    def final GIT_COMMIT_HASH = project.hasProperty('git_commit_hash') ? project.property('git_commit_hash') : config.bigtop.components[target].git.commit_hash
    def final GIT_USER_NAME = config.bigtop.components[target].git.user ?: config.bigtop.git.user
    def final GIT_ACCESS_TOKEN = config.bigtop.components[target].git.token ?: config.bigtop.git.token

    if (!DOWNLOAD_URL && !(GIT_REPO && GIT_REF))
      return

    mkdir(DL_DIR)
    if (TARBALL_DST?.isEmpty() || new File(DOWNLOAD_DST)?.exists() || new File(config.bigtop.components[target].targetdl)?.exists()) {
      println "\tFile $DOWNLOAD_DST appears to be already downloaded. Exiting..."
      return
    }
    if (GIT_REPO && GIT_REF) {
      def dir = GIT_DIR
      if (dir == null || dir.isEmpty()) {
        dir = TARBALL_SRC.substring(0, TARBALL_SRC.lastIndexOf(".t"))
      }
      delete("${DL_DIR}/${dir}")
      def depth = "--depth 1"
      if ( GIT_COMMIT_HASH ) {
        depth = ""
      }
      if (GIT_USER_NAME && GIT_ACCESS_TOKEN) {
        def uri = new URI(GIT_REPO)
        if (!GIT_REPO.toLowerCase().startsWith("http")) {
          println("\tGit credentials supported only with 'http' or 'https' schemes");
          return
        }
        uri = new URI(uri.getScheme(),
         "${GIT_USER_NAME}:${GIT_ACCESS_TOKEN}".toString(), // userInfo
         uri.getHost(), uri.getPort(), uri.getPath(), uri.getQuery(),
         uri.getFragment())
        exec {
          workingDir DL_DIR
          commandLine "git clone ${depth} --branch $GIT_REF ${uri} ${dir}".split()
          errorOutput devNull
          standardOutput devNull
        }
      } else {
        exec {
          workingDir DL_DIR
          commandLine "git clone ${depth} --branch $GIT_REF ${GIT_REPO} ${dir}".split()
          errorOutput devNull
          standardOutput devNull
        }
      }
      exec {
        workingDir "$DL_DIR/${dir}"
        commandLine "git submodule update --init".split()
        errorOutput devNull
        standardOutput devNull
      }
      if ( GIT_COMMIT_HASH ) {
        exec {
          workingDir "$DL_DIR/${dir}"
          commandLine "git reset $GIT_COMMIT_HASH --hard".split()
          errorOutput devNull
          standardOutput devNull
        }
      }
      delete("${DL_DIR}/${dir}/.git")
      exec {
        workingDir DL_DIR
        commandLine "tar -czf ${TARBALL_DST} ${dir}".split()
      }
      delete("${DL_DIR}/${dir}")
    }
    else {
      download {
        src DOWNLOAD_URL
        dest DOWNLOAD_DST
      }
    }
    touchTargetFile(config.bigtop.components[target].targetdl)
  }
  task "${target}-tar" (dependsOn: ["${target}_vardefines", "${target}-download"],
      description: "Preparing a tarball for $target artifacts",
      group: PACKAGES_GROUP) doLast {
    if (new File(config.bigtop.components[target].targettar)?.exists()) {
      println "\tNothing to do. Exiting..."
      return
    }
    def final TAR_DIR = config.bigtop.components[target].tardir
    def final TARBALL_SRC = config.bigtop.components[target].tarball.source ?: ""
    def final TARBALL_DST = config.bigtop.components[target].tarball.destination
    def final DOWNLOAD_DST = config.bigtop.components[target].downloaddst ?: ""
    def final SEED_TAR = config.bigtop.components[target].seedtar

    safeDelete(TAR_DIR); mkdir(TAR_DIR)

    if (TARBALL_SRC.isEmpty() || TARBALL_SRC.endsWith('.zip')) {
      if (TARBALL_SRC.isEmpty()) {
        // if no tar file needed (i.e. bigtop-utils)
        // create some contents to pack later
        copy {
          from 'LICENSE'
          into TAR_DIR
        }
      } else {
        // i.e. a ZIP file
        exec {
          workingDir TAR_DIR
          commandLine "unzip $DOWNLOAD_DST".split(' ')
        }
        def unpacked = new File(TAR_DIR)
        // check wether we have to move contents one level up
        if (unpacked.list().size() == 1) {
          def TOP_LEVEL_DIR = unpacked.list()[0]
          new File("$TAR_DIR/$TOP_LEVEL_DIR").list({ d, f ->
            (f != "." && f != "..")}).each { f ->
              new File("$TAR_DIR/$TOP_LEVEL_DIR/$f").renameTo("$TAR_DIR/$f")
          }
          safeDelete(TOP_LEVEL_DIR)
        }
      }
      // create SEED_TAR
      exec {
        workingDir "$TAR_DIR/.."
        commandLine "tar -czf $SEED_TAR ${new File("$TAR_DIR/..").list().join(' ')}".split(' ')
      }
    } else {
      println "Copy $DOWNLOAD_DST to $SEED_TAR"
      copy {
        from DOWNLOAD_DST
        into config.bigtop.builddir + "/$target/tar/"
        rename TARBALL_DST, SEED_TAR
      }
    }
    touchTargetFile(config.bigtop.components[target].targettar)
  }

  // Keeping the reference to deb task to be used later for correct sequencing
  Task tdeb = task "$target-deb"(dependsOn: "${target}-sdeb",
      description: "Building DEB for $target artifacts",
      group: PACKAGES_GROUP) doLast {
    if (new File(config.bigtop.components[target].targetdeb)?.exists()) {
      println "\tNothing to do. Exiting..."
      return
    }
    def final BIGTOP_BUILD_STAMP = System.getenv('BIGTOP_BUILD_STAMP') ?:
            config.bigtop.components[target].version.release
    def final PKG_NAME = config.bigtop.components[target].pkg
    def final PKG_VERSION = config.bigtop.components[target].version.pkg
    def final PKG_OUTPUT_DIR = config.bigtop.components[target].outputdir
    def final BASE_VERSION = config.bigtop.components[target].version.base
    def final SRCDEB = "${PKG_NAME}_$PKG_VERSION-${BIGTOP_BUILD_STAMP}.dsc"
    def final HADOOP_VERSION = config.bigtop.components["hadoop"].version.pkg

    exec {
      workingDir PKG_OUTPUT_DIR
      commandLine "dpkg-source -x $SRCDEB".split(' ')
    }
// Order of debuild parameters is important; hence specifying explicitely rather
// than in an array of args
    def command = """debuild \
--preserve-envvar PATH \
--preserve-envvar MAVEN3_HOME \
--preserve-envvar MAVEN_OPTS \
--preserve-envvar JAVA_HOME \
--preserve-envvar BIGTOP_JDK \
--set-envvar=HADOOP_VERSION=$HADOOP_VERSION \
--set-envvar=${toOldStyleName(target)}_BASE_VERSION=$BASE_VERSION \
--set-envvar=${toOldStyleName(target)}_VERSION=$PKG_VERSION \
--set-envvar=${toOldStyleName(target)}_RELEASE=$BIGTOP_BUILD_STAMP \
-uc -us -b
"""
    exec {
      workingDir "$PKG_OUTPUT_DIR/$PKG_NAME-$PKG_VERSION"
      commandLine command.split(' ')
    }
    exec {
      workingDir "$PKG_OUTPUT_DIR"
      commandLine 'rm','-rf',"$PKG_NAME-$PKG_VERSION"
    }
    touchTargetFile(config.bigtop.components[target].targetdeb)
  }
  // Guarantee that tasks are ran in the order set by BOM file dependencies section
  if (buildDependencies)
    config.bigtop.dependencies.each { dependsOn, dependees ->
      if (dependees.contains(tdeb.name-"-deb")) tdeb.dependsOn "$dependsOn-deb"
    }
  // If dependencies aren't explicitly set, the default build order is defined
  // by the sequence of the components in the BOM file
  if (!config.bigtop.dependencies && bomTasks.size() > 0)
    tdeb.mustRunAfter "${bomTasks.get(bomTasks.size() - 1)}-deb".toLowerCase()
   task "$target-sdeb" (dependsOn: ["${target}_vardefines",  "${target}-tar"],
      description: "Building SDEB for $target artifacts",
      group: PACKAGES_GROUP
  ) doLast {
    if (new File(config.bigtop.components[target].targetsdeb)?.exists()) {
      println "\tNothing to do. Exiting..."
      return
    }
     def final BIGTOP_BUILD_STAMP = System.getenv('BIGTOP_BUILD_STAMP') ?:
             config.bigtop.components[target].version.release
    def final TARBALL_SRC = config.bigtop.components[target].tarball.source
    def final TARBALL_DST = config.bigtop.components[target].tarball.destination ?: TARBALL_SRC
    def final PKG_BUILD_DIR = config.bigtop.components[target].builddir
    def final NAME = config.bigtop.components[target].name
    def final PKG_NAME = config.bigtop.components[target].pkg
    def final SEED_TAR = config.bigtop.components[target].seedtar
    def final PKG_VERSION = config.bigtop.components[target].version.pkg
    def final PKG_OUTPUT_DIR = config.bigtop.components[target].outputdir
    delete ("$PKG_BUILD_DIR/deb")
    def final DEB_BLD_DIR = "$PKG_BUILD_DIR/deb/$NAME-${PKG_VERSION}"
    def final DEB_PKG_DIR = "$PKG_BUILD_DIR/deb/$PKG_NAME-${PKG_VERSION}-${BIGTOP_BUILD_STAMP}"
    mkdir (DEB_BLD_DIR)
    copy {
      from SEED_TAR
      into "$PKG_BUILD_DIR/deb/"
      rename TARBALL_DST, "${PKG_NAME}_${PKG_VERSION}.orig.tar.gz"
    }
    exec {
      workingDir DEB_BLD_DIR
      commandLine "tar --strip-components 1 -xf $DEB_BLD_DIR/../${PKG_NAME}_${PKG_VERSION}.orig.tar.gz".split(' ')
    }
    copy {
      from fileTree("${BASE_DIR}/bigtop-packages/src/deb/$NAME") {
        include '**/*'
      }
      into "$DEB_BLD_DIR/debian"
    }
    copy {
      from "${BASE_DIR}/bigtop-packages/src/templates/init.d.tmpl"
      into "$DEB_BLD_DIR/debian"
    }
    copy {
      from "${BASE_DIR}/bigtop-packages/src/scripts"
      into "$DEB_BLD_DIR/debian"
    }
    copy {
      from "${BASE_DIR}/bigtop-packages/src/extensions"
      into "$DEB_BLD_DIR/debian"
    }
    copy {
      from fileTree("$BASE_DIR/bigtop-packages/src/common/$NAME") {
        include '**/*'
      }
      into "$DEB_BLD_DIR/debian"
    }
    // Prepeare bom file with all the versions
    def bomWriter = new File("$DEB_BLD_DIR/debian/bigtop.bom").newWriter()
    bomVersions.each { bomWriter << "$it\n"}
    bomWriter.close()
    // Create changelog
    def changelog = new File("$DEB_BLD_DIR/debian/changelog").newWriter()
    changelog << "$PKG_NAME ($PKG_VERSION-$BIGTOP_BUILD_STAMP) stable; urgency=low\n"
    changelog << "  Clean build\n"
    changelog << " -- Bigtop <dev@bigtop.apache.org>  ${getDate()}\n"
    changelog.close()

    // Move patches and create "series"
    def patches = new File( "$DEB_BLD_DIR/debian").list({ d, f -> f ==~ /patch.*diff/}).sort()
    if (patches.size() > 0) {
      mkdir("$DEB_BLD_DIR/debian/patches")
      def seriesWriter = new File("$DEB_BLD_DIR/debian/patches/series").newWriter()
      patches.each { f ->
        def res = new File("$DEB_BLD_DIR/debian/$f").renameTo( "$DEB_BLD_DIR/debian/patches/$f")
        seriesWriter << "$f\n"
      }
      seriesWriter.close()
    }
    // Deleting obsolete files
    delete fileTree(dir: "$DEB_BLD_DIR/debian", includes: ['*.ex', '*.EX', '*.~'])
    // Creating source package
    exec {
      workingDir DEB_BLD_DIR
      commandLine "dpkg-buildpackage -uc -us -sa -S".split(' ')
    }
    mkdir(PKG_OUTPUT_DIR)
    copy {
      from fileTree(dir: "$DEB_PKG_DIR/..", includes: ['*.dsc', '*.diff.gz', '*.debian.tar.gz', '*.debian.tar.xz', "*_source.changes", "*.orig.tar.gz" ])
      into PKG_OUTPUT_DIR
    }
    safeDelete(DEB_BLD_DIR)
    touchTargetFile(config.bigtop.components[target].targetsdeb)
  }

  // Keeping the reference to task to be used later for correct sequencing
  Task trpm = task "$target-rpm" (dependsOn: ["${target}-srpm"],
      description: "Building RPM for $target artifacts",
      group: PACKAGES_GROUP) doLast {
    if (new File(config.bigtop.components[target].targetrpm)?.exists()) {
      println "\tNothing to do. Exiting..."
      return
    }
    def final BIGTOP_BUILD_STAMP = System.getenv('BIGTOP_BUILD_STAMP') ?:
            config.bigtop.components[target].version.release
    def final PKG_BUILD_DIR = config.bigtop.components[target].builddir
    def final NAME = config.bigtop.components[target].name
    def final PKG_NAME = config.bigtop.components[target].pkg
    def final PKG_OUTPUT_DIR = config.bigtop.components[target].outputdir
    def final PKG_VERSION = config.bigtop.components[target].version.pkg
    def final BASE_VERSION = config.bigtop.components[target].version.base
    def final HADOOP_VERSION = config.bigtop.components["hadoop"].version.pkg
    def RELEASE_DIST = "rpmbuild --eval '%{?dist}' 2>/dev/null".execute().text.trim().replaceAll("'",'')
    def SRCRPM="$PKG_OUTPUT_DIR/$PKG_NAME-${PKG_VERSION}-$BIGTOP_BUILD_STAMP${RELEASE_DIST}.src.rpm"

    def final DO_MAVEN_DEPLOY = project.findProperty('doMavenDeploy') == 'true'
    def final MAVEN_DEPLOY_SOURCE = project.findProperty('mavenDeploySource') == 'true'
    def final MAVEN_REPO_ID = project.hasProperty('mavenRepoId') ? project.property('mavenRepoId') : 'default'
    def final MAVEN_REPO_URI = project.hasProperty('mavenRepoUri') ? project.property('mavenRepoUri') : null

    def command = [
        '--define', "_topdir $PKG_BUILD_DIR/rpm/",
        '--define', "${NAME}_base_version $BASE_VERSION",
        '--define', "hadoop_version ${HADOOP_VERSION}",
        '--define', "${NAME}_version ${PKG_VERSION}",
        '--define', "${NAME}_release ${BIGTOP_BUILD_STAMP}%{?dist}",
        '--rebuild', SRCRPM,
        '--define', "do_maven_deploy ${DO_MAVEN_DEPLOY}",
        '--define', "maven_deploy_source ${MAVEN_DEPLOY_SOURCE}"
    ]

   if (MAVEN_REPO_URI != null) {
      command.addAll('--define', "maven_repo_uri ${MAVEN_REPO_URI}")
      command.addAll('--define', "maven_repo_id ${MAVEN_REPO_ID}")
    }

    exec {
      workingDir BASE_DIR
      executable 'rpmbuild'
      args command
    }
    copy {
      from fileTree("$PKG_BUILD_DIR/rpm/RPMS") {
        include '**/*'
      }
      into PKG_OUTPUT_DIR
    }
    touchTargetFile(config.bigtop.components[target].targetrpm)
  }
  // Guarantee that tasks are ran in the order set by BOM file dependencies section
  if (buildDependencies)
    config.bigtop.dependencies.each { dependsOn, dependees ->
      if (dependees.contains(trpm.name - "-rpm")) trpm.dependsOn "$dependsOn-rpm"
    }
  // If dependencies aren't explicitly set, the default build order is defined
  // by the sequence of the components in the BOM file
  if (!config.bigtop.dependencies && bomTasks.size() > 0)
    trpm.mustRunAfter "${bomTasks.get(bomTasks.size() - 1)}-rpm".toLowerCase()
  task "$target-srpm" (dependsOn: ["${target}_vardefines" , "${target}-tar"],
      description: "Building SRPM for $target artifacts",
      group: PACKAGES_GROUP) doLast {
    if (new File(config.bigtop.components[target].targetsrpm)?.exists()) {
      println "\tNothing to do. Exiting..."
      return
    }
    def final BIGTOP_BUILD_STAMP = System.getenv('BIGTOP_BUILD_STAMP') ?:
            config.bigtop.components[target].version.release
    def final NAME = config.bigtop.components[target].name
    def final PKG_NAME = config.bigtop.components[target].pkg
    def final PKG_NAME_FOR_PKG = NAME.replaceAll("-", "_")
    def final PKG_BUILD_DIR = config.bigtop.components[target].builddir
    def final SEED_TAR = config.bigtop.components[target].seedtar
    def final PKG_VERSION = config.bigtop.components[target].version.pkg
    def final BASE_VERSION = config.bigtop.components[target].version.base
    def final PKG_OUTPUT_DIR = config.bigtop.components[target].outputdir
    safeDelete ("$PKG_BUILD_DIR/rpm")
    ['INSTALL','SOURCES','BUILD','SRPMS','RPMS'].each { rpmdir ->
      mkdir("$PKG_BUILD_DIR/rpm/$rpmdir")
    }
    copy {
      from fileTree("${BASE_DIR}/bigtop-packages/src/rpm/$NAME") {
        include '**/*'
      }
      into "$PKG_BUILD_DIR/rpm"
    }
    copy {
      from SEED_TAR
      into "$PKG_BUILD_DIR/rpm/SOURCES"
    }
    copy {
      from "${BASE_DIR}/bigtop-packages/src/templates/init.d.tmpl"
      into "$PKG_BUILD_DIR/rpm/SOURCES"
    }
    copy {
      from "${BASE_DIR}/bigtop-packages/src/extensions"
      into "$PKG_BUILD_DIR/rpm/SOURCES"
      include "*"
    }
    copy {
      from "${BASE_DIR}/bigtop-packages/src/scripts"
      into "$PKG_BUILD_DIR/rpm/SOURCES"
      include "*"
    }
    copy {
      from fileTree("$BASE_DIR/bigtop-packages/src/common/$NAME") {
        include '**/*'
      }
      into "$PKG_BUILD_DIR/rpm/SOURCES"
    }
    // Writing bigtop.bom files with all the versions
    def bomWriter = new File("$PKG_BUILD_DIR/rpm/SOURCES/bigtop.bom").newWriter()
    bomVersions.each { bomWriter << "$it\n"}
    bomWriter.close()

    def specFileName = "${PKG_BUILD_DIR}/rpm/SPECS/${NAME}.spec"
    def specTmpFileName = "${PKG_BUILD_DIR}/rpm/SPECS/tmp_${NAME}.spec"
    def specFile = new File(specFileName)
    def specWriter = new File(specTmpFileName).newWriter()
    def patches = new File("${PKG_BUILD_DIR}/rpm/SOURCES").list({ d, f -> f ==~ /patch.*diff/}).sort()
    specFile.eachLine { line ->
      if (line.startsWith("#BIGTOP_PATCH_FILES")) {
        def patchNum = 0
        patches.each { p ->
          specWriter << "Patch$patchNum: $p\n"
          patchNum++
        }
      } else {
        if (line.startsWith("#BIGTOP_PATCH_COMMANDS")) {
          def patchNum = 0
          patches.each { p ->
            specWriter << "%patch$patchNum -p1\n"
            patchNum++
          }
        } else {
          specWriter << "$line\n"
        }
      }
    }
    specWriter.close()
    specFile.delete()
    new File(specTmpFileName).renameTo(specFileName)

    def command = [
        '--define', "_topdir $PKG_BUILD_DIR/rpm/",
        '--define', "${PKG_NAME_FOR_PKG}_base_version $BASE_VERSION",
        '--define', "${PKG_NAME_FOR_PKG}_version ${PKG_VERSION}",
        '--define', "${PKG_NAME_FOR_PKG}_release ${BIGTOP_BUILD_STAMP}%{?dist}",
        '-bs', '--nodeps', "--buildroot=${PKG_BUILD_DIR}/rpm/INSTALL",
        specFileName,
    ]
    exec {
      workingDir BASE_DIR
      executable 'rpmbuild'
      args command
    }
    mkdir(PKG_OUTPUT_DIR)
    def RELEASE_DIST = "rpmbuild --eval '%{?dist}' 2>/dev/null".execute().text.trim().replaceAll("'",'')
    copy {
      from "$PKG_BUILD_DIR/rpm/SRPMS/${PKG_NAME}-${PKG_VERSION}-${BIGTOP_BUILD_STAMP}${RELEASE_DIST}.src.rpm"
      into PKG_OUTPUT_DIR
    }
    touchTargetFile(config.bigtop.components[target].targetsrpm)
  }
  if (nativePackaging) {
    def ptype = nativePackaging.pkg
    task "$target-pkg" (dependsOn: "$target-$ptype",
        description: "Invoking a native binary packaging target $ptype",
        group: PACKAGES_GROUP) doLast {
    }
    task "$target-spkg" (dependsOn: "$target-s$ptype",
        description: "Invoking a native binary packaging target s$ptype",
        group: PACKAGES_GROUP) doLast {
    }
  }
  task "$target-pkg-ind" (
          description: "Invoking a native binary packaging for $target in Docker. Usage: \$ ./gradlew " +
                  "-POS=[centos-7|fedora-31|debian-9|ubuntu-16.04] " +
                  "-Pprefix=[trunk|1.4.0|1.3.0|1.2.1|...] $target-pkg-ind " +
                  "-Pnexus=[true|false]",
          group: PACKAGES_GROUP) doLast {
    def _prefix = project.hasProperty("prefix") ? prefix : "trunk"
    def _OS = project.hasProperty("OS") ? OS : "centos-7"
    def _target_pkg = "$target-pkg"
    def _docker_run_option = project.hasProperty("docker-run-option") ? this.'docker-run-option' : ""
    def additionalConfigKeys = ['git_repo', 'git_ref', 'git_dir', 'git_commit_hash', 'base_version']
    additionalConfigKeys.each { key ->
      if (project.hasProperty(key)) {
        _target_pkg += " -P${key}=" + project.property(key)
      }
    }
    def command = [
            'bash', '-x',
            './bigtop-ci/build.sh',
            '--prefix', _prefix,
            '--os', _OS,
            '--target', _target_pkg,
            '--docker-run-option', _docker_run_option,
    ]
    if ( project.hasProperty("nexus") ) {
      command.add('--nexus')
    }

    println "Building $_prefix $_target_pkg on $_OS in Docker...\n"

    exec {
      workingDir BASE_DIR
      commandLine command
    }
  }
  task "$target-version" (description: "Show version of $target component", group: PACKAGES_GROUP) doLast {
    println "Base: ${config.bigtop.components[target].version.base}"
  }
  task "${target}_vardefines" doLast {
    if (project.hasProperty('base_version')) {
      def BASE_VERSION = project.property("base_version")
      if (config.bigtop.components[target].tarball.source) {
        config.bigtop.components[target].tarball.source = config.bigtop.components[target].tarball.source
                .replaceAll(config.bigtop.components[target].version.base, BASE_VERSION)
      }
      config.bigtop.components[target].tarball.destination = config.bigtop.components[target].tarball.destination
              .replaceAll(config.bigtop.components[target].version.base, BASE_VERSION)

      config.bigtop.components[target].version.base = BASE_VERSION
      config.bigtop.components[target].version.pkg = BASE_VERSION
    }

    setDefaults(config.bigtop.components[target])

    config.bigtop.components[target].package.release = '1'

    config.bigtop.components[target].builddir = config.bigtop.builddir + "/$target"
    config.bigtop.components[target].outputdir = config.bigtop.outputdir + "/$target"
    config.bigtop.components[target].srcdir = config.bigtop.builddir + "/source"
    config.bigtop.components[target].tardir = config.bigtop.builddir + "/$target/tar/${target}-${config.bigtop.components[target].version.base}"
    config.bigtop.components[target].seedtar = config.bigtop.builddir + "/$target/tar/" + config.bigtop.components[target].tarball.destination

    config.bigtop.components[target].downloadurl =
        (!config.bigtop.components[target].url.isEmpty() &&
            !config.bigtop.components[target].url.site.isEmpty() &&
            !config.bigtop.components[target].tarball.source.isEmpty()) ?
            config.bigtop.components[target].url.site + '/' + config.bigtop.components[target].tarball.source : null
        if (!config.bigtop.components[target].tarball.destination.isEmpty())
          config.bigtop.components[target].downloaddst = DL_DIR + '/' + config.bigtop.components[target].tarball.destination

    // test that the download url will return http 200.  If it does not, use the ARCHIVE url instead of the MIRROR SITE url
    if (!config.bigtop.components[target].url.isEmpty() && !ifExists(config.bigtop.components[target].downloadurl)) {
      config.bigtop.components[target].downloadurl = config.bigtop.components[target].url.archive + '/' + config.bigtop.components[target].tarball.source
    }

    config.bigtop.components[target].targetdl  = config.bigtop.components[target].builddir + '/.download'
    config.bigtop.components[target].targettar  = config.bigtop.components[target].builddir + '/.tar'
    config.bigtop.components[target].targetsrpm  = config.bigtop.components[target].builddir + '/.srpm'
    config.bigtop.components[target].targetrpm  = config.bigtop.components[target].builddir + '/.rpm'
    config.bigtop.components[target].targetsdeb  = config.bigtop.components[target].builddir + '/.sdeb'
    config.bigtop.components[target].targetdeb  = config.bigtop.components[target].builddir + '/.deb'
    config.bigtop.components[target].targetrelnotes  = config.bigtop.components[target].builddir + '/.relnotes'

    if (System.getProperty(VERBOSE)) {
      println "$target properties (explcit and derived)"
      config.bigtop.components[target].toProperties(target).each {k ,v ->
        println "$k\t= $v"
      }
    }
  }

  task "$target-info" (dependsOn: "${target}_vardefines",
      description: "Info about $target component build",
      group: PACKAGES_GROUP) doLast {
    println "Info for package $target"
    println "  Will download from URL: ${config.bigtop.components[target].downloadurl}"
    println "  To destination file: ${config.bigtop.components[target].downloaddst}"
    println "  Then unpack into ${config.bigtop.components[target].srcdir}"
    println "  And create a seed tarball ${config.bigtop.components[target].seedtar}"

    println "Version: " + config.bigtop.components[target].version.base
    //TODO more about stamping
  }
  task "$target-relnotes" (description: "Preparing release notes for $target. No yet implemented!!!", group: PACKAGES_GROUP) doLast {
  }
  task "$target-clean" (dependsOn: "${target}_vardefines",
      description: "Removing $target component build and output directories",
      group: PACKAGES_GROUP) doLast {
    safeDelete(config.bigtop.components[target].builddir)
    safeDelete(config.bigtop.components[target].outputdir)
  }
  task "$target-help" (description: "List of available tasks for $target", group: PACKAGES_GROUP) doLast {
    println (target + "\n\t[" + tasks.findAll { alltask -> alltask.name.startsWith(target)}*.name.join(", ") + "]")
  }

  bomTasks.add(target)
}

// Let's enforce some of the configuration requirements
private void doValidateBOM(config) {
  assert config.bigtop.version
  assert config.bigtop.stack.jdk
  assert config.bigtop.stack.scala
  assert config.bigtop.apache.size() != 0
}

// We need to make sure that all dynamic tasks are available for invocation
project.afterEvaluate {
  doValidateBOM(config)
  config.bigtop.components.each { component_label, comp ->
    assert component_label == comp.name
    genTasks(comp.name)
  }
  // Versions need to be preserved for more than just component:
  //  - there are JDK version requirement
  //  - possibly more in the future
  bomVersions = config.bigtop.components.collect {
    "${toOldStyleName(it.value.name)}_VERSION=${it.value.version.base}"
  }
  bomVersions += config.bigtop.stack.collect { // Version of the stack have different syntax
    "${toOldStyleName(it.key)}_VERSION=${it.value.version_base}"
  }
  if (System.getProperty(VERBOSE))println "BIGTOP_BOM_VERSIONS:\n${bomVersions.join(' ')}"
  // Putting all targets of different types into one common target
  task "srpm" (dependsOn: tasks.findAll { alltask -> alltask.name.endsWith("-srpm")}*.name,
      description: "Build all SRPM packages for the stack components",
      group: PACKAGES_GROUP
  ) doLast { }
  task "rpm" (dependsOn: tasks.findAll { alltask -> alltask.name.endsWith("-rpm")}*.name,
      description: "Build all RPM packages for the stack",
      group: PACKAGES_GROUP
  ) doLast { }
  task "sdeb" (dependsOn: tasks.findAll { alltask -> alltask.name.endsWith("-sdeb")}*.name,
      description: "Build all SDEB packages for the stack components",
      group: PACKAGES_GROUP
  ) doLast { }
  task "deb" (dependsOn: tasks.findAll { alltask -> alltask.name.endsWith("-deb")}*.name,
      description: "Build all DEB packages for the stack components",
      group: PACKAGES_GROUP
  ) doLast { }
  task "pkgs" (dependsOn: tasks.findAll { alltask -> alltask.name.endsWith("-pkg")}*.name,
      description: "Build all native packages for the stack components",
      group: PACKAGES_GROUP
  ) doLast { }
  task "pkgs-ind" (dependsOn: tasks.findAll { alltask -> alltask.name.endsWith("-pkg-ind")}*.name,
          description: "Build all native packages for the stack components inside Docker",
          group: PACKAGES_GROUP
  ) doLast { }

  task allclean (dependsOn: [clean, tasks.findAll { alltask -> alltask.name.endsWith("-clean")}*.name],
      description: "Removing $BUILD_DIR, $OUTPUT_DIR, and $DIST_DIR.\n\t\t" +
        "Cleaning all components' build and output directories.",
      group: PACKAGES_GROUP) doLast {
    safeDelete(BUILD_DIR)
    safeDelete(OUTPUT_DIR)
    safeDelete(DIST_DIR)
  }
  task realclean (dependsOn: allclean,
      description: "Removing $BUILD_DIR, $OUTPUT_DIR, $DIST_DIR, and $DL_DIR",
      group: PACKAGES_GROUP) doLast {
    delete (DL_DIR)
  }
}

task "apt" (
    description: "Creating APT repository",
    group: PACKAGES_GROUP) doLast {

  delete ( "$OUTPUT_DIR/apt")
  mkdir ("$OUTPUT_DIR/apt/conf")

  generateDistributionsFile("$OUTPUT_DIR/apt/conf/distributions");

  fileTree (OUTPUT_DIR) {
    include "*/*.changes"
  }.each  { changeFile ->
    exec {
      workingDir BUILD_DIR
      commandLine "reprepro -Vb $OUTPUT_DIR/apt include bigtop $changeFile".split(' ')
    }
  }
}

task "yum" (
    description: "Creating YUM repository",
    group: PACKAGES_GROUP) doLast {
  delete ( "$OUTPUT_DIR/repodata")
  exec {
    workingDir BUILD_DIR
    commandLine "createrepo -o $OUTPUT_DIR $OUTPUT_DIR".split(' ')
  }
}

if (nativePackaging) {
  task "repo" (dependsOn: nativePackaging.repo,
      description: "Invoking a native repository target ${nativePackaging.repo}",
      group: PACKAGES_GROUP) doLast { }
}

task "repo-ind" (
    description: "Invoking a native repository in Docker. Usage: \$ ./gradlew " +
            "-POS=[centos-7|fedora-31|debian-9|ubuntu-16.04] " +
            "-Pprefix=[trunk|1.4.0|1.3.0|1.2.1|...] repo-ind",
    group: PACKAGES_GROUP) doLast {
  def _prefix = project.hasProperty("prefix") ? prefix : "trunk"
  def _OS = project.hasProperty("OS") ? OS : "centos-7"
  def _docker_run_option = project.hasProperty("docker-run-option") ? this.'docker-run-option' : ""
  def command = [
      'bash', '-x',
      './bigtop-ci/build.sh',
      '--prefix', _prefix,
      '--os', _OS,
      '--target', 'repo',
      '--docker-run-option', _docker_run_option
  ]
  exec {
    workingDir BASE_DIR
    commandLine command
  }
}
