I am currently doing some work where I am using tools that are considered tools for creating Cloud Native Applications. Cloud Native Applications are the latest trend in enterprise software. The problem is, what is Cloud Native? The Wikipedia page is lacking a good definition. A search of the web shows everybody has there own definition. So coming up with a good definition that everyone can agree with is hard. I am going to attempt to give a definition that I think defines Cloud Native. I mentioned tools at the beginning of this post and most of the tools are owned/maintained by the Cloud Native Computing Foundation. I am not going to go into details about the projects the CNCF maintains in this post, but you can check out their site for more information.
Cloud Native Defined
Many people define Cloud Native as only running in the cloud. Others define it as moving my current applications so that it runs in a Virtual Machine in the cloud. The Cloud does play an important role in Cloud Native, but that cloud does not have to be the public cloud. It could mean private infrastructure as well. It also doesn’t have to be a brand new application, and you can adapt your current on-premises. I was reading up on DevOps best practices for Cloud Native apps (Cloud Native DevOps with Kubernetes). They layout some properties that define a Cloud Native application. I agree with them so here they are:
Of course a DevOps book will lead with automation. I worked at a company that would deploy their application by copying the app to each machine and would manually modify XML config files to configure the app. This process was time-consuming and error-prone. The deployment and configuration of a Cloud Native applications should be automated. Automation provides repeatable deployments that, once configured, can be fire and forget. This saves time and is less error-prone. It doesn’t matter the environment, dev, test, and prod; the application should be deployed in the same manner with predictable results every time.
Ubiquitous and flexible
Cloud Native applications tend to be hosted in containers like Docker and run in an orchestrator in the cloud, like Kubernetes. Kubernetes is an open-source system for automating deployment, scaling, and management of containerized applications. If you are not up to speed on Kubernetes, then check out this book Kubernetes Up and Running. I found this to be a helpful learning tool. So how does Kubernetes allow you to be ubiquitous and flexible? Containerization removes the dependency of the underlying hardware. Once your application runs in a container, it runs anywhere Kubernetes can run. That means you are now flexible to run on Azure, AWS, Google Cloud, or even your in-house hardware.
Resilient and scalable
One of the biggest plagues of applications is failure. It doesn’t matter if the application runs on on-premises or in the cloud; any failure will cause harm to your user and organization. The cloud adds additional challenges in that if there is a hardware failure, you don’t have access to fix the problem. Cloud Native apps tend to be distributed, so they need to handle failure gracefully. There should be redundancy so that should a service fail, there are backups in its place.
One of the reason to develop a Cloud Native application is to reduce the cost associated with that application. You reduce the cost of hosting your application by taking advantage of the cloud. Your Cloud Native app should maximize the resources available. Kubernetes scheduler handles that for you. It maintains your application at levels you configure. Your environment can also be configured to handle bursts of traffic to your application by scaling up or down the number of nodes available.
Having an application distributed around the world can cause logistics nightmares when trying to debug issues. Cloud Native applications need to include monitoring. By incorporating monitoring, logging, and tracing into your application, you can garner data that can help you understand how your application is behaving in the wild.
Your Cloud Native application should take advantage of the distributed nature of the Cloud. The age of monolithic applications should be coming to an end. You should be able to update pieces of your application at different intervals. I have avoided the use of the word microservices because your application doesn’t have to utilize microservices to be Cloud Native.
Infrastructure as Code
I added this property to those provided by the DevOps book. The project I was on had the requirement to run on a few different cloud platforms. Kubernetes is great at orchestrating different pieces of your application; it is not good at setting up the infrastructure in a repeatable way. For that, I used Terraform. Terraform is a great tool that allows you to set up infrastructure using a declarative language that can then be checked into source control. Terraform can be automated using many different build platforms like Azure DevOps, Jenkins, and the like. I found this book Terraform Up and Running, useful in getting up to speed. If you would like to learn more, I will be giving a talk, All the Cool Kids Use Terraform to Deploy Kubernetes …So Can You!, about using Terraform to deploy Kubernetes, at the Boston Code Camp on March 21, 2020.
I think that this is a pretty good definition of Cloud Native. Do you need to use all the tools that I did to be Cloud Native? Of course not; you don’t have to use any of these tools. I think that as long as your application follows the properties I discussed, then you are well on your way to being Cloud Native. You may not agree with my Cloud Native definition, and that is ok too.
*Note that some of the links on this page are affiliate links. You can help out my blog by using them if you think the information provided by those books would be helpful to you.