On Developing Kubernetes Locally

Kubernetes has been a large force in the app deployment industry for some time now, and this article is by no means the authority on Kubernetes. I’ve personally have had some stop and go with adoption, and knowing a technology “enough” can lead to bad practices. This article will walk you through the basic logistics of developing for K8s on your machine without “experimenting in production.” The goal of this article is to note commands for new k8s developers and to demonstrate validating k8s manifests locally in order to cut down development time.

We’ll create a Kubernetes Cluster locally on our machines which will let us test our code more quickly, and give us a space to experiment and make bad decisions.

Creating a Local Kubernetes Cluster

We’ll use minikube to develop on Macintosh. MicroK8s may be a good option for linux. In both cases we’ll need to have docker installed as well.

If you’ve installed everything correctly you can run:

minikube start

Perhaps you’ll note your laptop’s fan trying to take off while you’re regaled with emojis. Hopefully we’ll see the following surfer:

🏄  Done! kubectl is now configured to use "minikube" cluster and "default" namespace by default

This is important to note. kubectl is the command we’ll be doing work with, and they were thoughtful enough to reconfigure our environment to point to the minikube cluster to get started. You may eventually have many clusters you’ll want to connect to (~/.kube/config is a good place to save them) and you can point kubectl to different clusters using environment variables.

Connecting to minikube

You have your own kubernetes cluster! You’re free to use this as you will. kubectl cluster-info is a good sanity check.
You’ll probably use the following commands useful for running kubernetes manifests you’re working on.

# deploy your deployment/service/pod...
kubectl apply -f path/[file.yml]

# undo
kubectl delete -f path/[file.yml]

# or if you've made a mess, and just want to kill stuff.
kubectl delete [pod|deployment] name-to-delete

# process list
kubectl get [pods|deployment]

If you want to check the syntax of manifest files you’ve written, consider the following. Checking your syntax on a local cluster without bumping into all your coworkers is already a big win. You’ll have reliable quick results without having to a server.

# this checks the `manifests` folder
kubectl apply -f manifests --dry-run

docker images in minikube

You’re eventually going to want to use a docker image you have built. Unfortunately minikube is running in it’s own container and your local machine’s images won’t be available there. It will probably make sense to share a docker registry between the two hosts, but a quick solution is to just build the docker images where you want them (in minikube.) Your code and local files should all show up in the minikube container.

You can change your shell’s environment to point to the minikube docker:

eval $(minikube docker-env)

docker build . -t your-tag-name # this will now build to your minikube repo

NOTE: You can always ssh into the minikube instance with minikube ssh if you want to tinker.

image pull problems

If you’re having problems with pulling docker images and you already have them locally, you can use the imagePullPolicy configuration as IfNotPresent or Never.

Otherwise updating .docker/config.json with your private registry may help.

connecting to your services

minikube is going to require an extra step to provide service access to your host machine. AKA: If you want to connect to your web service from your browser, you’ll have to do this.
If you have set up a k8s service, you can run minikube service {service-name} and a tunneling process will start up (and maybe open your browser!)

If you are using LoadBalancer, minikube tunnel may work better for you.


As technologists, we always need to be sharpening our tools. Hopefully the steps above have helped you improve your development environment and sped up your kubernetes development process.