@Library("ogury-jenkins-lib@v5.6.0")

def projectName = pipelineUtils.getProjectName()
def podLabel = pipelineUtils.getPodLabel()
def confMap = pipelineUtils.getConf()

def helmChartVersion = "5.12.0"

def oguryEnv = confMap["environment"]
def dockerTag = confMap["dockerTag"]
def deploy = confMap["deploy"]
def secretNames = [:]

def regions;
def multiAZ;

if (oguryEnv == "devc") {
  regions = ["eu-west-1"];
  multiAZ = false
} else {
  regions = ["eu-west-1", "us-east-1","us-west-2", "ap-northeast-1"]
  multiAZ = true
}

def sonarCmd = 'echo "No sonar for branch"'
if(env.CHANGE_ID != null){
  sonarCmd = 'yarn sonar:pr'
}

if(env.BRANCH_NAME == "master"){
  sonarCmd = 'yarn sonar'
}

def clusters = pipelineUtils.getClusters(multiAZ)

pipeline {
    agent {
        kubernetes {
            label "${podLabel}"
            defaultContainer 'worker'
            yaml script {
                templates.docker(imageVersion: "2.0.2", role: "infra-kube1-jenkins-pod-slave")
            }
        }
    }
    stages {
        stage('Init tests') {
            when {
                anyOf {
                    expression{env.CHANGE_ID != null}
                    expression{env.BRANCH_NAME == "master"}
                    changelog '.*#RUNTEST.*'
                }
            }
            agent {
               kubernetes {
                 label "${podLabel}-tests"
                 defaultContainer 'node'
                 yamlFile 'JenkinsPodTemplate.yaml'
               }
            }
            environment {
                NPM_TOKEN = credentials('NPM_TOKEN')
                SONAR_TOKEN = credentials('SONAR_CLOUD_TOKEN')
                NODE_OPTIONS="--max-old-space-size=4092"
            }
            stages {
                stage("Fetch master ref for Sonar PR analysis") {
                    environment {
                        GIT_SSH_COMMAND = 'ssh -o StrictHostKeyChecking=no'
                    }
                    when {
                        expression{env.CHANGE_ID != null}
                    }
                    steps {
                        sshagent(['Ogy-JenkinsAuth']) {
                            sh """
                                git fetch --no-tags ${env.GIT_URL} +refs/heads/master:refs/remotes/origin/master
                            """
                        }
                    }
                }

                stage("Build tests") {
                    steps {
                        sh "apt-get -y update && apt-get -y install python make g++"
                        sh "apt-get -y install zlib1g-dev openssl libsasl2-2 libsasl2-dev"
                        sh "yarn install --production=false --frozen-lockfile"
                        sh "yarn run lint:ci"
                    }
                }

                stage("Run tests (Unit/Int./Cov.) ") {
                  steps {
                    sh "yarn test:cov && yarn test:report"
                  }
                }

                stage("Push to Sonar") {
                  steps {
                    sh sonarCmd
                  }
                }
            }
        }

        stage("Deployment") {
            when {
               expression { deploy }
            }
            stages {
                stage('Build docker image') {
                    environment {
                        NPM_TOKEN = credentials('NPM_TOKEN')
                    }
                    steps {
                        script {
                            dockerUtils.build(
                                name: projectName,
                                tag: dockerTag,
                                regions: regions,
                                buildArgs: ["NPM_TOKEN": NPM_TOKEN],
                                push: deploy,
                                failOnCriticalVulnerability: true,
                            )
                        }
                    }
                }

                stage('Initializing Kubernetes namespace') {
                    steps {
                        script {
                            kubeUtils.init(
                                name: projectName,
                                regions: regions,
                                environment: oguryEnv,
                                clusters: clusters
                            )
                        }
                    }
                }

                stage('Create secrets') {
                    steps {
                        script {
                            secretNames = kubeUtils.createSecretFromSSM(
                                projectName: projectName,
                                regions: regions,
                                environment: oguryEnv,
                                clusters: clusters
                            )
                        }
                    }
                }

                stage('Deploying Helm') {
                    steps {
                        script {
                            for(r in regions) {
                                def region = r
                                if (oguryEnv == 'prod' || region == "eu-west-1") {
                                    stage("${region}") {
                                        def parallelDeployStages = [:]
                                        for(c in clusters) {
                                            def cluster = c
                                            def clusterFullName = cluster + "-" + region + "." + oguryEnv + ".cloud.ogury.io"
                                            if ( clusterFullName in globalVars.getKubeClusters() ) {
                                                parallelDeployStages["internal-${cluster}"] = {
                                                    helmUtils.install(
                                                        name: "${projectName}-int",
                                                        namespace: projectName,
                                                        dockerName: projectName,
                                                        regions: [region],
                                                        environment: oguryEnv,
                                                        clusters: [cluster],
                                                        dockerTag: dockerTag,
                                                        secretNames: secretNames,
                                                        chartName: "ogury-ws",
                                                        chartVersion: helmChartVersion,
                                                        chartValueFiles: ["choices-internal.yaml"],
                                                        chartGlobalValueFile: ".kubernetes/config/global.yaml"
                                                    )
                                                }
                                                parallelDeployStages["external-${cluster}"] = {
                                                    helmUtils.install(
                                                        name: "${projectName}-ext",
                                                        namespace: projectName,
                                                        dockerName: projectName,
                                                        regions: [region],
                                                        environment: oguryEnv,
                                                        clusters: [cluster],
                                                        dockerTag: dockerTag,
                                                        secretNames: secretNames,
                                                        chartName: "ogury-ws",
                                                        chartVersion: helmChartVersion,
                                                        chartValueFiles: ["choices-external.yaml"],
                                                        chartGlobalValueFile: ".kubernetes/config/global.yaml"
                                                    )
                                                }
                                            }
                                        }
                                        parallel parallelDeployStages
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
    }
}
