version: 2.1
orbs:
  k8s: circleci/kubernetes@0.7.0
  s3: circleci/aws-s3@1.0.13
commands:
  git_checkout_from_cache:
    description: "Git checkout and save cache"
    steps:
      - restore_cache:
          name: Git restore cache
          keys:
            - source-v1-{{ .Branch }}-{{ .Revision }}
            - source-v1-{{ .Branch }}-
            - source-v1-
      - run: 
          name: Fetch git tags 
          command: |
            mkdir -p ~/.ssh
            echo 'github.com ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEAq2A7hRGmdnm9tUDbO9IDSwBK6TbQa+PXYPCPy6rbTrTtw7PHkccKrpp0yVhp5HdEIcKr6pLlVDBfOLX9QUsyCOV0wzfjIJNlGEYsdlLJizHhbn2mUjvSAHQqZETYP81eFzLQNnPHt4EVVUh7VfDESU84KezmD5QlWpXLmvU31/yMf+Se8xhHTvKSCZIFImWwoG6mbUoWf9nzpIoaSjB+weqqUUmpaaasXVal72J+UX2B+2RPW3RcT0eOzQgqlJL3RKrTJvdsjE3JEAvGq3lGHSZXy28G3skua2SmVi/w4yCE6gbODqnTWlg7+wC604ydGXA8VJiS5ap43JXiUFFAaQ== ' >> ~/.ssh/known_hosts
            # Fetch tags if git cache is present
            if [ -e /home/circleci/project/.git ]
            then
              git fetch origin --tags
            fi
      - checkout
      - run:
          name: Compress git objects 
          command: git gc
      - save_cache:
          name: Git save cache
          key: source-v1-{{ .Branch }}-{{ .Revision }}
          paths:
            - ".git"
  npm_install:
    description: "Install npm modules"
    steps:
      - restore_cache:
          name: Restore npm cache
          keys:
            - npm-v1-{{ checksum "package.json" }}
            - npm-v1-
      - run:
          name: Install npm modules
          command: yarn
      - save_cache:
          name: Save NPM cache
          key: npm-v1-{{ checksum "package.json" }}
          paths:
            - "node_modules"

  build:
    description: "Build"
    steps:
      - run:
          name: "yarn build"
          command: yarn build
  
  compress:
    description: "Compress"
    steps:
      - run:
          name: "Compress"
          command: |
            pushd lib/
            tar -cvf artifact.tar *
            mv artifact.tar ${OLDPWD}/
      - run:
          name: "Tag commit id as artifact identifer"
          command: echo "${CIRCLE_SHA1}" > artifact-info.txt

  upload_artifact:
    description: "upload build artifact to s3 bucket"
    steps:
      - s3/copy:
          from: artifact.tar
          to: 's3://${CONTEXT_ARTIFACT_S3_BUCKET}/${CIRCLE_PROJECT_REPONAME}/'
          aws-access-key-id: env_CONTEXT_ARTIFACT_S3_AWS_ACCESS_KEY_ID
          aws-secret-access-key: env_CONTEXT_ARTIFACT_S3_AWS_SECRET_ACCESS_KEY
          aws-region: env_CONTEXT_ARTIFACT_S3_AWS_REGION
          arguments: '--metadata "{\"x-amz-artifact-id\": \"${CIRCLE_SHA1}\" }"'

  upload_checksum:
    description: "upload artifact checksum to s3"
    steps:
      - s3/copy:
          from: artifact-info.txt
          to: 's3://${CONTEXT_ARTIFACT_S3_BUCKET}/${CIRCLE_PROJECT_REPONAME}/'
          aws-access-key-id: env_CONTEXT_ARTIFACT_S3_AWS_ACCESS_KEY_ID
          aws-secret-access-key: env_CONTEXT_ARTIFACT_S3_AWS_SECRET_ACCESS_KEY
          aws-region: env_CONTEXT_ARTIFACT_S3_AWS_REGION 
  docker:
    description: "Build and Push image to docker hub"
    steps:
      - setup_remote_docker
      - run: 
          name: Building docker image
          command: |
            docker build -t ${DOCKHUB_ORGANISATION}/binary-static-liveapi:${CIRCLE_SHA1} -t ${DOCKHUB_ORGANISATION}/binary-static-liveapi:latest .
      - run: 
          name: Pushing Image to docker hub
          command: |
            echo $DOCKERHUB_PASSWORD | docker login -u $DOCKERHUB_USERNAME --password-stdin
            docker push ${DOCKHUB_ORGANISATION}/binary-static-liveapi:${CIRCLE_SHA1}
            docker push ${DOCKHUB_ORGANISATION}/binary-static-liveapi:latest

  k8s_deploy:
    description: "Deploy to k8s cluster"
    steps:
      - k8s/install-kubectl
      - run: 
          name: Deploying to k8s cluster for service binary-liveapi
          command: |
            for SERVER_ID in {1..5}
            do
              KUBE_SERVER_REF="KUBE_SERVER_$SERVER_ID"
              SERVICEACCOUNT_TOKEN_REF="SERVICEACCOUNT_TOKEN_$SERVER_ID"
              CA_CRT_REF="CA_CRT_$SERVER_ID"
              if [ ! -z "${!KUBE_SERVER_REF}" ]
              then
                echo "Deploying to cluster $SERVER_ID"
                CA_CRT="${!CA_CRT_REF}"
                KUBE_SERVER="${!KUBE_SERVER_REF}"
                SERVICEACCOUNT_TOKEN="${!SERVICEACCOUNT_TOKEN_REF}"
                echo $CA_CRT | base64 --decode > ca.crt
                kubectl --server=${KUBE_SERVER} --certificate-authority=ca.crt --token=$SERVICEACCOUNT_TOKEN set image deployment/liveapi-binary-com liveapi-binary-com=${DOCKHUB_ORGANISATION}/binary-static-liveapi:${CIRCLE_SHA1}
              fi
            done

jobs:
  release:
    docker:
      - image: circleci/node:9.9.0-stretch
    steps:
      - git_checkout_from_cache
      - npm_install
      - build
      - compress
      - upload_artifact  # uploading the built code to s3 to create a backup of key services separate from Kubernetes deployment
      - upload_checksum  # uploading compressed artifact checksum to cross match artifact fingerprint
      - docker
      - k8s_deploy
      
workflows:
  release:
    jobs:
      - release:
          filters:
            branches:
              only: /^master$/
          context: binary-frontend-artifact-upload  # using context to retrieve shared secret from circle ci
