Start your Kubernetes journey with Learning Paths today!


No results found.

Choose language

Lesson 5 11:24

Packaging Your Application

In this lesson, you’ll learn how to use Helm to template your manifests and package your application for deployment.


Hi, and welcome to the fifth lesson in the KubeAcademy series, Building Apps for Kubernetes. I'm Eric Smalling, Staff Field Engineer at VMware.

So far in this course, we've gone over the basics of building and running your application in containers on a Kubernetes cluster. Now, we're going to take a look at a popular package manager for Kubernetes called HELM. HELM uses a templating syntax, as opposed to the overlays you saw used by the customized tool in the prior lesson. One note to touch on before we get started is where you can store the files HELM uses that you'll create for your application. These are called HELM charts. Most seem to prefer to keep all their various HELM charts in a common repo. But in this case, for simplicity, we're going to keep the HELM chart in the app code repo, which also works fine. I should also note that we're going to use the latest version of HELM here, version three, which has some substantial changes from prior version.

First of all, let's use the HELM tool to create a starting point for our chart, the command, HELM create, and we'll give it a name. We'll call it, build for Kube, to match this course. That'll create a simple directory structure for our chart. I'm going to use tree to take a look at that. And you can see from here, we have a chart YAML file that describes the chart. We'll take a look at that in a moment. We have some boilerplate templates that were created and a values YAML file that has some extracted configuration values. All of this is boilerplate sample stuff. We're going to clean it out. The first lesson, we don't need the values YAML, so I'm going to delete that. And I'm also going to clean out all these template files. We don't need that for this lesson either.

Okay. Let's take a look at the chart, that YAML file that got generated for us. As you can see, we've got some boilerplate fields, like the API version. We've got the name that we gave HELM to create the chart with. And we've got a description here that I'm going to go ahead and change to something a little more appropriate. We'll say KubeAcademy Demo. We've got a few other fields, including at the bottom, you'll see a couple of version fields. Ones for versioning the chart itself. And the other is for your application that's going to be deployed, what version it is. We'll leave those alone for now. Let us now go look into the templates folder. And I'm going to copy forward the deployment and service manifests that we've been working on throughout prior lessons.

Let's take a look at that deployments manifest and turn it into a template. Now, when we templatize for HELM, what we're really doing is we're adding or changing values into variables, so that they can be replaced by the HELM tool upon deployment. The first one is going to be the name of this deployment. Now, when you do an install in HELM, or a deployment of your application, there is a concept called a release name. This allows you to have multiple versions of your application running or different configurations of the application running, and they're differentiated by their release name. I want to add that to the Kubernetes deployment name. So that when I look at it with Kube CTL, or other tools, I can determine which release this is from. The way we're going to do that, is we'll add a variable right here. Release name. I need a dot at the front of that, excuse me.

And the curly braces for hyphen, and surround that in quotes. The next thing is to look for any variables we want to remove. Now, just like in software development, you don't want to have magic numbers, string literals throughout your code, because if you need to change them, you have to go all throughout the code and change it all over the place. We want to centralize those things. Such as, say, the replica count. Let's take that out and replace it. And I'm going to put a values, which we'll show you where that comes from in a moment. And I'm going to create a kind of schema here. And I'm just going to say, deploy, since this is the deployment, and replicates.

Now, if you go to the bottom of this, you'll also see we have this image, and I don't want to have the version of my image hard-coded. What I'm going to do is I'm going to refer back to the chart we saw, the chart YAML. And it has an app version in it. I'm going to refer to that and use that as my image version. Also, I don't like this hard coded docker hub accounts and repository name, because if we were to ever want to move this to a different registry, or rename it, or do anything like that, we've got to go find all of it, everywhere in the manifest we use it and change that. So I'm going to copy it first, and then I am going to change this to... Excuse me. There we go. Look back into the values, into that deploy schema. And then we're going to do image repository.

