The drill environment of this article is Kubernetes cluster built based on Virtualbox. The specific steps to build the cluster can refer to kubeadm installation Kubernetes V1.11.1

1. Basic concepts

1.1 What is a Pod

Pod is the smallest unit that can be created and deployed in Kubernetes. It is an application instance in Kubernetes cluster and is always deployed on the same Node Node. A Pod contains one or more containers, storage, network, and other resources shared by each container. Pod supports a variety of container environments, with Docker being the most popular.

  • Single-container Pod, the most common application.
  • Multi-container PODS. For multi-container pods, Kubernetes ensures that all containers are running on the same physical or virtual host. Multi-container PODS are a relatively advanced use and are generally not recommended unless the application coupling is extremely severe. Containers within a Pod share IP addresses and port ranges, and containers can access each other via localhost.

Pod does not provide the ability to guarantee normal operation because it may be affected by physical failures of nodes, network partitions, etc. Overall high availability is achieved by Kubernetes cluster by scheduling nodes within the cluster. Usually we don’t create pods directly, we usually manage them through controllers, but it’s good to know about pods to get familiar with controllers.

1.2 Benefits of Pod

Benefits of Pod

  • As a service unit that can run independently, Pod simplifies the difficulty of application deployment and provides great convenience for application deployment management with a higher level of abstraction.
  • As the smallest application instance, Pod can run independently, facilitating deployment, horizontal expansion and contraction, scheduling management, and resource allocation.
  • Containers in Pod share the same data and network address space, and unified resource management and allocation is carried out among PODS.

1.3 Common Pod Management Commands

The Pod configuration information has several important parts, apiVersion, KIND, Metadata, Spec, and Status. ApiVersion and KIND are fixed, and status is the runtime state, so metadata and spec are the most important parts.

Let’s start with a typical configuration file called first-pod.yml

apiVersion: v1
kind: Pod
metadata:
  name: first-pod
  labels:
    app: bash
    tir: backend
spec:
  containers:
  - name: bash-container
    image: docker.io/busybox
    command: ['sh'.'-c'.'echo Hello Kubernetes! && sleep 3600']
Copy the code

When writing configuration files, you can refer to API Reference or view them by running commands.

[root@devops-101 ~]# kubectl explain pod
KIND:     Pod
VERSION:  v1

DESCRIPTION:
     Pod is a collection of containers that can run on a host. This resource is
     created by clients and scheduled onto hosts.

FIELDS:
   apiVersion	<string>
     APIVersion defines the versioned schema of this representation of an
     object. Servers should convert recognized schemas to the latest internal
     value, and may reject unrecognized values. More info:
     https://git.k8s.io/community/contributors/devel/api-conventions.md#resources

   kind	<string>
     Kind is a string value representing the REST resource this object
     represents. Servers may infer this from the endpoint the client submits
     requests to. Cannot be updated. In CamelCase. More info:
     https://git.k8s.io/community/contributors/devel/api-conventions.md#types-kinds

   metadata	<Object>
     Standard object's metadata. More info:
     https://git.k8s.io/community/contributors/devel/api-conventions.md#metadata

   spec	<Object>
     Specification of the desired behavior of the pod. More info:
     https://git.k8s.io/community/contributors/devel/api-conventions.md#spec-and-status

   status	<Object>
     Most recently observed status of the pod. This data may not be up to date.
     Populated by the system. Read-only. More info:
     https://git.k8s.io/community/contributors/devel/api-conventions.md#spec-and-status
[root@devops-101 ~]# kubectl explain pod.spec
KIND:     Pod
VERSION:  v1

RESOURCE: spec <Object>

DESCRIPTION:
     Specification of the desired behavior of the pod. More info:
     https://git.k8s.io/community/contributors/devel/api-conventions.md#spec-and-status

     PodSpec is a description of a pod.

