Learning Kubernetes

Multi-Host Container Scheduling:

- Done by the kube-scheduler
- Assigns pods to nodes at runtime
- Checks resources, quality of service, policies, and user specifications before scheduling

Scalability and Availability:

- K8s master can be deployed in a highly available configuration
- Multi-region deployments are available
- 5000 node cluster/150,000 total pods
- Pods can be horizontally scaled via API

Flexibility and Modularization:

- Plug-and-play architecture
- Extend architecture when needed
- Add-ons: network drivers, service discovery, container runtime, visualization, and command

Features that allow Kubernetes to scale:

- Registration: nodes register themselves with master
- Service Discovery: automatic detection of services and endopoints via DNS or environment variables

Persistent Storage:

- Pods can use persistent volumes to store data
- Data retained across pod restarts and crashes

Application Upgrades and Rollbacks are supported out of the box

Kubernetes Maintenance and Upgrades:

- Features are always backward-compatible
- APIs are versioned
- Turn off/on host during maintenance (unschedulable)

Logging and Monitoring:

- Application monitoring built in
    - TCP, HTTP, or container execution health check
- Node health check:
    - Failures monitored by node controller
- Kubernetes status:
    - Add-ons: Heapster and cAdvisor
- Using existing logging framework or extend out and use your own

Secrets Management

- Secrets are mounted as data volumes or env variables
- Spacific to namespace - not shared accross all the applications


Other Orchestrators

  • Mesos/Rancher/Docker Swarm/Kubernetes
  • Amazon EC2 Container Service or Oracle Container Cloud Service

Architecture of a Kubernetes Cluster

  • Master Node: overall management of the kubernetes cluster and consists of 3 components:

    • Communications: The API Server - kube api server
    • Scheduling:
      • Scheduler - watches created pods that do not have design yet, and designs a pod to run on a specific node
    • Clustering: Conroller/Cluster Manager:
      • Run controllers - background threads that run tasks in a cluster
      • Controller has many different roles, but they are compiled into a single binnary - the roles include:
        • The node controller - responsible for the worker states
        • The replication controller - responsible for maintaining the current numbder of pods for the replicated controllers
        • The end-point controller - joins services and pods together
        • Service accounts and token controllers - handle access management
    • etcd: a simple key-value store:
      • Kubernetes stores all cluster data here in etcd:
        • stores job scheduling information, pod details, state information, etc.
    • kubectl: application that allows us to interact with master node
      • Command-line interface to Kubernetes
      • contains config file - kubeconfig (authentication/cluster info)
  • Worker Nodes: where the applications are operating

    • The communicate back to the master node
    • Communication to worker nodes is handled by Kubelet Process: agent that communicates with the master node over the API Server, to see if the pods have been designed to the nodes
    • It executes Pod containers via the container engine
    • It runs and mounts Pod volumes and secrets
    • Is aware of the Pod and Node states and responds back to the Master
    • Docker works together with the Kubelet to run containers on the node
  • Kube-Proxy:

    • This process is the Network Proxy and the Load Balancer for the service, on a single Worker Node
    • It handles the network routing for the TCP and UDP packets
    • It also performes connection forwarding

Summary:

  • Having the Docker Demon allows you to run containers.
  • Containers of an application are tightly coupled together in a Pod.By definition, a Pod is the smallest unit that can be scheduled as a deployment in Kubernetes.
  • This group of containers share storage, Linux name space, IP addresses, amongst other things.
  • They're also call located and share resources that are always scheduled together.
  • Once Pods have been deployed, and are running, the Kubelet process communicates with the Pods to check on state and health, and the Kube-proxy routes any packets to the Pods from other resources that might be wanting to communicate with them.
  • Worker Nodes can be exposed to the internet via load balancer. And, traffic coming into the Nodes is also handled by the Kube-proxy, which is how an End-user ends up talking to a Kubernetes application.

Basic Building Blocks: Nodes and Pods

Node:

  • Serves as a worker machine in a K8s cluster. The node can be a physical computer or a virtual machine
  • Each node has to have the following:

    • A kubelet running
    • Container toolike (Docker)
    • A kube-proxy process running
    • Process for starting/stoping components - Supervisord
  • In production setting, it is recommended to have at least a 3 node cluster

Minikube:

  • Lightweight Kubernetes implementation that create a VM on your local machine and deploys a simple cluster containing only one node

Pods: the most basic unit needed to run the kubernetes cluster

  • We can create/deploy/delete pods and it represents one running process on your cluster
  • Contains:
    • The Docker application container
    • Storage resources
    • Unique network IP
    • Options that govern how the container(s) should run
    • It is possible to have a few containers running in the pod, but pod represents a single unit of deployment - a single instance of an application in Kubernetes that is tighly coupled and shares resources.

