Squadcast made it to the "Best Software Award" in the IT Management category by G2 🎉 Read full report here.

Helm - Package Manager for Kubernetes

December 28, 2021
Share this post:
Helm - Package Manager for Kubernetes
December 28, 2021
Share this post:
Squadcast way to resolve Incidents
Subscribe to our latest updates
Enter your Email Id
Thank you! Your submission has been received!
Oops! Something went wrong while submitting the form.

Deploying applications to Kubernetes can be complex as you may be required to create multiple interdependent resources. This blog explains how Helm can help software professionals to package, configure and deploy applications onto Kubernetes.

What is Helm and why do we need it?

Helm is an open source package manager for Kubernetes. Most software development processes need a package manager which can simplify installation and maintenance. However, with increase in the number of components in an infrastructure, managing clusters in Kubernetes can become very complicated. This is where Helm comes into the picture as it wraps up all the components in a single package. It also helps automate software installation, configure software deployments and fetch relevant data. Let's take an example of an app that needs:

  • Deployments
  • Service to expose the application
  • Persistent volume to store data
  • Secrets to hold confidential data.

Now, every object of the application requires a separate 'yaml' file. To create these objects, we need to run the 'kubectl' command. Complications may arise in situations where a bug is introduced or we need to modify the value of secrets. In these situations, we need to rollback, which requires revisiting every file individually to keep them in a particular order.

This problem can be solved by creating one huge file and defining all the object resources in it. By doing this, we can avoid frequent rollbacks. But think in terms of the need to modify values in a large file. For example, what if we need to modify the persistent volume size from 10GB to 100GB?. Given the size of the file, we would need to make sure we are making changes in the right place, and also not introduce any new bugs.

Let's take the example of rpm. An application consists of configuration files, binary files, etc. Rather than placing all these files in an individual directory of our system, we can run one rpm command, which will take care of installing all configuration and binary files in an appropriate directory. Helm takes a similar approach to solve this problem in the previous scenario.

It wraps together all the necessary components (deployments, services, secrets, persistent volume) in a single package. Whenever we need to install these resources, we just need to trigger the requirement in Helm to install a package, and it will install all the corresponding resources. Also, we only need to modify a single file (values.yaml) to update all the resources that are packaged using Helm.

Advantages of using Helm

  • Application installation with a single command (helm install <application name>) even if it consists of thousands of objects.
  • One place to update/modify the resource values (values.yaml).
  • Upgrade your application with a single command (helm upgrade <application name>). Helm keeps track of individual objects that require updates.
  • Single command to rollback your application (helm rollback <application name>). It maintains records of updates made to the application, so it can rollback to the previous versions.
  • Single command to uninstall the app (helm uninstall <application name>). It keeps track of all the objects and knows which object needs to be removed.

Helm Installation

Prerequisites

  • A running Kubernetes cluster (For more info, refer here)
  • Installed Kubectl (For more info, refer here)
  • Helm installation on Mac, Linux, or Windows operating system.

Installation

  • To install Helm, run the commands

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/a933f3f2497889fcbcc9465214049601.js</p>

  • To verify if Helm is installed successfully, run

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/05c5d1788c464e8292ba32758803a394.js</p>

To install Helm on all the supported platforms, check the following documentation.

Helm Internals

Helm uses a command-line utility on your local system to perform Helm actions like install, upgrade, or rollback charts. Let us first understand what is a chart? Helm bundles all your related manifests into a chart, such as deployments, services, and pods. This chart contains all of Helm's instructions to create a Kubernetes object in your cluster.

When you install a chart, a release is created. Within each release, you can have multiple revisions. This chart is then passed to Helm, and it connects to Kubernetes API using kubeconfig (~/.kube/config) to create Kubernetes objects. Now, the next question is where does Helm store the metadata information (such as the installed release, the chart used, revision state), and the answer to that question is inside your Kubernetes cluster in the form of a secret.

  • Use the below command to get the secret value

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/e91afd94b4413ff731a650bdf3235ba0.js</p>

Using Existing Helm Charts

The way we can find docker images in a DockerHub, we can also find the Helm chart in a repository called ArtifactHUB.

