stages:
  - auto-tagging
  - validate
  - scan
  - build
  - deploy
  - update
  
variables:
  MYSQL_CONNECTION: "mysql -h $MYSQL_HOST -u $MYSQL_USER -p$MYSQL_PASS "
  STATUS_SCRIPT: /home/gitlab-runner/monitor/deployment-status.sh
  HELM_CHART: /home/gitlab-runner/kubernetes/ilens/$QA_ENV/ilens-modules
  VARIABLES_YML: variables.yml
  DEPLOYMENT_YML: $CI_PROJECT_NAME.yml
  TIMEOUT: 960s

before_script:
  - val=`echo $($MYSQL_CONNECTION -e "SELECT COUNT(*) FROM $VERSION_DB.$DB_TABLE WHERE category='Server' AND type='Service' AND os='docker' AND module_name='$CI_PROJECT_NAME' ") | cut -d " " -f2`
  - if [ $val == 0 ]; then $MYSQL_CONNECTION -e "INSERT INTO $VERSION_DB.$DB_TABLE values('Server','Service','$CI_PROJECT_NAME','docker', '2', '0', '0', '0')";fi
  - QA=$($MYSQL_CONNECTION -N -e "SELECT qa FROM $VERSION_DB.$DB_TABLE where module_name = '$CI_PROJECT_NAME' AND type = 'Service' AND category = 'Server' AND os = 'docker'")
  - DEV=$($MYSQL_CONNECTION -N -e "SELECT dev FROM $VERSION_DB.$DB_TABLE where module_name = '$CI_PROJECT_NAME' AND type = 'Service' AND category = 'Server' AND os = 'docker'")
  - UAT=$(mysql -h $MYSQL_HOST -u $MYSQL_USER -p$MYSQL_PASS -N -e "SELECT uat FROM $VERSION_DB.$DB_TABLE where module_name = '$CI_PROJECT_NAME' AND type = 'Service' AND category = 'Server' AND os = 'docker'")
  - PROD=$($MYSQL_CONNECTION -N -e "SELECT prod FROM $VERSION_DB.$DB_TABLE where module_name = '$CI_PROJECT_NAME' AND type = 'Service' AND category = 'Server' AND os = 'docker'")

