k8s cka 02 - core concepts
- cluster architecture
- service & other network primitives
- api primitives
- host applications
- container runtime
a distributed reliable key-value store that is simple, secure & fast
- key-value store
- no duplicate keys cause each value is used once
- download binaries
- run the executeable
etcd will listen on port
2379 by default
etcdctl is used to handle keys and values
etcd in kubernetes
every information we became using the
kubectl get command is received from
every changes are updated in etcd server
therte are 2 ways to install etcd
- setup manual
- configure using the advertise client url
- setup kubeadm
- create a pod which contains the etcd server
etcdctl is the cli tool to interact with
etcdctl can interact using api
version 2 and
by default etcdctl uses version 2
# version 2 > etcdctl backup > etcdctl cluster-health > etcdctl mk > etcdctl mkdir > etcdctl set # version 3 > etcdctl snapshot save > etcdctl endpoint health > etcdctl get > etcdctl put
the primary management resource in kubernetes - api server can also be managed by sending a post request instead of the the kubectl command
- authenticate user
- validate request
- retrieve data
- update etcd
api-server is the only part that communicate with etcd directly
important options in kube-apiserver service are
if installed per kubeadm - the kube-apiserver is deployed by using a pod on the
master node. in this case the api-server configuration file lays under:
/etc/kubernetes/manifests/kube-apiserver.yaml - to get this information on a none kubeadm setup is to inspect the systemd unit file - also
ps aux|grep kube-apiserver shows the actually used options as well
can continiously monitoring the status of the components using in the system and bringing the whole system in a functionally state.
node-controller - receives every 5 seconds a heartbeat from the nodes (over the apiserver)
- node monitor period = 5sec
- node monitor grace period = 40sec
- pod eviction timeout = 5min
- if this fail the node controller removes all pods from there and roll the pods in another node relais on the replicaset
replication controller - monitoring the status of the replicasets and ensure the given number of pods are available
there are also
all of these are managed in the
kube-controller-manger - the kube-controller-manager is setting up by systemd unit file as well
in this unitfile we specified the
with the option
--controller we can chosse which kind of controllers are used - by default all controllers are enabled
if installed per kubeadm - the kube-controller-manager is deployed by using a pod on the
master node - in this case the kube-controller-manager configuration file lays under:
/etc/kubernetes/manifests/kube-controller-manager.yaml - to get this information on a none kubeadm setup is to inspect the systemd unit file - also
ps aux|grep kube-controller-manager shows the actually used options as well
responsable for scheduling pods or nodes
kube-scheduleronly decide which pod goes on which node
here we can setup a multinode setup with different efficient hardware dedicated to the application runs on
high level workflow
- filter nodes that fits the profile - maybe 10 cpus
- ranks nodes the get the best node for the pod - which has more free cpus
if installed per kubeadm - the kube-scheduler is deployed by using a pod on the
master node - in this case the kube-scheduler configuration file lays under:
/etc/kubernetes/manifests/kube-scheduler.yaml - to get this information on a none kubeadm setup is to inspect the systemd unit file - also
ps aux|grep kube-scheduler shows the actually used options as well
the kubelet - which runs on the
worker nodes - register the nodes on k8s cluster. when it get a instruction - from the scheduler over the api-server - it request the container runtime to pull the required image and run that instance. kubelet monitors the state of the node and pods
kubeadm does NOT deploy kubelets
inspect the systemd unit file - also
ps aux|grep kubelet shows the actually used options as well
is a process that runs on each node in a cluster. its job is to look for new services - it creates the appropiate rules on each node to forward traffic to those services to the backend. one way to do this is using iptables to forward traffic heading to the ip of the service to the ip of the pod.
if installed per kubeadm - the kube-scheduler is deployed in a
daemon-set by using a pod on
each node in the cluster
to install this service per hand you have to download the binary and create a systemd unit with all needed options for it. this will deploy it as an daemonset in a pod avail on each node.
a single instance of an application. k8s does not deploy container directly on a node. the containers are encapsulated into a object called pod. it is the smallest object you can craete in a k8s cluster. pods have an 1to1 relationship with the containers running our application. to scale up your cluster you add additianl pods to your cluster and additional nodes for our pods. what we not do to scale our application is to add more containers to our pods. but you can or must have more containers in our pod. as example: an application needs “helper containers” to. this is helpfull when container stays in direct relationship with another on. so when one pod gets updated the other one does too, same as when delete or upscale. these booth containers as example share the same network namespace and storage. multiple container in a pod are rare usecases.
this example shows how to create a pod using cli
> kubectl run nginx --image nginx
this example shows how to create a pod using a yml file.
apiVersion: v1 kind: Pod metadata: name: myapp-pod labels: apps: myapp type: front-end spec: containers: - name: nginx-container image: nginx
metadatak8s accept only pre defined entrys.
labelsyou can define as much as you like.
to run this yml use
kubectl create -f my-pod.yml
to check the pod use
kubectl describe pod myapp-pod
if you run kubectl
applyit doesn’t matter - they do the same
the rp take care of our deployment or our pod. it can scale the pod or ensure that a given value of instances is available. how ever. it is the older specification of controllers. the new recommended way is to use the successor which is called
rs is very similar to
rc. instead of rc - rs can also manage pods which are not created as a part of the replication. replicasets can be scaled by label which makes the usage by many pods very handy.
to update an rs you can use:
kubectl replace -f foo.yml
or use the scale command:
kubectl scale --replicas=6 -f foo.yml
deployments stays higher then replicasets which stays higher then pods which stays hihger than containers. deployments are usefull to make usage of rolling upgrades since they instruct replicasets to ensure a given number of pods are avail. so if we upgrade our pods - or better the container inside of the pods - with the rolling upgrade strategy and something goes wrong so that the pod won’t came up again - we are not losing our availabillity since the deployment brings pods down and start the new ones one by another and the rs take of our replications we ensure that a given number of pods are always available.
per default k8s creates a few namesspaces. one of them is the
default namespace in which we run our whole deployment. a other one which is created by k8s is the
kube-system namespace in which run all core parts of k8s - this prevents an accidently deletion of our whole setup - a third one is called
kube-public in which where ressources that should be made avail to all users.
on bigger installations we can make usage of more then the default namespace to create isolated environments like dev, staging and production. so while working on dev you cannot accidentally modify ressources in production. you can call from one ns to another by append the name of the ns to the hostname you want to call. in the same ns you call other pods by there hostnames only. example address:
to start a deployment or a single pod in another ns just append
--namespace=dev as example to the end of the
kubectl create command. you can also do this by adding a
namespace: dev under the meta section like
labels are in a definition file.
... metadata: name: myapp-deployment namespace: dev labels: app: myapp type: front-end ...
to create a namespace write a config for it
apiVersion: v1 kind: Namespace metadata: name: dev
or just do a create command
> kubectl create namespace dev
you can also make usage of quotas in a namespace. to do this you need to create a
hard entry under the
specs section in which are all limits listed.
services enable communication betweeen various components in- and outside of the application. you can connect applications with each other, front to backend - expose application to the web or linked with other services like databases.