A closer look at commands and args in Kubernetes Pods
In my previous blog post, we looked at how commands and args work in Docker. If you missed that one, the link is down below.
Today we will be looking at the same but in Kubernetes. To get started, we will be building on top of the following Dockerfile.
FROM debian
ENTRYPOINT ["printf", "Hello from %s\n"]
CMD ["Name Printer"]
This would simply print out Hello from Name Printer
when you run it.
As a time-saver, I have already packaged up the image. You can have look at the image layers in Docker Hub.
You could run this with Docker like so.
docker run sahan/name-printer:latest
That should give you Hello from Name Printer
as the output.
Now let’s do the same thing in Kubernetes. I’m a big fan of imperative commands in k8s. You can simple create resources without having to write definition files for simple things.
kubectl run test --image=sahan/name-printer:latest
💡 You can quickly delete the pod with
kubectl delete pod test --grace-period=0 --force
command.
Let’s export the pod definition to a file.
kubectl run test --image=sahan/name-printer:latest --dry-run=client -o yaml > pod.yml
In the pod definition file, we will add a new field called args
under spec.containers.args
like so:
apiVersion: v1
kind: Pod
metadata:
creationTimestamp: null
labels:
run: test
name: test
spec:
containers:
- image: sahan/name-printer:v1
name: test
args: ["Kubernetes"]
resources: {}
dnsPolicy: ClusterFirst
restartPolicy: Always
status: {}
Running and building this gives you Hello from Kubernetes
on the console
kubectl create -f pod.yml
This makes sense because we didn’t change/override the ENTRYPOINT
. Whatever we define as args
simply gets appended to that. So how can we change the ENTRYPOINT
’s behaviour?
We can use the command
attribute to define whichever command we want to run in it.
apiVersion: v1
kind: Pod
metadata:
creationTimestamp: null
labels:
run: test
name: test
spec:
containers:
- image: sahan/name-printer:latest
name: test
command: ["date"]
args: ["-u"]
resources: {}
dnsPolicy: ClusterFirst
restartPolicy: Always
status: {}
Now when we run the new pod definition it should print out the current date-time in UTC format. As you can see it’s easy to override the ENTRYPOINT
’s behaviour in the container.
One thing to take note of is, remember that we had bash
as CMD
set in our that why we didn’t have to pass in that. If you have a container that and you want to invoke a command, you can simply prepend /bin/bash -c
to the command you want to run.
Conclusion
That’s it for this one - hope it’s useful to understand how commands and args work in pods.