Figure 1: Searching Helm chart in ArtifactHUB
  • To install this chart, follow the official instructions here.
  • 'helm repo add' command is used to add the chart repository

<p> CODE: https://gist.github.com/ShubhanjanMedhi-dev/2c6b5a2e4deb9e83e2b6845eea19e69b.js</p>

  • To list the chart repository use

<p> CODE: https://gist.github.com/ShubhanjanMedhi-dev/584ba5ea8ab1651a23ff5adf447e8ef4.js</p>

  • To install a chart, run ‘helm install’ followed by the name and then chart name

<p> CODE: https://gist.github.com/ShubhanjanMedhi-dev/95c676eee2e9d3cda0e3314f13b8e55b.js</p>

NOTE: After you have installed the chart, you will also get some useful information like how to use this chart.

<p> CODE: https://gist.github.com/ShubhanjanMedhi-dev/0977d8c337cfe9b7f18130b36a8a334d.js</p>

  • To verify the installation, use the ‘helm list’ command to list all the releases. As discussed earlier, once the chart is installed, it’s deployed as a release.

<p> CODE: https://gist.github.com/ShubhanjanMedhi-dev/65652ab417daf7b892e901f2fc6852ec.js"</p>

  • You can also search for the chart in the ArtifactHUB using the command line with the ‘helm search hub’ command followed by the application name.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/e11da3b1c927b713e95e7a16abe0136c.js</p>

  • Just like you have added the 'bitnami repo' earlier, you can search it using the ‘helm search repo' followed by the application name.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/f11d0d4bd1aabbc04811f9892ef77fb3.js</p>

  • If you want to uninstall the release, use the ‘helm uninstall’ command followed by the release name. Helm will take care of removing all the objects. If you wish to do it manually on the command line, then you will need to remove all the objects one by one.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/8c48b8a91256076bfb5dd1cfc7d761da.js</p>

  • To remove the chart repository, use the ‘helm repo remove command’ followed by repo name.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/cbaf9703f1ff3b005b37cd0aa063e94d.js</p>

Customizing existing charts

Previously, we installed the chart using the default value. But that may not be your requirement all the time. Hence, you may also pull the chart and then modify 'values.yaml' file according to your requirements.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/530bc938d3062b74c6d477c5f29333de.js</p>

  • The above command will pull the chart in 'tgz format'. Use the below command to view the file.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/debf603241984cb4cc41061cc271d2d2.js</p>

  • If you want to untar the file during the download use

<p> CODE: https://gist.github.com/ShubhanjanMedhi-dev/34060bb6ca3e23e14d1a71a41d0af4ca.js</p>

  • You can set the custom root password by modifying 'values.yaml'

<p> CODE: https://gist.github.com/ShubhanjanMedhi-dev/3aa8f5cc247639f9dd445821fd7a503e.js</p>

  • To install the chart with the custom password value, use ‘helm install’ with the name and the path to the downloaded directory.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/74ab78908784972a12eadda143dc0e1c.js</p>

  • You can use the set command to make the changes permanent and set a custom password, using the command line.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/3dbeffc253b7785603f3f1cf07817ef5.js</p>

  • You can also create your custom value file using

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/b729b502b1f7367ef9191d9cae89ddb2.js</p>

  • Pass it to the command line using –-value.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/1e90729136f1245dbc388296dcbcc624.js</p>

So far you have learned how to install an existing chart from ArtifactHUB and modify the values in those charts. In the next section, we will learn how to build our chart from scratch.

Building your first chart

In previous steps you have installed or modified a chart created by someone else, which is fine in most scenarios. But in cases where you have a custom application, or you need to customize your chart, you will be required to create your own custom chart.

The easiest way to get started with charts is by using ‘helm create’ command. This will create a chart structure for you.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/cf23722af4c93604fbb35257c027a96f.js</p>

  • Let’s explore the directory and other subdirectories/files one by one.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/1866bc6f9c7c003d0c57b29e047d8251.js</p>

  • First, start with the 'Chart.yaml' file. It contains metadata such as chart application version, etc.