auto-tagging:
  stage: auto-tagging
  before_script:
    - val=`echo $($MYSQL_CONNECTION -e "SELECT COUNT(*) FROM $VERSION_DB.$VERSION_RELEASE_TABLE WHERE  module_name='$CI_PROJECT_NAME' ") | cut -d " " -f2`
    - if [ $val == 0 ]; then $MYSQL_CONNECTION -N -e "INSERT INTO $VERSION_DB.$VERSION_RELEASE_TABLE values('$CI_PROJECT_NAME', 'iLens', '6', '3', '0', '0')";fi
    - ILENS=$($MYSQL_CONNECTION -N -e "SELECT ilens_version FROM "$VERSION_DB.$VERSION_RELEASE_TABLE" where module_name = '$CI_PROJECT_NAME'")
    - RELEASE=$($MYSQL_CONNECTION -N -e "SELECT release_version FROM "$VERSION_DB.$VERSION_RELEASE_TABLE" where module_name = '$CI_PROJECT_NAME'")
    - FEATURE=$($MYSQL_CONNECTION -N -e "SELECT feature_version FROM "$VERSION_DB.$VERSION_RELEASE_TABLE" where module_name = '$CI_PROJECT_NAME'")
    - PATCH=$($MYSQL_CONNECTION -N -e "SELECT patch_version FROM "$VERSION_DB.$VERSION_RELEASE_TABLE" where module_name = '$CI_PROJECT_NAME'")

  script:
    - SOURCE_BRANCH=$(echo $CI_COMMIT_TITLE | cut -f 3 -d " " | cut -f 1 -d "/" | cut -f 2 -d "'")
    - >
        if [ "$SOURCE_BRANCH" = "QA" ]; then
          ((RELEASE=RELEASE+1)) && FEATURE=0 && PATCH=0;
          TAG_NAME=v$ILENS.$RELEASE.$FEATURE
          IMAGE_URL=azrilensprod.azurecr.io/ilens/release/versions/v"$ILENS.$RELEASE:$CI_PROJECT_NAME-$TAG_NAME"
          PROD=$RELEASE; QA=0; DEV=0;
          $MYSQL_CONNECTION -e "UPDATE $VERSION_DB.$DB_TABLE SET prod='$PROD' ,qa='$QA', dev='$DEV' WHERE module_name='$CI_PROJECT_NAME' AND type='Service' AND category='Server' AND os='docker'"         
        elif [ $SOURCE_BRANCH == "feature" ]; then
          ((FEATURE=FEATURE+1)) && PATCH=0;
          TAG_NAME=v$ILENS.$RELEASE.$FEATURE
          IMAGE_URL=azrilensprod.azurecr.io/ilens/release/versions/v"$ILENS.$RELEASE:$CI_PROJECT_NAME-$TAG_NAME"
        elif [ $SOURCE_BRANCH == "patch" ]; then
          ((PATCH=PATCH+1));
          TAG_NAME=v$ILENS.$RELEASE.$FEATURE.$PATCH
          IMAGE_URL=azrilensprod.azurecr.io/ilens/release/versions/v"$ILENS.$RELEASE:$CI_PROJECT_NAME-$TAG_NAME"
        else
          exit 1
        fi
        
    - echo -e "\n\nImage:" $IMAGE_URL >> ReleaseNote.txt
    - sed -i "1s|^|Version":" $TAG_NAME\n|" ReleaseNote.txt
    - sed -i "1s|^|Module Name":" $CI_PROJECT_NAME\n|" ReleaseNote.txt
    - docker build -t $IMAGE_URL .
    - docker push $IMAGE_URL
    - docker rmi --force $IMAGE_URL
    - URL=$(echo $CI_PROJECT_URL | sed 's|https://||')
    - git remote set-url origin https://$GIT_USRNAME:$GIT_USRPASSWD@$URL
    - git config user.email "devopsilens@gmail.com"
    - git config user.name "$GIT_USRNAME"    
    - git tag -a $TAG_NAME -F ReleaseNote.txt
    - git push origin $TAG_NAME
    - $MYSQL_CONNECTION -e "UPDATE $VERSION_DB.$VERSION_RELEASE_TABLE SET release_version='$RELEASE', feature_version='$FEATURE', patch_version='$PATCH'  WHERE module_name = '$CI_PROJECT_NAME' "
    - $MYSQL_CONNECTION -e "INSERT INTO $HISTORY_DB.$VERSION_RELEASE_TABLE values('$CI_JOB_ID', '$CI_PROJECT_NAME','iLens', '$ILENS.$RELEASE.$FEATURE', '$CI_COMMIT_SHA', '$GITLAB_USER_NAME', '$CI_COMMIT_REF_NAME')"
  tags:
    - shell
  only:
    - master