There we go. Let's go ahead and also change the service name, the same way we did the other. We put the release name on the front of it. I'll leave the rest of this alone for now. Now, where do these values come from? Let's go take a look at the top level. We need to add a new values YAML file. And remember, we removed one that was created at the beginning, when we did the HELM install. That had a bunch of boilerplate stuff in it we didn't need. All that we need here is the schema that I started to create in the deployment YAML. Let's say deploy replicas. And we had two. And we also had image. and under that we had repository, and there's that value. And we'll save that.

Finally, let's go ahead and... CD up out of the chart directory, and we're going to run HELM install. I'm going to say, generate name. This creates that release name I talked about. You could specify your own, but I'm just going to generate one. And I'm going to point it at my chart. I'm also going to use a dry run, which is very similar to the Kube CTL dry run. It's not going to actually send this to the cluster. It's just going to output the manifest that it would've created otherwise. There we go. Here at the top, we see the build name that was generated for me. And then that's prefixed to my service name and my deployment name. That's good. Replicas is populated correctly, as is the image. That looks good. Oops, 1160. I know that's not right. Let's go change our chart to have a real version. I know that this image has a .01.

I'm going to rerun the same dry run. There we go. That looks better. It's got the .01. Let's go ahead and deploy this to the cluster. To deploy this, we'll issue the same command, I'll just remove the dry run from it. And there it goes. It says it went, so let's do a Kube CTL gets all. See what we've got going on. And sure enough, there, we have our deployment with the prefixed HELM release name, as well as the pods and service, and everything looks good.

Let's say you've got a new version of the app. There's a .02 version now. We will change the chart to version .02. And we will do a HELM upgrade. We need to tell it the release name that we're upgrading. We're going to change, paste that in there, and where the chart is. I'm not going to do a dry run. I'm just going to run. It says it did it. Let's check on it. If you look at our pods, we see that it's rotating in some new pods. Let's do Kube CTL describe on our deployment, and see what exactly is in the pod spec.

Sure enough. We've got .02 in the deployment image. Now, what happens if, oh my gosh, we need to roll back. There's something wrong with that release. We want to go back to .01. There's a couple ways to do this. The simplest typing way to do this is probably to do a HELM rollback. And that... Oops, that's something. The release name. That will undo the last upgrade you just did. Just to check on it, let's do our get all. We see the pods rotating. That's good. There's some old ones terminating, at least. Let's do the same describe.

And we see we're back to the .1 release. Now, that works. It's perfectly fine, and will get you back to the prior release. But what we have going on now is our chart that would most likely be in version control, no longer matches what's deployed to the cluster. Another way to do this would be to come into the chart, change the release back... The app version back to .1, and then do another HELM upgrade. Which is kind of counterintuitive because you're not really upgrading, but you are, from the charts point of view, you are. This would be preferable, especially if you've got automation and you're using like a CD pipeline to do this. Because you would change it in Git, or whatever version control you use, and your CD tool would then upgrade to the prior version that way.

Now that you've learned how to use HELM to deploy your application, let's look at the package management function. It's very simple. You type HELM package. Give it the name of your directory for your chart. This will create a tar zip file that is named with the version number that's in your chart YAML. If we go into the chart YAML, for instance, and change this one to 1.1, and run the package again. You'll see it creates a 1.1. package. HELM packages can be saved and retrieved from remote registries as well. Take a look at HELM's documentation for the instructions on how to do this.

At this point in the course, you've been introduced to several tools that will help you build and run your application in Kubernetes. In the next lesson, we'll introduce one more tool that will help tie everything together into a productive development workflow. Thanks for watching.


Eric Smalling

Eric is a Docker Captain and Senior Developer Advocate at where he helps developers secure the applications, containers and Kubernetes platforms they build and deploy to.

View Profile


Have feedback about this course or lesson? We want to hear it!

Send your thoughts to

Lesson Completed

Advancing to the next lesson in seconds…

Next Lesson
What did you think of this lesson?