📜 ⬆️ ⬇️

CD setup via gitlab

I once thought about automating the deployment of my project. gitlab.com kindly provides all the tools for this, and of course I decided to use it by sorting out and writing a small deployment script. In the article, I share my experience with the community.

TL; DR


  1. Configure VPS: disable root, log in with password, install dockerd, configure ufw
  2. Generate certificates for server and client / from the docker config.
  3. Register paths to certificates in docker.json
  4. Register in gitlab variables in the CI / CD settings with the contents of the certificates. Write a script .gitlab-ci.yml for deployment.

All examples will be shown on the Debian distribution.

Initial VPS Setup


Here you bought an instance, for example, at DO , the first thing to do is to protect your server from the aggressive outside world. I will not prove and argue anything, just show the virtual server’s var / log / messages log:

Screenshot
image

First, install the ufw firewall:
')
apt-get update && apt-get install ufw 

Enable the default policy: block all incoming connections, allow all outgoing connections:

 ufw default deny incoming ufw default allow outgoing 

Important: do not forget to allow ssh connection:

 ufw allow OpenSSH 

The general syntax is: Allow connection by port: ufw allow 12345, where 12345 is the port number or the name of the service. Prohibit: ufw deny 12345

Turn on the firewall:

 ufw enable 

We leave the session and log in again using ssh.

Add a user, assign a password to it and add it to the sudo group.

 apt-get install sudo adduser scoty usermod -aG sudo scoty 

Further, according to the plan, you should disable the input by password. To do this, copy your ssh-key to the server:

 ssh-copy-id root@10.101.10.28 

ip server must be yours. Try to log in now under the user created earlier, you no longer need to enter the password. Further in the configuration settings we change the following:

 sudo nano /etc/ssh/sshd_config 

disable login by password:

 PasswordAuthentication no 

Restart sshd daemon:

 sudo systemctl reload sshd 

Now if you or someone else tries to log in with the root user, he will fail.

Next, we put dockerd, I’m not going to describe the process here, since everything can already be changed, go to the official website link and go through the docker installation steps on your virtual machine: https://docs.docker.com/install/linux/docker- ce / debian /

Certificate Generation


To control the docker daemon remotely, an encrypted TLS connection is required. To do this, you must have a certificate and a key that must be generated and transferred to your remote machine. Follow the steps given in the instructions on the official docker website: https://docs.docker.com/engine/security/https/#create-a-ca-server-and-client-keys-with-openssl All generated * .pem files for the server, namely ca.pem, server.pem, key.pem must be placed in the / etc / docker directory on the server.

Dockerd setup


In the docker daemon startup script, we remove the -H df: // option, this option answers on which host you can control the docker daemon.

 # At /lib/systemd/system/docker.service [Service] Type=notify ExecStart=/usr/bin/dockerd 

Next, create a configuration file, if it is not already there, and set options:

/etc/docker/daemon.json
 { "hosts": [ "unix:///var/run/docker.sock", "tcp://0.0.0.0:2376" ], "labels": [ "is-our-remote-engine=true" ], "tls": true, "tlscacert": "/etc/docker/ca.pem", "tlscert": "/etc/docker/server.pem", "tlskey": "/etc/docker/key.pem", "tlsverify": true } 


Allow connections on port 2376:

 sudo ufw allow 2376 

Restart dockerd with new settings:

 sudo systemctl daemon-reload && sudo systemctl restart docker 

Check:

 sudo systemctl status docker 

If everything is “green”, then we believe that we have successfully configured docker on the server.

Setting up continuous deleivery on gitlab


In order for the worker of the gitalab to execute commands on the remote docker's host, it is necessary to decide how and where to store the certificates and the key for the encrypted connection with dockerd. I solved this problem simply by writing to variables in the gitlbab settings:

Spoiler header
image

Simply output the contents of the certificates and key via cat: cat ca.pem . Copy and paste into the value of variables.

Let's write the script for deployment through gitlab. Will use a docker-in-docker (dind) image.

.gitlab-ci.yml
 image: name: docker/compose:1.23.2 #  entrypoint ,    dind entrypoint: ["/bin/sh", "-c"] variables: DOCKER_HOST: tcp://docker:2375/ DOCKER_DRIVER: overlay2 services: - docker:dind stages: - deploy deploy: stage: deploy script: - bin/deploy.sh #    


The contents of the deployment script with comments:

bin / deploy.sh
 #!/usr/bin/env sh #  ,   -  set -e # ,  ,   set -v # DOCKER_COMPOSE_FILE=docker-compose.yml #   DEPLOY_HOST=185.241.52.28 #    ,      - gitlab- DOCKER_CERT_PATH=/root/.docker # ,      docker info docker-compose version #   (    -  gitlab') mkdir $DOCKER_CERT_PATH #   ,         . echo "$CA_PEM" | tr -d '\r' > $DOCKER_CERT_PATH/ca.pem echo "$CERT_PEM" | tr -d '\r' > $DOCKER_CERT_PATH/cert.pem echo "$KEY_PEM" | tr -d '\r' > $DOCKER_CERT_PATH/key.pem #       chmod 400 $DOCKER_CERT_PATH/ca.pem chmod 400 $DOCKER_CERT_PATH/cert.pem chmod 400 $DOCKER_CERT_PATH/key.pem #       docker-. ,   export DOCKER_TLS_VERIFY=1 export DOCKER_HOST=tcp://$DEPLOY_HOST:2376 # ,     docker-compose \ -f $DOCKER_COMPOSE_FILE \ ps #   docker-,     ""  docker login -u $DOCKER_USER -p $DOCKER_PASSWORD docker-compose \ -f $DOCKER_COMPOSE_FILE \ pull app #   docker-compose \ -f $DOCKER_COMPOSE_FILE \ up -d app 


The main problem was to “pull out” the contents of certificates in normal form from the gitlab CI / CD variables. I could not understand why the connection to the remote host did not work. On the host, I looked at sudo journalctl -u docker, there was an error in the handshake. I decided to look at what is generally stored in variables, for this you can look at cat -A $ DOCKER_CERT_PATH / key.pem. Overcame the error by adding a carriage character tr -d '\ r' deletion.

Further, in the script, you can add post-release task at your discretion. You can view the working version in my repository https://gitlab.com/isqad/gitlab-ci-cd

Source: https://habr.com/ru/post/449952/


All Articles