Everyone loves security, yeah?!
Up until recently, it's cost a fair whack of money to use SSL certificates on your website. This has been a barrier for a lot of smaller website, which subsequently leaves them vulnerable to common attacks such as man in the middle .
Then comes letsencrypt , a free, crowdfunded way to get valid https certificates, like the one used on this website! In order to keep costs down (you know, as its free) they rely a lot on automated scripts and domain validation, which can be a little fiddly. I also have to do this for lots, and lots of microservices and websites that I host - so I wanted to encapsulate all of these concerns into a simple container which was generic, and did it all for me.
docker-nginx-letsencryptI created this docker container which is an NGINX reverse proxy, which will front your microservice with a valid HTTPS certificate without you having to do much at all!
Lets take this website, karlstoney.com as an example. The blog is actually a ghost nodejs application, which serves up http on port karlstoney.www.svc.cluster.local:2368 . However, I want to expose that to the world on karlstoney.com. I could use the following docker-compose file to do just that:
version: '2' services: nginx: image: stono/docker-nginx-letsencrypt restart: always volumes: - ./certs:/etc/letsencrypt/live environment: - HOST_WEBSITE1=karlstoney.com,karlstoney.www.svc.cluster.local:2368,default_server ports: - 443 - 80That's it, watch what happens when the container boots on my server:
Generating self signed certificate for karlstoney.com Generating a 4096 bit RSA private key ................................................++ .............++ writing new private key to 'key.pem' ----- Writing nginx config for karlstoney.com with an upstream of karlstoney.www.svc.cluster.local:2368 server { listen 80; server_name karlstoney.com; location ~ /.well-known { allow all; break; } location / { return 301 https://$host$request_uri; } } server { listen 443 default_server; server_name karlstoney.com; ssl on; ssl_certificate /etc/letsencrypt/live/karlstoney.com/fullchain.pem; ssl_certificate_key /etc/letsencrypt/live/karlstoney.com/key.pem; ssl_session_cache builtin:1000 shared:SSL:10m; ssl_protocols TLSv1 TLSv1.1 TLSv1.2; ssl_ciphers HIGH:!aNULL:!eNULL:!EXPORT:!CAMELLIA:!DES:!MD5:!PSK:!RC4; ssl_prefer_server_ciphers on; access_log /var/log/nginx/karlstoney.com.access.log; set $upstream_endpoint_host_karlstoney http://karlstoney.www.svc.cluster.local:2368; resolver 10.37.80.10; resolver_timeout 5s; location / { proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; proxy_set_header Host $host; proxy_pass $upstream_endpoint_host_karlstoney; proxy_redirect http://karlstoney.www.svc.cluster.local:2368 https://karlstoney.com; proxy_read_timeout 90; } } nginx: the configuration file /etc/nginx/nginx.conf syntax is ok nginx: configuration file /etc/nginx/nginx.conf test is successful Starting Nginx 2016/12/30 21:06:31 [notice] 26#0: using the "epoll" event method 2016/12/30 21:06:31 [notice] 26#0: nginx/1.11.5 2016/12/30 21:06:31 [notice] 26#0: built by gcc 4.8.5 20150623 (Red Hat 4.8.5-11) (GCC) 2016/12/30 21:06:31 [notice] 26#0: OS: linux 4.4.21+ 2016/12/30 21:06:31 [notice] 26#0: getrlimit(RLIMIT_NOFILE): 1048576:1048576 2016/12/30 21:06:31 [notice] 26#0: start worker processes 2016/12/30 21:06:31 [notice] 26#0: start worker process 28 Nginx started with pid 26 Running simp_le letsencrypt for karlstoney.com 2016-12-30 21:06:34,455:INFO:simp_le:1211: Generating new account key 10.37.64.1 - - [30/Dec/2016:21:06:36 +0000] "GET /.well-known/acme-challenge/h_rKjS1mbLjzs9d0bw6yDfk7M8RBr7_FVkPprVD_wkE HTTP/1.1" 200 87 "-" "python-requests/2.12.4" 2016/12/30 21:06:36 [info] 28#0: *1 client 10.37.64.1 closed keepalive connection 2016-12-30 21:06:36,648:INFO:simp_le:1305: karlstoney.com was successfully self-verified 2016-12-30 21:06:36,861:INFO:simp_le:1313: Generating new certificate private key 10.37.64.1 - - [30/Dec/2016:21:06:37 +0000] "GET /.well-known/acme-challenge/h_rKjS1mbLjzs9d0bw6yDfk7M8RBr7_FVkPprVD_wkE HTTP/1.1" 200 87 "-" "Mozilla/5.0 (compatible; Let's Encrypt validation server; +https://www.letsencrypt.org)" 2016-12-30 21:06:39,370:INFO:simp_le:391: Saving account_key.json 2016-12-30 21:06:39,371:INFO:simp_le:391: Saving fullchain.pem 2016-12-30 21:06:39,383:INFO:simp_le:391: Saving key.pem 2016/12/30 21:06:39 [notice] 26#0: signal 1 (SIGHUP) received, reconfiguring 2016/12/30 21:06:39 [notice] 26#0: reconfiguring 2016/12/30 21:06:39 [notice] 26#0: using the "epoll" event method 2016/12/30 21:06:39 [notice] 26#0: start worker processes 2016/12/30 21:06:39 [notice] 26#0: start worker process 40 2016/12/30 21:06:39 [notice] 28#0: gracefully shutting down 2016/12/30 21:06:39 [notice] 28#0: exiting 2016/12/30 21:06:39 [notice] 28#0: exit 2016/12/30 21:06:39 [notice] 26#0: signal 17 (SIGCHLD) received 2016/12/30 21:06:39 [notice] 26#0: worker process 28 exited with code 0 2016/12/30 21:06:39 [notice] 26#0: signal 29 (SIGIO) receivedYou can view the full repo here