#~~~~~| Requirements.txt version check |~~~~~#
package-version-check:
  stage: validate
  script:
    - REQUIREMENTS=$(cat requirements.txt)
    - FAILED=0
    - >
        for REQ in ${REQUIREMENTS[@]};
        do
            PKG=$(echo $REQ | tr = " " | awk '{print $1}')
            VER=$(echo $REQ | tr = " " | awk '{print $2}')
            VER=${VER//[^[:alnum:]]/}
            if [ ! -z "${VER//[0-9]}" ] || [ -z $VER ]; then
                echo " Package version not specified for: $PKG "
                FAILED=`expr $FAILED + 1`
            fi
        done

    - if [ $FAILED -gt 0 ]; then exit 1; fi

  only:
  - QA
  tags: 
  - shell

#~~~~~| QA K8 |~~~~~#
qa-k8-deployment:
  stage: deploy
  script:
    - REGISTRY_URL=azacrknowledgelens.azurecr.io/knowledgelens/products/ilens/qa
    - export KUBECONFIG=/home/gitlab-runner/.kube/$QA_ENV
    - NAMESPACE=ilens-core
    - QA=`expr $QA + 1` && DEV=0
    - docker build -t $REGISTRY_URL/$CI_PROJECT_NAME:v$PROD.$QA.$DEV .
    - docker push $REGISTRY_URL/$CI_PROJECT_NAME:v$PROD.$QA.$DEV
    - echo "Deploying $CI_PROJECT_NAME"
    - >
        for YML in ${DEPLOYMENT_YML[@]};
        do
            FILE_PATH=$HELM_CHART/$YML
            SERVICE=$(echo $YML | cut -f 1 -d "." )
            CURR_VERSION=$(cat $FILE_PATH | grep "imageName:" )
            CURR_VERSION=$(echo $CURR_VERSION | cut -f 3 -d ":")
            echo " Deploying $SERVICE"
            echo " $SERVICE Version: $CURR_VERSION"
            sed -E -i'' "s|(.*imageName:.*"$REGISTRY_URL"/).*|\1"$CI_PROJECT_NAME":v"$PROD.$QA.$DEV"|" $FILE_PATH
            helm upgrade --install $SERVICE $HELM_CHART -f $FILE_PATH -f $VARIABLES_YML -n $NAMESPACE --history-max 1
            if ! sh $STATUS_SCRIPT $SERVICE $NAMESPACE $TIMEOUT ; then
              sed -E -i'' "s|(.*imageName:.*"$REGISTRY_URL"/).*|\1"$CI_PROJECT_NAME":"$CURR_VERSION"|" $FILE_PATH
              helm upgrade --install $SERVICE $HELM_CHART -f $FILE_PATH -f $VARIABLES_YML -n $NAMESPACE --history-max 1
              echo " $SERVICE Reverted to the previous version..."
              exit 1
            fi
            UI_POD=$(kubectl get pods -n $NAMESPACE | grep ilens-ui | awk '{print $1}')
            kubectl delete pod $UI_POD -n $NAMESPACE
        done
   
  only:
  - QA
  tags:
  - shell

#~~~~~| Vulnerability Scanner |~~~~~#
vulnerability-scanner:
  stage: scan
  script:
     - QA=`expr $QA + 1` && DEV=0
     - DOCKER_IMAGE=$CI_PROJECT_NAME:vulnarable-scan 
     - docker build -t $DOCKER_IMAGE --no-cache .
     - trivy image --format template --template "@/home/gitlab-runner/image-scanner/templates/html.tpl" -o imageScanner-$CI_PROJECT_NAME.html $DOCKER_IMAGE
     - trivy image --format json -o imageScanner-$CI_PROJECT_NAME.json $DOCKER_IMAGE
     - docker rmi --force $DOCKER_IMAGE
     - mv imageScanner-$CI_PROJECT_NAME.html /data0/email-util/module/reports/
     - >
        if ! /home/gitlab-runner/image-scanner/severity_check imageScanner-$CI_PROJECT_NAME.json ; then
          cd /home/gitlab-runner/image-scanner/
          ./mail imageScanner-$CI_PROJECT_NAME.html $DOCKER_IMAGE
        fi
    
     
  only:
  - QA
  tags: 
  - shell



tag-update-qa:
  stage: update
  script:
     - QA=`expr $QA + 1` && DEV=0
     - REGISTRY_URL=azacrknowledgelens.azurecr.io/knowledgelens/products/ilens/qa
     - docker rmi --force $REGISTRY_URL/$CI_PROJECT_NAME:v$PROD.$QA.$DEV
     - $MYSQL_CONNECTION -e "INSERT INTO $HISTORY_DB.$DB_TABLE values('$CI_JOB_ID','Server','Service', '$CI_PROJECT_NAME','docker', '$PROD.$QA.$DEV', '$CI_COMMIT_SHA', '$GITLAB_USER_NAME', '$CI_COMMIT_REF_NAME')"
     - $MYSQL_CONNECTION -e "UPDATE $VERSION_DB.$DB_TABLE SET prod='$PROD' ,qa='$QA', dev='$DEV' WHERE module_name = '$CI_PROJECT_NAME' AND type = 'Service' AND category = 'Server' AND os = 'docker'"
  dependencies:
    - qa-k8-deployment
  only:
  - QA
  tags: 
  - shell


#~~~~~| DEV 220 |~~~~~#
dev-deployment-220:
  stage: deploy
  script:
    - tar czvf $CI_PROJECT_NAME.tar.gz *
    - echo "Deploying to the dev 220 server..."
    - sshpass -p $OFC_PASSWD ssh $OFC_USERNAME@$OFC_HOSTNAME "mkdir -p /tmp/$CI_PROJECT_NAME/tar/"
    - sshpass -p $OFC_PASSWD ssh $OFC_USERNAME@$OFC_HOSTNAME "mkdir -p /tmp/$CI_PROJECT_NAME/untar/"
    - sshpass -p $OFC_PASSWD scp $CI_PROJECT_NAME.tar.gz $OFC_USERNAME@$OFC_HOSTNAME:/tmp/$CI_PROJECT_NAME/tar/ 
    - sshpass -p $OFC_PASSWD ssh $OFC_USERNAME@$OFC_HOSTNAME "tar xzvf /tmp/$CI_PROJECT_NAME/tar/$CI_PROJECT_NAME.tar.gz -C /tmp/$CI_PROJECT_NAME/untar/"
    - sshpass -p $OFC_PASSWD ssh $OFC_USERNAME@$OFC_HOSTNAME "rsync -r /tmp/$CI_PROJECT_NAME/untar/* /opt/services/ilens2.0/$CI_PROJECT_NAME/"
    - sshpass -p $OFC_PASSWD ssh $OFC_USERNAME@$OFC_HOSTNAME "/home/svc-ilens/.miniconda3/envs/ilens37/bin/pip install -r /opt/services/ilens2.0/$CI_PROJECT_NAME/requirements.txt"    
    - sshpass -p $OFC_PASSWD ssh $OFC_USERNAME@$OFC_HOSTNAME "sudo systemctl restart ilens_2.0_dev_$CI_PROJECT_NAME.service"
    - sshpass -p $OFC_PASSWD ssh $OFC_USERNAME@$OFC_HOSTNAME "sudo systemctl status ilens_2.0_dev_$CI_PROJECT_NAME.service"
 
  after_script:
    - sshpass -p $OFC_PASSWD ssh $OFC_USERNAME@$OFC_HOSTNAME "rm -rf /tmp/$CI_PROJECT_NAME"
    - rm -f $CI_PROJECT_NAME.tar.gz
  only:
  - develop
  tags:
  - shell


#~~~~~| CODE QUALITY |~~~~~#
codequality:
  stage: deploy
  image: azacrknowledgelens.azurecr.io/knowledgelens/klit-operation/devops/gitlab-runner:ubuntu-sonarscanner
  script:
     - /opt/sonar-scanner/bin/sonar-scanner -Dsonar.projectKey=$CI_PROJECT_NAME -Dsonar.projectName=$CI_PROJECT_NAME -Dsonar.typescript.node=./node/node -Dsonar.login=admin -Dsonar.password=admin -Dsonar.sources=.
     - sleep 5
     - python3 /opt/code_quality_report/static_code_quality_report_csv_v2.py $CI_PROJECT_NAME $GITLAB_USER_EMAIL,$EMAIL_TO $EMAIL_FROM $EMAIL_PASSWD False admin admin
  only:
     - develop
  tags:
     - docker