apiVersion: When Helm3 was introduced, it came as a field 'apiVersion' to differentiate between Helm v2 vs. Helm v3 chart. For example, Helm v3 has field dependencies not present in Helm v2. So the general rule now is, all the charts built for Helm2 have the field set to v1 and for Helm3 it is v2.

appVersion: This is the version of the application that's inside your chart. For example, if you are installing MySQL, it is the version of the MySQL database. This field is for informational purposes only.

version: The version field holds the value of a chart's version which is independent of the app's version that you have deployed. This is independent of the version of the app you have deployed. This field helps you to keep track of the changes in the chart.

name: This field represents the name of the chart.

description: This field holds the description of your chart.

type: There are two types of charts: applications (default) and library. The application chart is used to build applications, whereas the library chart is used to provide utilities that help build charts.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/aa0b2969dcc254c6ab7b28742cc6e86e.js</p>

templates: It’s the most critical directory and contains Kubernetes resource definitions, for example; deployments, services, etc.

  • Let’s start with a clean slate and delete all the files inside this directory.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/9dd38e94151dafc1e0354e6a7e62b831.js</p>

  • Create a deployment file; we are going to template it, which we will see in the later section.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/f9189ef2d9e349940967abbdcf86b3c3.js</p>

  • Expose the above deployment.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/0101f4252fc99754b4bfbf372a55dcd8.js</p>

NOTE: We are trying to expose the deployment which doesn’t exist. Let’s create it temporarily as we want to create it via Helm.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/8eb1e42e645698f139bc6e2e421241ff.js</p>

  • Try to expose the deployment again, and this time, it should work.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/1b388c13ed648cbf1f059cbed52c63a5.js</p>

  • Don’t forget to cleanup the deployment after that.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/04817c6bbc91711e8e85c47ecb683cc5.js</p>

This is all we need at this stage. Our Helm chart is ready to go. But before that, let's verify the files we created in the earlier steps, for example, 'deployments.yaml'. As you can see in deployments, all the values are static, for example, name: nginx, replicas: 1, or image, name: nginx.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/7829bac639c3a38dba51037be28966e2.js</p>

  • As you can imagine, hardcoding these values is not a good solution, instead, we can fix this problem in Helm, by templating it. The way we can solve this problem is by using Helm templating language.
  • The first thing we will do is templatize the name, where we use Helm, to use deployment's name based on what user chose to name their release.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/20f4673c5699cc0779176f415298108b.js</p>

  • If we try to install Helm chart, then in this case the name should be picked from the release name which is 'my-demo-chart', so the name is 'my-demo-chart-nginx' (as you have appended -nginx in the end)

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/43cc941b42a9742de789e6fef6b0528f.js</p>

  • To templatize something we should add two curly brackets {{ }} and add something between these two curly brackets and this is called a 'template directive' which is a part of the Go Programming template language. For more information please check here.
  • To parameterize other variables we can use 'values.yaml' file. The 'values.yaml' file contains all the parameterized values.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/1247ccb8192e90a93c926e6aa6d3f166.js</p>

  • To refer to these values we need to use 'Values' followed by key names. So for 'replicaCount', we will use 'Values.replicaCount' and 'Values.image.repository'.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/9b2fc809d106cf3716e9cd60ba7ea566.js</p>

By now you must be eager to run your first Helm chart but before doing that, check if your chart is working as expected. There are three ways of doing that:

  • helm lint: Linting helps you verify if the chart and yaml format are correct. Some common errors that linting helps with are, not enough white space or typo mistakes in the file. To do that, you need to pass the chartname (for example: mydemochart) to the ‘helm lint’ command, and it will give you a file, and tell you which file or line has the errors. Also, it recommends some of the best practices like using icons in the 'Chart.yaml'.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/f6c3a5e81adbbdb87e04572d25b65dc1.js</p>

  • helm template: Ensures that the templating part is working as expected. With lint, you have verified there are no typing mistakes; By using templates, we can ensure that the templating stuff you have added in the 'deployment.yaml' is generating the correct output as expected i.e. 'Release.Name' is translating to the actual release name. The way it works is, it renders the chart template locally and displays the output.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/9e7cfe6d690a711b843bcb7af8eaa86c.js</p>

  • --dry-run: 'helm lint' and 'helm template' command are enough to catch errors and ensure functioning of Helm with Kubernetes. However if there is an issue with the Kubernetes manifest file, it will pretend to install packages in a cluster and will catch the issue shown by Kubernetes during the actual run. This is a handy way to verify it before running the actual chart.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/926588855c7e77b4338fa26c6b1815e6.js</p>

  • If things look good, you can deploy the chart using,

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/15ead47885332c714c7a6706fa08c11d.js</p>

  • To verify the installation, run the ‘helm list’ command

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/89d3daf137a86bfd49534c44a5d66bca.js</p>

  • To uninstall the chart, run

