// Build body of the release pipeline for the Qt6-migrated legatus
// validation-scope branch (story/release-validation-scope): TetraIF, Z,
// Lts/Common (+ Lts/Proxies/TrainingAreaBase) -> 5 release DEB packages.
//
// Loaded by jenkins-ci-rme/Jenkinsfile inside the allocated node after the
// checkout; job properties/parameters live there.
//
// Workspace layout (checked out by Jenkins, DLBO Qt6 repo):
//   <WORKSPACE>/
//     jenkins-ci-rme/Jenkinsfile     (entry point)
//     new_docker_build.sh            (local build driver)
//     rpmbuild/make_rpm_ubuntu26.py  (in-tree packaging)
//     jenkins-ci-rme/                (this pipeline)
//
// The build container image is the prebuilt image shipped in the repo as
// legatus-qt6_1.0.tar.gz; it is loaded onto the agent when not installed
// yet, never built here.

def project = params.ProjectName
def imageName = 'legatus-qt6:1.0'
def imageArchive = 'legatus-qt6_1.0.tar.gz'

env.GIT_TERMINAL_PROMPT = '0'
env.LTS_VERSION = "${params.LtsVersion}"
env.ARTIFACTREPO = 'https://internal-repo.sl.defence-elec.de'

// OS versions this build covers, built one after another (the builder
// stages the workspace into a shared deb_stage directory); output is
// still isolated under rpms/${project}/${osVersion}.
def osVersions = params.OsVersions.split(',').collect { it.trim() }.findAll { it }

def buildOsVersion = { String osVersion ->
    def rpmsDir = "rpms/${project}/${osVersion}"

    stage("Prepare ${project} (${osVersion})") {
        sh "rm -rf ${rpmsDir}"
        sh "mkdir -p ${rpmsDir}"
    }

    stage("Build DEB ${project} (${osVersion})") {
        def buildContainer = docker.image("${imageName}")
        def guezMode = (project == 'guez') ? 'ON' : 'OFF'

        def dockerOpts = "--init --shm-size=2g" +
                         " -v ${WORKSPACE}:/workspace" +
                         " -e WORKSPACE=/workspace" +
                         " -e PROJECT_BASE_DIR=/workspace" +
                         " -e PROJECT=${project}" +
                         " -e OS_VERSION=${osVersion}" +
                         " -e LTS_VERSION=${LTS_VERSION}" +
                         " -e GUEZ_MODE=${guezMode}" +
                         " -e BUILD_NUMBER=${env.BUILD_NUMBER}" +
                         " -e BUILD_TAG=${env.BUILD_TAG}"

        buildContainer.inside(dockerOpts) {
            sh "bash /workspace/jenkins-ci-rme/jenkins_builder_ubuntu26.sh"
        }
    }

    stage("Coverage ${project} (${osVersion})") {
        if (!params.RunCoverage) {
            echo "Coverage skipped for ${project} (OS ${osVersion}, RunCoverage=false)"
            return
        }
        // The driver (run on the agent, same pattern as the image-build
        // stage) builds the scope with -O0 --coverage, runs ctest and
        // collects the lcov report into the workspace mount.
        sh "bash ./new_docker_build.sh --docker-image ${imageName} --run-coverage --coverage-output-dir ${WORKSPACE}/coverage/${project}/${osVersion}"
        archiveArtifacts artifacts: "coverage/${project}/${osVersion}/**", allowEmptyArchive: true
    }

    stage("Publish ${project} (${osVersion})") {
        if (params.PublishArtifactRepo) {
            withCredentials([usernamePassword(credentialsId: 'internal-repo-uploader',
                                              usernameVariable: 'CURL_USER',
                                              passwordVariable: 'CURL_PASS')]) {
                sh """
                    export CURL_CRED="\${CURL_USER}:\${CURL_PASS}"
                    export PROJECT='${project}'
                    export OS_VERSION='${osVersion}'
                    export LTS_VERSION='${LTS_VERSION}'
                    export BUILD_NUMBER='${env.BUILD_NUMBER}'
                    export ARTIFACTREPO='${env.ARTIFACTREPO}'
                    export ARTIFACTFOLDER='${project}'
                    bash jenkins-ci-rme/jenkins_publisher_ubuntu26.sh
                """
            }

            def tdsUrl     = readFile("url-${project}-${osVersion}.txt").trim()
            def tdsVersion = readFile("tdsversion-${project}-${osVersion}.txt").trim()
            def link = """<a href="${tdsUrl}" target="_blank">${project} ${tdsVersion} (OS ${osVersion})</a>"""
            currentBuild.description = currentBuild.description ? "${currentBuild.description}<br/>${link}" : link
        } else {
            echo "Artifact-repo publish skipped for ${project} (OS ${osVersion}, PublishArtifactRepo=false)"
        }
    }
}

try {
    stage("Initialization") {
        echo "Legatus Qt6 release build initialized — branch '${env.BRANCH_NAME}', project: ${project}, LTS ${env.LTS_VERSION}, OS version(s): ${osVersions.join(', ')}"
    }

    stage("Install build image") {
        // Reuse the prebuilt image when it is already installed on the agent;
        // otherwise load it from the archive shipped in the repo.
        def imageInstalled = sh(script: "docker image inspect '${imageName}' >/dev/null 2>&1", returnStatus: true) == 0
        if (imageInstalled) {
            echo "Build image ${imageName} is already installed on the agent - reusing it"
        } else {
            if (!fileExists(imageArchive)) {
                error "Build image ${imageName} not installed and image archive ${imageArchive} not found in the workspace"
            }
            echo "Build image ${imageName} not installed on the agent - loading it from ${imageArchive}"
            sh "docker load -i '${imageArchive}'"
            if (sh(script: "docker image inspect '${imageName}' >/dev/null 2>&1", returnStatus: true) != 0) {
                error "Build image ${imageName} still not available after loading ${imageArchive}"
            }
            echo "Build image ${imageName} installed on the agent"
        }
    }

    for (osVersion in osVersions) {
        buildOsVersion(osVersion)
    }

    stage("Finalization") {
        echo "Legatus Qt6 release build completed — project: ${project} (LTS ${env.LTS_VERSION}), OS version(s): ${osVersions.join(', ')}"
    }

    currentBuild.result = 'SUCCESS'
} catch (e) {
    currentBuild.result = 'FAILURE'
    throw e
}