More About Pods:

  • Pods are designed to be ephemeral, disposable entities.
  • Never create Pods just by themselves in a production application. Only do that when you need to test whether the underlying containers actually work.
  • Pods also don't self-heal. If a Pod dies, for some reason, it will not be rescheduled.
  • Also, if a Pod is exited from a Node because of lack of resources, it will not be restarted on different healthier Nodes.
  • There are higher level constructs to manage and add stability to Pods, called controllers. So pro-tip, don't use a Pod directly. Use a controller instead, like a deployment.
  • Through its life-cycle, a Pod has the following states:
    • Pending, which means that the Pod has been accepted by the Kubernete system, but a container has not been created yet.
    • Running, where a Pod has been scheduled on a Node, and all of its containers are created, and at least one container is in a running state.
    • Succeeded, which means that all the containers in the Pod have exited with an exit stat of zero, which indicates successful execution, and will not be restarted.
    • Failed, which means all the containers in the Pod have exited and at least one container has failed and returned a non-zero exit status
    • CrashLoopBackOff. This is where a container fails to start, for some reason, and then Kubernetes tries over and over and over again to restart the Pod.

Deployments, ReplicaSets and Services

Benefits of Conrollers:

  • These are application reliability: where multiple instances of an application running prevent problems if one or more instance fails.
  • Scaling - when your pods experience a high volume of requests, Kubernetes allows you to scale up your pods, allowing for a better user experience.
  • Load balancing - where having multiple versions of a pod running allow traffic to flow to different pods and doesn't overload one single pod or a node.

Kinds of Controllers:

  • ReplicaSets:
    • It has one job, it ensures that the specified number of replicas for a pod are running at all times. If the number of pods is less than what the ReplicaSet expects, for example, when a pod might have crashed, the ReplicaSet controller will start up a new pod, however, you can't actually declare a ReplicaSet by itself. You'll need to use it within a deployment, so let's look at what that is.
  • Deployments:
    • A Deployment Controller provides declarative updates for pods and ReplicaSets. This means that you can describe the desired state of a deployment in a YAML file and the Deployment Controller will align the actual state to match. Deployments can be defined to create new ReplicaSets or replace existing ones with new ones. Most applications are packages deployments, so chances are, you'll end up creating Deployments more than anything else. Essentially, a deployment manages a ReplicaSet which, in turn, manages a pod.
    • The benefit of this architecture is that deployments can automatically support a role-back mechanism. A new ReplicaSet is created each time a new Deployment config is deployed, but it also keeps the old ReplicaSet. This allows you to easily roll back to the old state if something isn't quite working correctly.
    • Deployment Controller Use Cases:
      • Pod management, where running a ReplicaSet allows us to deploy a number of pods and check their status as a single unit.
      • Scaling a ReplicaSet, which scales out the pods and allows for the deployment to handle more traffic.
      • Pod updates and role-backs, where the Deployment Controller allows updates to the PodTemplateSpec. This creates a new ReplicaSet and deploys a newer version of the pod. Also, if you don't like what you see in the newer version of the pod, just roll-back to the old ReplicaSet.
      • Pause and resume - Sometimes we have larger changesets or multiple updates that need to happen to a deployment. In these scenarios, we can pause a deployment, make all the necessary updates, and then resume the deployment. Once the deployment is resumed, the new ReplicaSet will be started up and the deployment will update as expected. Please note that while a deployment is paused, it means that only updates are paused, but traffic will still get passed to the existing ReplicaSet as expected.
      • Status - Getting the deployment status is an easy way to check for the health of your pods and identify issues during a roll-out.
    • Replication Controllers - has been replaced by Deployments and ReplicaSets
  • DaemonSets:
    • Ensure that all nodes run a copy of a specific pod
    • As nodes are added or removed from the cluster, a DaemonSet will add or remove the required pods.
    • Deleting a DaemonSet will also clean up all the pods that it created.
    • The typical use case for a DaemonSet is to run a single log aggregator or monitoring agent on a node.
  • Jobs:
    • Basically a supervisor process for pods carrying out batch processes to completion. As the pod completes successfully, the job tracks information about the completion state of the pod.
    • Jobs are used to run individual processes that need to run once and complete successfully. Typically, jobs are run as a cron job to run a specific process at a specific time and repeat at another time. You might use a cron job to run a nightly report or database backups, for example.
  • Services:
    • Provides network connectivity to one or more pods in your cluster.
    • When you create a service, it's designed a unique IP address that never changes through the lifetime of the service. Pods are then configured to talk to the service and can rely on the service IP on any requests that might be sent to the pod.
    • Services are a really important concept because they allow one set of pods to communicate with another set of pods in an easy way. It's a best practice to use a service when you're trying to get two deployments to talk to each other. That way, the pod in the first deployment always has an IP that they can communicate with regardless of whether the pod IPs in the second deployment changes.
    • For example, when your front-end deployment needs to call a back-end deployment, you want to address the back-end with a service IP. Using the Backend Pod IP is a bad choice here because it can change over time and would wreak havoc for your application. A service provides an unchanging address so that the Frontend Pods can effectively talk to them at all times.
    • There's a few kind of services that you can use:
      • Internal services, where an IP is only reachable from within the cluster, this is the cluster IP in Kubernetes speak
      • External services, where services running web servers, or publicly accessible pods, are exposed through an external endpoint. These endpoints are available on each node through a specific port. This is called a NodePort in Kubernetes speak.
      • Load balancer - this is for use cases when you want to expose your application to the public internet. It's only used when you are using Kubernetes in a cloud environment backed by a cloud provider such as AWS