FIELDS:
   activeDeadlineSeconds	<integer>
     Optional duration in seconds the pod may be active on the node relative to
     StartTime before the system will actively try to mark it failed and kill
     associated containers. Value must be a positive integer.

   affinity	<Object>
     If specified, the pod's scheduling constraints automountServiceAccountToken <boolean> AutomountServiceAccountToken indicates whether a service  account token should be automatically mounted.Copy the code

1.3.1 create

Using the Kubectl command line management tool, we can create directly from the command line through the configuration file. If the Dashboard GUI is installed, you can also create a Pod using the GUI. Since the creation of a Pod is ultimately a command, here is how to create it using the Kubectl administration tool.

Create a Pod using a configuration file.

$ kubectl create -f first-pod.yml 
Copy the code

1.3.2 Viewing the Configuration

If you want to know the configuration of a running Pod, you can use the following command.

[root@devops-101 ~]# kubectl get pod first-pod -o yaml
apiVersion: v1
kind: Pod
metadata:
  creationTimestamp: 2018-08-08T01:45:16Z
  labels:
    app: bash
  name: first-pod
  namespace: default
  resourceVersion: "184988"
  selfLink: /api/v1/namespaces/default/pods/first-pod
  uid: b2d3d2b7-9aac-11e8-84f4-080027b7c4e9
spec:
  containers:
  - command:
    - sh
    - -c
    - echo Hello Kubernetes! && sleep 3600
    image: docker.io/busybox
    imagePullPolicy: Always
    name: bash-container
    resources: {}
    terminationMessagePath: /dev/termination-log
    terminationMessagePolicy: File
    volumeMounts:
    - mountPath: /var/run/secrets/kubernetes.io/serviceaccount
      name: default-token-trvqv
      readOnly: true
  dnsPolicy: ClusterFirst
  nodeName: devops-102
  restartPolicy: Always
  schedulerName: default-scheduler
  securityContext: {}
  serviceAccount: default
  serviceAccountName: default
  terminationGracePeriodSeconds: 30
  tolerations:
  - effect: NoExecute
    key: node.kubernetes.io/not-ready
    operator: Exists
    tolerationSeconds: 300
  - effect: NoExecute
    key: node.kubernetes.io/unreachable
    operator: Exists
    tolerationSeconds: 300
  volumes:
  - name: default-token-trvqv
    secret:
      defaultMode: 420
      secretName: default-token-trvqv
status:
  conditions:
  - lastProbeTime: null
    lastTransitionTime: 2018-08-08T01:45:16Z
    status: "True"
    type: Initialized
  - lastProbeTime: null
    lastTransitionTime: 2018-08-08T01:45:16Z
    message: 'containers with unready status: [bash-container]'
    reason: ContainersNotReady
    status: "False"
    type: Ready
  - lastProbeTime: null
    lastTransitionTime: null
    message: 'containers with unready status: [bash-container]'
    reason: ContainersNotReady
    status: "False"
    type: ContainersReady
  - lastProbeTime: null
    lastTransitionTime: 2018-08-08T01:45:16Z
    status: "True"
    type: PodScheduled
  containerStatuses:
  - image: docker.io/busybox
    imageID: ""
    lastState: {}
    name: bash-container
    ready: falseRestartCount: 0 State: waiting: Reason: ContainerCreating hostIP: 192.168.0.102 Phase: Pending qosClass: BestEffort startTime: 2018-08-08T01:45:16ZCopy the code

1.3.3 Viewing Logs

You can view logs of the command line standard output.

[root@devops-101 ~]# kubectl logs first-pod
Hello Kubernetes!
Copy the code

Kubectl logs pod-name -c container-name kubectl logs pod-name -c container-name

1.3.4 Label Management

Tags are important for Kubernetes to manage pods. They can be specified in the metadata of the Pod Yaml file or managed through the command line.

Displays the Pod label

[root@devops-101 ~]# kubectl get pods --show-labels
NAME        READY     STATUS    RESTARTS   AGE       LABELS
first-pod   1/1       Running   0          15m       app=bash
Copy the code

With second-pod.yml we create a pod with two tags.

