AmitKumarDas / Decisions

Apache License 2.0
10 stars 3 forks source link

K8s: Amazing Controllers ~ Origins #221

Open AmitKumarDas opened 4 years ago

AmitKumarDas commented 4 years ago

Motivation: This is part of the series of articles that helps us to achieve the following:

AmitKumarDas commented 4 years ago

Kubernetes Controllers - A Primer: Let us try to refresh our understanding on Kubernetes (K8s) controllers before trying to dig deep into csi external attacher project. Note that this external attacher project can be considered as one of the implementations of K8s controller.

A K8s controller is a logic that tries to arrive the K8s cluster into some desired state. There can be so many desired states due to the needs of various components, applications, etc running on Kubernetes. However, K8s provides us with the ability to define a particular desired state in form of specifications. A specifications is a well defined schema that can act as a payload to a particular endpoint of the K8s API Server.

While designing applications to run on Kubernetes, it is important to define a desired state that tries to handle a single responsibility. One can always define multiple desired states (hereafter referred to as specs) to achieve the entire requirement. If we are able to define clear separation of responsibilities as specific specs, we can let Kubernetes reconciliation mechanism to solve other additional concerns that are related to infrastructure, deployments, security, self-heal, and many more.

All these while, we have been talking about design part. Lets talk a bit about K8s controllers. What are they? These is definitely some logic/code :smiley: . However, this is more aligned to write logic in a way K8s wants us to. One can even consider this as a framework or pattern if that aligns with your mental model. As per Kubernetes docs itself, its controller (implementation) is a reconciliation loop that runs continuously to merge (reconcile) the current (last observed) state in K8s to its desired state in k8s. Since this is a continuous loop, user (or tool) can keep updating (via specs) the desired state and let this reconciliation logic to realise the desired state.

AmitKumarDas commented 4 years ago

Kubernetes Controllers - Basic Building Blocks Since K8s wants us to write the reconcile logic in a certain way, let us try to understand various parts that builds this particular approach. To start with, there is an Informer which has the ability to inform us about the desired state of a particular resource. Note that a resource here implies the specific specs we talked about earlier. Informer has various tunables and coordinates with a configurable cache that abstracts us from the low level specifics to get the latest desired state of a resource.

The next blocks that we need to be concerned about are the ones that interacts with above Informer to act based on the latest desired state information. Since desired state is already described in the specifications, these blocks can calculate the difference between current state (can be other K8s specs or state received from third party invocations) and desired state and apply the difference to arrive at this desired state.

However, these blocks needs to be implemented as hooks set against the Informer. In other words, the definition of Informer will have the references to these hooks that gets invoked when Informer has any information of the current state of the specifications. These hooks can further be categorised into add, update, delete hooks. However, we will eventually learn that hook type does not matter since all of them should be idempotent in nature.