In [Part 1] and [Part 2] we built a functional API using Golang and MongoDB, although as it stands its insecure. We can add password protection using Basic Auth while deploying ([See here]). In this tutorial we will build a very tiny docker container and deploy to our Kubernetes Cluster.
For the purposes of this tutorial I won’t be showing you how to setup a Kubernetes Cluster, However you can do it easily with [Terraform] and [DigitalOcean].
- You have a functional Kubernetes Cluster
- GKE – Google Kubernetes Engine
- AKE – Azure Kubernetes Engine
- EKS – Elastic Kubernetes Engine (AWS)
- Rolled your own
- You have a working [nginx ingress] controller
- You have a working loadbalancer for your cluster
- You have Docker running on your machine
- You have a dockerhub account
Accepting Environment Variables
As we will be deploying this to a cluster with an external MongoDB instance we need to accept an environment variable for MongoDB.
in our main.go file replace
var session, _ = mgo.Dial("127.0.0.1")
Remember to add the os import
Building our Container
Compiling the Binary
As I mentioned we will be building a very minimal docker container for our API. This is acomplished by building our go binary using CGO and GOOS environment variables. This will build a statically linked binary for the GOOS we choose, For this scenario it will be Linux.
So in our project directory lets build our binary. To make it easier and repeatable I have created a Makefile
now run make and you will have an ELF binary in bin/todo-api
You can run this however it will fail to connect unless you specify a valid MongoDB host using the MONGO_HOST environment variable.
Building the Container
In order to make our container as small as possible we will be using the scratch base image from Docker. This image literally has nothing in it, This will allow us to add our binary and nothing else. So lets write our Dockerfile
Now we have the Dockerfile we can run
$ docker build -t affixxx/todo-api:latest .
remember to tag it with your own dockerhub username!
And thats it we now have a super small Docker container mine is 7.52MB
You can run it but remember to specify the MONGO_HOST environment variable.
Lets push to dockerhub
$ docker push affixxx/todo-api
And thats all there is to it. We can now look at deploying our application. Feel free to [deploy mine]
Deploying to Kubernetes
Before we start I recommend we create a namespace for our project.
Having our project in a seperate namespace ensures that we won’t affect anything else on our kubernetes cluster.
Our MongoDB deployment has 2 parts, A Service and a Deployment. Setting up Persistent Volumes is beyond scope and I will write a tutorial in the future on working with PVs in kubernetes.