Labels, Selectors and Namespaces

Labels:

  • Are key value pairs that are attached to objects like pods, services, and deployments.
  • Labels are for us, the users of Kubernetes, to identify attributes for objects.
  • Typically, labels are used to organize clusters in some meaningful way. They can be added at deployment time, or later on and changed at any time.
  • Label keys are unique per object. Here are some examples of labels we might use:
    • We might have a release label that has stable or canary deploys.
    • We could have environment labels that specify the environment, such as dev, qa, production, et cetera.
    • Perhaps tier labels to signify that something is a front end or a back end tier.
  • As you can tell, labels are very specific to your use case, and they are built for users, so think about what your environment looks like, and how you want to organize your applications, and then get your label maker out.

Selectors: By themselves, labels aren't really that powerful. But when you add selectors, you introduce a very powerful feature. With labels and selectors, you can identify a specific set of objects. There are two kinds of selectors: equality-based and set-based:

  • Equality-based selectors include the equals and not equals, where the equals represents equality, where two labels or values of labels should be equal. Not equal represents inequality. This means that the values of the labels should not be equal.
  • Set-based selectors that include IN, NOTIN, and EXISTS operators:
    • The IN operator specifies that the value should be in a set of defined values.
    • The NOTIN operators specified that the value should not be in a set of defined values.
    • And finally, the EXISTS operator is used to determine whether a label exists or not.
  • Labels and label selectors are typically used with a kubectl command to list and filter objects. We'll look at examples of how to use labels and selectors later on in the demo section of the course.

Namespaces: And finally, we have namespaces. Unlike labels and selectors, the namespace concept is a feature of Kubernetes that allows you to have multiple virtual clusters backed by the same physical cluster. Namespaces are a great concept to use for large enterprises where there are many users and teams and you want to give access to different teams but at the same time have a rough idea of who owns what in the Kubernetes environment. For example, if you have a big e commerce company, you might have a namespace for your catalog team, card team and order status team to run their different applications. It's also a great way to divide cluster resources between multiple users and this can be done using resource quotas. Namespaces provide scope for names. Names of resources, like deployments and pods, must be unique within the namespace, but not necessarily across separate namespaces. So in our example, the catalog team and the card team can have an application name authentication in their own namespaces. When you launch Kubernetes, there is a default namespace where all our objects get placed, but you are allowed to create new namespaces as and when you wish. Also you'll notice that when you install newer application Kubernetes, they'll typically install in a brand new namespace, so that they don't interfere with your existing cluster and cause confusion. In this section, we've gone over ways to organize your applications. Join me in the next section to go cover the Kubelet and Kube-proxy topics.


Kubelet and kube proxy

Kubelet - Kubernetes node agent:

  • It communicates with the API server to see if pods have been assigned to the nodes.
  • It executes the pod containers via the container engine.
  • It mounts and runs pod volumes and secrets.
  • It executes health checks and is aware of pod and node status and reports that back to the API server.
  • The kubelet works in terms of Podspec, which is just a YAML file that describes the pod.
  • The kubelet takes a set of Podspecs that are provided by the kube-api server and ensures that the containers described in those Podscpecs are running and healthy.
  • It's important to note that the kubelet only manages containers that were created by the API server, and not any other containers that might be running on the node.
  • We can also manage the kubelet without an API server by using HTP endpoint or a file, but that's beyond the scope of this course.

kube-proxy - The network proxy:

  • This is another process that runs on all the worker nodes. The kube-proxy reflects services that are defined in the API on each node and can do simple network stream or round-robin forwarding across a set of backends. Service cluster IPs and ports are currently found through Docker-link compatible environment variables specifying ports opened by the service proxy.
  • The kube-proxy has three modes: the user space mode, Iptables mode, and ipvs mode, which is an alpha feature in Kuberetes 1.8. The user space is the most common mode, and the one we will use in this course. If you're really interested in the gory networking details, take a look at the handout for more information on those. These modes are important when it comes to using services. Services are defined against the API server. The kube-proxy watches the API server for addition and removal of services. For each new service, kube-proxy opens a randomly chosen port on the local node. Any connections made to that port are proxied to one of the corresponding back-end pods.

In [ ]: