Table of Contents

Infrastructure Workflow: Deploy a Kubernetes Stack With Hub CLI

Agile Stacks Updated by Agile Stacks

In this tutorial, you are going to deploy a Kubernetes cluster on AWS using Spot instances and cluster autoscaling for cost optimization. The cluster will be integrated with DNS, TLS via Let's Encrypt, and SSO via Okta.

Hub CLI is a powerful and easy to use tool for infrastructure automation. It is also an interface to SuperHub (API). SuperHub is an infrastructure automation service to deploy and manage software stacks - in the cloud and on-prem. You can manage, configure, and implement change control for your infrastructure-as-code using the SuperHub.

Install Hub CLI

First, install Hub CLI binary:

On Mac

curl -O https://controlplane.agilestacks.io/dist/hub-cli/hub.darwin_amd64
mv hub.darwin_amd64 hub
chmod +x hub
sudo mv hub /usr/local/bin

On Linux

curl -O https://controlplane.agilestacks.io/dist/hub-cli/hub.linux_amd64
mv hub.linux_amd64 hub
chmod +x hub
sudo mv hub /usr/local/bin

Login into SuperHub:

hub login -u your@email.tld
Password:

Add export HUB_TOKEN=... to your ~/.bash_profile / etc.

On-Board Your Cloud Account

SuperHub is linked to the AWS cloud account via credentials supplied by you. When Hub CLI works in the local mode it talks to the cloud directly - by using ~/.aws/credentials. When Hub CLI drives SuperHub via its API, it must setup several essential cloud resources in the account:

  1. An S3 bucket for Hub CLI and Terraform state, for backups;
  2. DNS zone that will be linked to superhub.io under a subdomain of your choice;
  3. A cross-account IAM role that will be used by SuperHub to securely deploy resources in your cloud account. SuperHub do not store your AWS keys.

Choose a cloud account name. This will become the subdomain under which all of your Kubernetes services are hosted. The name will become a subdomain under superhub.io

For the rest of this example, we will use my-domain-01.superhub.io Please replace it with your chosen name in the rest of the examples.

By default, we host everything in the superhub.io domain. This is to ensure that there is a valid zone to host all of the Kubernetes clusters that are created. This can be changed later, but for now, the fastest approach is to just use 'superhub.io'

hub api cloudaccount onboard -w my-domain-01.superhub.io aws us-east-2

Consult hub api cloudaccount onboard --help for futher examples.

You can list cloud accounts via:

hub api cloudaccount get

Create an Environment

The environment is a SuperHub umbrella entity that organizes deployments, parameters, external facts, and Team's permissions. A good name for the environment is Dev, QA, etc.

Create environment:

hub api environment create Dev01 my-domain-01.superhub.io

You can list environments via:

hub api environment get

A single cloud account can host multiple environments.

Create Your Template

SuperHub approach of repeatable infrastructure-as-code revolves around Templates - a collection of automation scripts to deploy interconnected software Components. A unit of deployment is a template; also, every component could be redeployed or undeployed individually.

Start by copy-pasting this json into your own template.json file. Feel free to name the template whatever you like, but remember it, because we'll use it in the next steps.

template.json

{
"name": "kubernetes-1",
"description": "Kubernetes with Let's Encrypt",
"tags": [
"kind=platform"
],
"stack": "k8s:1",
"componentsEnabled": [
"traefik",
"dex",
"cluster-autoscaler",
"cert-manager",
"kube-dashboard2"
],
"verbs": [
"deploy",
"undeploy"
],
"parameters": [
{"name": "component.kubernetes.etcd.count", "value": 1},
{"name": "component.kubernetes.etcd.size", "value": "t3.micro"},
{"name": "component.kubernetes.etcd.spotPrice", "value": 0.20},
{"name": "component.kubernetes.master.size", "value": "t3.medium"},
{"name": "component.kubernetes.master.count", "value": 1},
{"name": "component.kubernetes.master.spotPrice", "value": 0.20},
{"name": "component.kubernetes.worker.size", "value": "m5.large"},
{"name": "component.kubernetes.worker.count", "value": 2},
{"name": "component.kubernetes.worker.spotPrice", "value": 0.20},
{"name": "component.kubernetes-dashboard.rbac.kind", "value": "admin"},
{"name": "component.ingress.urlPrefix", "value": "app"},
{"name": "component.ingress.ssoUrlPrefix", "value": "apps"}
]
}

Create the template in the SuperHub service using the template file you just created.

$ hub api template create < template.json

Here is a template named kubernetes-1 which provides several software components:

  • Traefik as ingress controller
  • Dex for SSO with Okta
  • Kubernetes Cluster Autoscaler
  • Cert-manager for TLS with Let's Encrypt
  • Kubernetes Dashboard v2

It's based on k8s:1 Super Template that provides boilerplate and default configuration.

Kubernetes will be deployed on Spot instances with one Etcd t3.micro VM, one Master on t3.medium, and one m5.large Worker node. Kubernetes Dashboard is given admin permissions. Ingress subdomain for the the cluster deployed from this template is appapps for SSO protected ingresses.

Initialize the template:

hub api template init kubernetes-1

This command creates a Git repository to host the template source code and populates it with automation scripts, components, and parameters. The repository is accessible via https URL, and you can clone a local copy on your computer using standard Git tools.

To list available templates:

hub api template get

Deploy Your Stack Instance

This step creates the Kubernetes cluster in your AWS account, and populates it with the components specified in the template.

We call it a "Stack Instance" because it is an instantiation of a Stack Template. You can create 1 or 1,000 instances of the same template. They can also be upgraded as their constituent components are upgraded.

Create stack instance with defaults from the template:

$ hub api instance create <<EOF
{
"name": "cluster-01",
"environment": "Dev01",
"template": "kubernetes-1"
}
EOF

The stack instance is created in initial state.

Note the name of the instance. This, along with the name of the cloud account, becomes the root domain name of the Kubernetes cluster.
Our convention is:
<stack instance name>.<cloud account name>.superhub.io

Finally, deploy!

hub api instance deploy -w cluster-01.my-domain-01.superhub.io

The command will follow the deployment log and will exit after the automation task is completed on SuperHub side.

Inspect the instance:

hub api instance get cluster-01.my-domain-01.superhub.io

Visit Kubernetes Dashboard at https://kubernetes.apps.cluster-01.my-domain-01.superhub.io

Also, you can view the Traefik Dashboard at https://apps.cluster-01.my-domain-01.superhub.io which will show you the services that are hosted in your K8s cluster.

From here you can explore SuperHub via hub api commands. Or check out the hub CLI documentation

Alternatively, go to https://controlplane.agilestacks.io to view resources created in UI. You can learn more about the control plane here

Like what you see? Request a demo today!


How did we do?

Development Workflow on Kubernetes - Local Development with Skaffold

Creating Stacks

Contact