[root@devops-101 ~]# kubectl create -f first-pod.yml 
pod/second-pod created
[root@devops-101 ~]# kubectl get pods --show-labels
NAME         READY     STATUS              RESTARTS   AGE       LABELS
first-pod    1/1       Running             0          17m       app=bash
second-pod   0/1       ContainerCreating   0          20s       app=bash,tir=backend
Copy the code

Query pods by label.

[root@devops-101 ~]# kubectl get pods -l tir=backend --show-labels
NAME         READY     STATUS    RESTARTS   AGE       LABELS
second-pod   1/1       Running   0          1m        app=bash,tir=backend
Copy the code

labeling

[root@devops-101 ~]# kubectl label pod first-pod tir=frontend
pod/first-pod labeled
[root@devops-101 ~]# kubectl get pods --show-labels
NAME         READY     STATUS    RESTARTS   AGE       LABELS
first-pod    1/1       Running   0          24m       app=bash,tir=frontend
second-pod   1/1       Running   0          7m        app=bash,tir=backend
Copy the code

Modify the label

[root@devops-101 ~]# kubectl label pod first-pod tir=unkonwn --overwrite
pod/first-pod labeled
[root@devops-101 ~]# kubectl get pods --show-labels
NAME         READY     STATUS    RESTARTS   AGE       LABELS
first-pod    1/1       Running   0          25m       app=bash,tir=unkonwn
second-pod   1/1       Running   0          8m        app=bash,tir=backend
Copy the code

Labels can be displayed as columns

[root@devops-101 ~]# kubectl get pods -L app,tir
NAME         READY     STATUS    RESTARTS   AGE       APP       TIR
first-pod    1/1       Running   0          26m       bash      unkonwn
second-pod   1/1       Running   0          9m        bash      backend
Copy the code

Tags are a very powerful feature in Kubernetes. Node nodes can also add tags. Using Pod’s tag selector, pods can be assigned to different types of Nodes.

1.3.5 delete Pod

[root@devops-101 ~]# kubectl delete pods first-pod
pod "first-pod" deleted
Copy the code

It can also be deleted according to the label selector.

[root@devops-101 ~]# kubectl delete pods -l tir=backend
pod "second-pod" deleted
Copy the code

1.4 Pod life cycle

Like individual container applications, pods are not persistent. After a Pod is created, Kubernetes assigns a UID to it, and it is scheduled to run in Node via Controller. Then the Pod stays running until it finishes running properly or is deleted. In the event of a Node failure, the Controller is responsible for dispatching it to another Node. Kubernetes defines several states for Pod, as follows:

  • Pending, Pod has been created and is waiting for container creation. Often the image is being downloaded, as this is the most time consuming step.
  • Running, the Pod is bound to a Node and Running. Or you may be restarting after an unexpected interruption.
  • Succeeded, indicating that the container in the Pod has ended normally and does not need to be restarted.
  • Failed, which means that the container in the Pod encountered an error and terminated.
  • Unknown: The Pod status cannot be obtained because of network or other reasons.

2. How do I perform a health check on Pod

Kubernetes uses the Handler function to probe the condition of a container in three forms.

  • ExecAction: Executes a specific command in the container.
  • TCPSocketAction: Checks whether container ports can be connected.
  • HTTPGetAction: Checks whether the HTTP request status is normal.

This part of the content is also more expanded, this part of the content refer to the Kubernetes Pod health check.

3. Init Containers

A Pod can contain one to more Init Containers that start running before other containers. Init Container can only be run to completion, that is, it cannot exist forever. Init Containers must be executed in sequence. Before App Container runs, all Init Containers must end properly.

During Pod startup, Init Containers start sequentially after network and storage initialization is complete. When a Pod restarts, all Init Containers are reexecuted.

However, if the Pod restartPolicy is set to Always, the Init Containers use RestartPolicy OnFailure.