<p> CODE: https://gist.github.com/ShubhanjanMedhi-dev/f3c84462ed6db7ee667fbc1debd5de19.js</p>

Once the chart is ready, we can share it with other team members or even globally, to promote collaboration. Developers on a global scale can help enhance the chart and fix bugs. In the next section, we will learn how to package a chart.

Packaging Chart

We have our chart ready, but if you want to share it with the rest of the team or the rest of the world, you need to package it.

  • To package your chart use the ‘helm package’ command. This command packages the chart in archive format (for example, mydemochart-0.1.0.tgz). The version number '0.1.0' is picked from the 'Chart.yaml' file.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/f192978680af5e95ba989b45b5952984.js</p>

  • To verify it use

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/2ad0ec5b9e1fcb1e193b7304066d43fa.js</p>

Now that we have packaged our chart, it’s time to upload it to online repositories like GitHub or a bucket in S3, etc. These are the steps we need to follow:

  • Create a directory and then copy the file we have created.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/094887c364621d9da7ab80a4dd49cb05.js</p>

  • Run the 'helm repo index command' and give the destination url.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/42d28a5bb846235f4ad6db24209f7a53.js</p>

  • The above command is going to generate the 'index.yaml' file. The file will contain information about the chart repository. The chart contains, a checksum, and a description of the chart. This is the file that Helm will read when we run a command like ‘helm repo’. It adds and points it to the chart repository.

<p>CODE: https://gist.github.com/ShubhanjanMedhi-dev/63a653d15757ae081c9ca5ecac374de9.js</p>

Conclusion

In this blog, we have learned the basics of Helm and how to create a Helm chart. Helm is a powerful tool, and it greatly simplifies how package management works with Kubernetes.

Squadcast is an incident management tool that’s purpose-built for SRE. Your team can get rid of unwanted alerts, receive relevant notifications, work in collaboration using the virtual incident war rooms, and use automated tools like runbooks to eliminate toil.

squadcast
Written By:
December 28, 2021
December 28, 2021
Share this post:
Related Content
The Age of Service Mesh
The Age of Service Mesh
November 28, 2019
Using observability tools to set SLOs for Kubernetes Applications
Using observability tools to set SLOs for Kubernetes Applications
April 16, 2020
Kubernetes Health Check Using Probes
Kubernetes Health Check Using Probes
March 2, 2022
Experience the Journey from
On-call to SRE
Experience the Journey from On-call to SRE
Squadcast - On-call shouldn't suck. Incident response for SRE/DevOps, IT | Product Hunt Embed
Squadcast is a leader in Incident Management on G2 Squadcast is a leader in Incident Management on G2 Users love Squadcast on G2 Best IT Management Products 2022 Squadcast is a leader in IT Service Management (ITSM) Tools on G2 Squadcast is a leader in IT Service Management (ITSM) Tools on G2 Squadcast is a leader in IT Service Management (ITSM) Tools on G2
Squadcast - On-call shouldn't suck. Incident response for SRE/DevOps, IT | Product Hunt Embed
Squadcast is a leader in IT Service Management (ITSM) Tools on G2 Squadcast is a leader in Incident Management on G2 Users love Squadcast on G2
Best IT Management Products 2022 Squadcast is a leader in IT Service Management (ITSM) Tools on G2 Squadcast is a leader in IT Service Management (ITSM) Tools on G2
Squadcast is a leader in IT Service Management (ITSM) Tools on G2
Copyright © Squadcast Inc. 2017-2021