3.1 the benefits

  • Run commands or tools that you don’t want to run in App Container
  • Contains some tools or specific code not found in App Image
  • The application image builder and deployer can work independently without relying on each other
  • Have a different namespace than App Container
  • Because the App Container must end before it runs, it is a good time to check and configure some preconditions

3.2 grammar

Let’s take a look at the explanation

[root@devops-101 ~]# kubectl explain pod.spec.initContainers
KIND:     Pod
VERSION:  v1

RESOURCE: initContainers <[]Object>

DESCRIPTION:
     List of initialization containers belonging to the pod. Init containers are
     executed in order prior to containers being started. If any init container
     fails, the pod is considered to have failed and is handled according to its
     restartPolicy. The name for an init container or normal container must be
     unique among all containers. Init containers may not have Lifecycle
     actions, Readiness probes, or Liveness probes. The resourceRequirements of
     an init container are taken into account during scheduling by finding the
     highest request/limit for each resource type, and then using the max of of
     that value or the sum of the normal containers. Limits are applied to init
     containers in a similar fashion. Init containers cannot currently be added
     or removed. Cannot be updated. More info:
     https://kubernetes.io/docs/concepts/workloads/pods/init-containers/

     A single application container that you want to run within a pod.
Copy the code

Concrete syntax.

apiVersion: v1
kind: Pod
metadata:
  name: myapp-pod
  labels:
    app: myapp
spec:
  containers:
  - name: myapp-container
    image: docker.io/busybox
    command: ['sh'.'-c'.'echo The app is running! && sleep 3600']
  initContainers:
  - name: init-myservice
    image: docker.io/busybox
    command: ['sh'.'-c'.'echo init-service && sleep 2']
  - name: init-mydb
    image: docker.io/busybox
    command: ['sh'.'-c'.'echo init-mydb && sleep 2']
Copy the code

Compatibility issues Prior to 1.5 syntax is written in annotations, versions 1.6 and above use the.spec.initcontainers field. You are advised to use the syntax of version 1.6. Versions 1.6 and 1.7 are compatible with versions 1.5 and below, and 1.8 is not compatible with older versions.

4. Pod Preset

You can use this feature to inject password Secrets, store Volumes, Volume Mounts, and environment variables into pods during Pod startup. The Pod is specified through the label selector. With this feature, the maintainer of the Pod Template does not need to provide attributes for each Pod display.

Specific working steps

  • Check all available ProdPresets
  • Check that there is a tag for ProdPreset that matches the Pod to be created
  • Merge the parameters defined in PodPreset with the Pod definition
  • If parameter merging fails, the ProPreset parameter is discarded and the creation of pods continues
  • Add an annotation to Pod that indicates that the layer has been modified by ProdPreset, in the form ofpodpreset.admission.kubernetes.io/podpreset-<pod-preset name>: "<resource version>"

For Env, EnvFrom, and VolumeMounts Kubernetes, modify the Container Spec. For Volume, modify the Pod Spec.

4.1 Disable individual PODS

Add a comment to the Spec:

podpreset.admission.kubernetes.io/exclude: "true"
Copy the code

Interruption of 5.

Pods can break for a variety of reasons.

5.1 Planned interruptions

  • Delete the Deployment or other controllers
  • Pod restart caused by updating the deployment template
  • Delete Pod directly
  • Cluster capacity reduction
  • Manually remove

5.2 Unplanned interruption

  • The hardware is faulty or the physical node is down
  • The cluster administrator deletes VMS by mistake
  • The host is unavailable due to a cloud provider fault
  • Kernel panic
  • The cluster network partition causes the node to disappear
  • Node deletion caused by resource exhaustion

5.3 PDB Disruption Budgets

Kubernetes offers features to help run highly available applications at the same time as frequent voluntary disruptions. We call this set of features Disruption Budgets.

Kubernetes allows us to create a PDB object to ensure that pods running in an RS do not fall under a budget. Eviction API.

The PDB is designed to address the separation of cluster management and application management responsibilities. If this is not the case in your organization, you can dispense with the PDB.

The resources

  1. Pods
  2. Kubernetes in action