Kubernetes detailed tutorial - Introduction to actual combat

4. Introduction to actual combat

This chapter describes how to deploy and access an nginx service in a kubernetes cluster.

4.1 Namespace

Namespace is a very important resource in kubernetes system. Its main function is to realize resource isolation of multiple environments or multi tenant resources.

By default, all pods in the kubernetes cluster can access each other. However, in practice, you may not want two pods to access each other. At this time, you can divide the two pods into different namespaces. Kubernetes can form logical "groups" by allocating resources in the cluster to different namespaces, so as to facilitate the isolated use and management of resources in different groups.

Different namespace s can be managed by different tenants through the authorization mechanism of kubernetes, so as to realize multi tenant resource isolation. At this time, the resource quota mechanism of kubernetes can be combined to limit the resources that can be occupied by different tenants, such as CPU usage, memory usage, etc., so as to realize the management of available resources for tenants.

kubernetes will create several namespace s by default after the cluster is started

[root@master ~]# kubectl  get namespace
NAME              STATUS   AGE
default           Active   45h     #  All objects that do not specify a Namespace are assigned in the default Namespace
kube-node-lease   Active   45h     #  The heartbeat maintenance between cluster nodes is introduced in v1.13
kube-public       Active   45h     #  Resources under this namespace can be accessed by everyone (including unauthenticated users)
kube-system       Active   45h     #  All resources created by the Kubernetes system are in this namespace

Let's look at the specific operations of the namespace resource:

4.1.1 view
# 1 view all ns commands: kubectl get ns
[root@master ~]# kubectl get ns
NAME              STATUS   AGE
default           Active   45h
kube-node-lease   Active   45h
kube-public       Active   45h     
kube-system       Active   45h     

# 2 view the specified ns command: kubectl get ns name
[root@master ~]# kubectl get ns default
NAME      STATUS   AGE
default   Active   45h

# 3 specify output format command: kubectl get ns name - o format parameter
# kubernetes supports many formats, such as wide, json and yaml
[root@master ~]# kubectl get ns default -o yaml
apiVersion: v1
kind: Namespace
metadata:
  creationTimestamp: "2021-05-08T04:44:16Z"
  name: default
  resourceVersion: "151"
  selfLink: /api/v1/namespaces/default
  uid: 7405f73a-e486-43d4-9db6-145f1409f090
spec:
  finalizers:
  - kubernetes
status:
  phase: Active
  
# 4. View ns details command: kubectl describe ns name
[root@master ~]# kubectl describe ns default
Name:         default
Labels:       <none>
Annotations:  <none>
Status:       Active  # Active namespace in use Terminating deleting namespace

# ResourceQuota resource restrictions for namespace
# LimitRange is the resource limit for each component in the namespace
No resource quota.
No LimitRange resource.
4.1.2 create
# Create namespace
[root@master ~]# kubectl create ns dev
namespace/dev created
4.1.3 deletion
# Delete namespace
[root@master ~]# kubectl delete ns dev
namespace "dev" deleted
4.1.4 configuration mode

First, prepare a yaml file: ns-dev.yaml

apiVersion: v1
kind: Namespace
metadata:
  name: dev

Then you can execute the corresponding create and delete commands:

Create: kubectl create - f ns dev.yaml

Delete: kubectl delete - f ns dev.yaml

4.2 Pod

Pod is the smallest unit for kubernetes cluster management. The program must be deployed in the container to run, and the container must exist in pod.

A Pod can be considered as a package of containers. One or more containers can exist in a Pod.

After kubernetes starts the cluster, all components in the cluster also run in Pod mode. You can view it with the following command:

[root@master ~]# kubectl get pod -n kube-system
NAMESPACE     NAME                             READY   STATUS    RESTARTS   AGE
kube-system   coredns-6955765f44-68g6v         1/1     Running   0          2d1h
kube-system   coredns-6955765f44-cs5r8         1/1     Running   0          2d1h
kube-system   etcd-master                      1/1     Running   0          2d1h
kube-system   kube-apiserver-master            1/1     Running   0          2d1h
kube-system   kube-controller-manager-master   1/1     Running   0          2d1h
kube-system   kube-flannel-ds-amd64-47r25      1/1     Running   0          2d1h
kube-system   kube-flannel-ds-amd64-ls5lh      1/1     Running   0          2d1h
kube-system   kube-proxy-685tk                 1/1     Running   0          2d1h
kube-system   kube-proxy-87spt                 1/1     Running   0          2d1h
kube-system   kube-scheduler-master            1/1     Running   0          2d1h
4.2.1 create and run

kubernetes does not provide the command to run Pod separately, but is implemented through the Pod controller

# Command format: kubectl run (pod controller name) [parameter] 
# --Image specifies the image of the Pod
# --Port specifies the port
# --Namespace specifies the namespace
[root@master ~]# kubectl run nginx --image=nginx:latest --port=80 --namespace dev 
deployment.apps/nginx created
4.2.2 viewing pod information
# View Pod basic information
[root@master ~]# kubectl get pods -n dev
NAME    READY   STATUS    RESTARTS   AGE
nginx   1/1     Running   0          43s

# View Pod details
[root@master ~]# kubectl describe pod nginx -n dev
Name:         nginx
Namespace:    dev
Priority:     0
Node:         node1/192.168.5.4
Start Time:   Wed, 08 May 2021 09:29:24 +0800
Labels:       pod-template-hash=5ff7956ff6
              run=nginx
Annotations:  <none>
Status:       Running
IP:           10.244.1.23
IPs:
  IP:           10.244.1.23
Controlled By:  ReplicaSet/nginx
Containers:
  nginx:
    Container ID:   docker://4c62b8c0648d2512380f4ffa5da2c99d16e05634979973449c98e9b829f6253c
    Image:          nginx:latest
    Image ID:       docker-pullable://nginx@sha256:485b610fefec7ff6c463ced9623314a04ed67e3945b9c08d7e53a47f6d108dc7
    Port:           80/TCP
    Host Port:      0/TCP
    State:          Running
      Started:      Wed, 08 May 2021 09:30:01 +0800
    Ready:          True
    Restart Count:  0
    Environment:    <none>
    Mounts:
      /var/run/secrets/kubernetes.io/serviceaccount from default-token-hwvvw (ro)
Conditions:
  Type              Status
  Initialized       True
  Ready             True
  ContainersReady   True
  PodScheduled      True
Volumes:
  default-token-hwvvw:
    Type:        Secret (a volume populated by a Secret)
    SecretName:  default-token-hwvvw
    Optional:    false
QoS Class:       BestEffort
Node-Selectors:  <none>
Tolerations:     node.kubernetes.io/not-ready:NoExecute for 300s
                 node.kubernetes.io/unreachable:NoExecute for 300s
Events:
  Type    Reason     Age        From               Message
  ----    ------     ----       ----               -------
  Normal  Scheduled  <unknown>  default-scheduler  Successfully assigned dev/nginx-5ff7956ff6-fg2db to node1
  Normal  Pulling    4m11s      kubelet, node1     Pulling image "nginx:latest"
  Normal  Pulled     3m36s      kubelet, node1     Successfully pulled image "nginx:latest"
  Normal  Created    3m36s      kubelet, node1     Created container nginx
  Normal  Started    3m36s      kubelet, node1     Started container nginx
4.2.3 accessing Pod
# Get podIP
[root@master ~]# kubectl get pods -n dev -o wide
NAME    READY   STATUS    RESTARTS   AGE    IP             NODE    ... 
nginx   1/1     Running   0          190s   10.244.1.23   node1   ...

#Access POD
[root@master ~]# curl http://10.244.1.23:80
<!DOCTYPE html>
<html>
<head>
	<title>Welcome to nginx!</title>
</head>
<body>
	<p><em>Thank you for using nginx.</em></p>
</body>
</html>
4.2.4 delete specified Pod
# Delete specified Pod
[root@master ~]# kubectl delete pod nginx -n dev
pod "nginx" deleted

# At this point, it is displayed that the Pod was deleted successfully, but after querying again, it is found that a new one has been generated 
[root@master ~]# kubectl get pods -n dev
NAME    READY   STATUS    RESTARTS   AGE
nginx   1/1     Running   0          21s

# This is because the current Pod is created by the Pod controller. The controller will monitor the Pod status. Once the Pod is found dead, it will be rebuilt immediately
# To delete the Pod, you must delete the Pod controller

# Let's first query the Pod controller in the current namespace
[root@master ~]# kubectl get deploy -n  dev
NAME    READY   UP-TO-DATE   AVAILABLE   AGE
nginx   1/1     1            1           9m7s

# Next, delete this PodPod controller
[root@master ~]# kubectl delete deploy nginx -n dev
deployment.apps "nginx" deleted

# Wait a moment, then query the Pod and find that the Pod has been deleted
[root@master ~]# kubectl get pods -n dev
No resources found in dev namespace.
4.2.5 configuration operation

Create a pod-nginx.yaml as follows:

apiVersion: v1
kind: Pod
metadata:
  name: nginx
  namespace: dev
spec:
  containers:
  - image: nginx:latest
    name: pod
    ports:
    - name: nginx-port
      containerPort: 80
      protocol: TCP

Then you can execute the corresponding create and delete commands:

Create: kubectl create -f pod-nginx.yaml

Delete: kubectl delete -f pod-nginx.yaml

4.3 Label

Label is an important concept in kubernetes system. Its function is to add identification on resources to distinguish and select them.

Features of Label:

  • A Label will be attached to various objects in the form of key/value pairs, such as Node, Pod, Service, etc
  • A resource object can define any number of labels, and the same Label can also be added to any number of resource objects
  • The Label is usually determined when the resource object is defined. Of course, it can also be dynamically added or deleted after the object is created

Multi dimensional grouping of resources can be realized through Label, so that resource allocation, scheduling, configuration, deployment and other management can be carried out flexibly and conveniently.

Some common Label examples are as follows:

  • Version label: "version": "release", "version": "stable"
  • Environment label: "environment": "dev", "environment": "test", "environment": "pro"
  • Schema label: "tier": "frontend", "tier": "backend"

After the label is defined, the label selection should also be considered, which requires the use of the Label Selector, namely:

Label is used to define an identity for a resource object

Label Selector is used to query and filter resource objects with certain labels

There are currently two types of label selectors:

  • Equation based Label Selector

    name = slave: select all objects with key="name" and value="slave" in the Label

    env != production: select all objects including key="env" in Label and whose value is not equal to "production"

  • Collection based Label Selector

    name in (master, slave): select all objects with key="name" and value="master" or "slave" in the Label

    name not in (frontend): select all objects that contain key="name" in Label and whose value is not equal to "frontend"

Multiple label selectors can be used for label selection. In this case, multiple label selectors can be combined and separated by comma "," and ". For example:

name=slave,env!=production

name not in (frontend),env!=production

4.3.1 command mode
# Tag pod resources
[root@master ~]# kubectl label pod nginx-pod version=1.0 -n dev
pod/nginx-pod labeled

# Update tags for pod resources
[root@master ~]# kubectl label pod nginx-pod version=2.0 -n dev --overwrite
pod/nginx-pod labeled

# View label
[root@master ~]# kubectl get pod nginx-pod  -n dev --show-labels
NAME        READY   STATUS    RESTARTS   AGE   LABELS
nginx-pod   1/1     Running   0          10m   version=2.0

# Filter Tags
[root@master ~]# kubectl get pod -n dev -l version=2.0  --show-labels
NAME        READY   STATUS    RESTARTS   AGE   LABELS
nginx-pod   1/1     Running   0          17m   version=2.0
[root@master ~]# kubectl get pod -n dev -l version!=2.0 --show-labels
No resources found in dev namespace.

#delete a tap
[root@master ~]# kubectl label pod nginx-pod version- -n dev
pod/nginx-pod labeled
4.3.2 configuration mode
apiVersion: v1
kind: Pod
metadata:
  name: nginx
  namespace: dev
  labels:
    version: "3.0" 
    env: "test"
spec:
  containers:
  - image: nginx:latest
    name: pod
    ports:
    - name: nginx-port
      containerPort: 80
      protocol: TCP

Then you can execute the corresponding update command: kubectl apply -f pod-nginx.yaml

4.4 Deployment

In kubernetes, pod is the smallest control unit, but kubernetes rarely directly controls pod, which is generally completed through pod controller. The pod controller is used for pod management to ensure that the pod resources meet the expected state. When the pod resources fail, it will try to restart or rebuild the pod.

There are many types of Pod controllers in kubernetes. This chapter only introduces one: Deployment.

4.4.1 command operation
# Command format: kubectl create deployment name [parameter] 
# --Image specifies the image of the pod
# --Port specifies the port
# --replicas specifies the number of created pod s
# --Namespace specifies the namespace
[root@master ~]# kubectl run nginx --image=nginx:latest --port=80 --replicas=3 -n dev
deployment.apps/nginx created

# View the created Pod
[root@master ~]# kubectl get pods -n dev
NAME                     READY   STATUS    RESTARTS   AGE
nginx-5ff7956ff6-6k8cb   1/1     Running   0          19s
nginx-5ff7956ff6-jxfjt   1/1     Running   0          19s
nginx-5ff7956ff6-v6jqw   1/1     Running   0          19s

# View deployment information
[root@master ~]# kubectl get deploy -n dev
NAME    READY   UP-TO-DATE   AVAILABLE   AGE
nginx   3/3     3            3           2m42s

# UP-TO-DATE: number of copies successfully upgraded
# AVAILABLE: number of AVAILABLE copies
[root@master ~]# kubectl get deploy -n dev -o wide
NAME    READY UP-TO-DATE  AVAILABLE   AGE     CONTAINERS   IMAGES              SELECTOR
nginx   3/3     3         3           2m51s   nginx        nginx:latest        run=nginx

# View deployment details
[root@master ~]# kubectl describe deploy nginx -n dev
Name:                   nginx
Namespace:              dev
CreationTimestamp:      Wed, 08 May 2021 11:14:14 +0800
Labels:                 run=nginx
Annotations:            deployment.kubernetes.io/revision: 1
Selector:               run=nginx
Replicas:               3 desired | 3 updated | 3 total | 3 available | 0 unavailable
StrategyType:           RollingUpdate
MinReadySeconds:        0
RollingUpdateStrategy:  25% max unavailable, 25% max surge
Pod Template:
  Labels:  run=nginx
  Containers:
   nginx:
    Image:        nginx:latest
    Port:         80/TCP
    Host Port:    0/TCP
    Environment:  <none>
    Mounts:       <none>
  Volumes:        <none>
Conditions:
  Type           Status  Reason
  ----           ------  ------
  Available      True    MinimumReplicasAvailable
  Progressing    True    NewReplicaSetAvailable
OldReplicaSets:  <none>
NewReplicaSet:   nginx-5ff7956ff6 (3/3 replicas created)
Events:
  Type    Reason             Age    From                   Message
  ----    ------             ----   ----                   -------
  Normal  ScalingReplicaSet  5m43s  deployment-controller  Scaled up replicaset nginx-5ff7956ff6 to 3
  
# delete 
[root@master ~]# kubectl delete deploy nginx -n dev
deployment.apps "nginx" deleted
4.4.2 configuration operation

Create a deploy-nginx.yaml as follows:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx
  namespace: dev
spec:
  replicas: 3
  selector:
    matchLabels:
      run: nginx
  template:
    metadata:
      labels:
        run: nginx
    spec:
      containers:
      - image: nginx:latest
        name: nginx
        ports:
        - containerPort: 80
          protocol: TCP

Then you can execute the corresponding create and delete commands:

Create: kubectl create -f deploy-nginx.yaml

Delete: kubectl delete -f deploy-nginx.yaml

4.5 Service

Through the previous lesson, we have been able to use Deployment to create a group of pods to provide services with high availability.

Although each Pod is assigned a separate Pod IP, there are two problems:

  • Pod IP will change with the reconstruction of pod
  • Pod IP is only a virtual IP visible in the cluster and cannot be accessed externally

This makes it difficult to access the Service. Therefore, kubernetes designed Service to solve this problem.

Service can be regarded as a group of external access interfaces of similar pods. With the help of service, applications can easily realize service discovery and load balancing.

4.5.1 create accessible services within the cluster
# Expose Service
[root@master ~]# kubectl expose deploy nginx --name=svc-nginx1 --type=ClusterIP --port=80 --target-port=80 -n dev
service/svc-nginx1 exposed

# View service
[root@master ~]# kubectl get svc svc-nginx1 -n dev -o wide
NAME         TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)   AGE     SELECTOR
svc-nginx1   ClusterIP   10.109.179.231   <none>        80/TCP    3m51s   run=nginx

# A CLUSTER-IP is generated here, which is the IP of the service. This address will not change during the service life cycle
# You can access the POD corresponding to the current service through this IP
[root@master ~]# curl 10.109.179.231:80
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
</head>
<body>
<h1>Welcome to nginx!</h1>
.......
</body>
</html>
4.5.2 create a Service that can also be accessed outside the cluster
# The type of the Service created above is ClusterIP. This ip address is accessible only within the cluster
# If you need to create a Service that can also be accessed externally, you need to modify the type to NodePort
[root@master ~]# kubectl expose deploy nginx --name=svc-nginx2 --type=NodePort --port=80 --target-port=80 -n dev
service/svc-nginx2 exposed

# At this time, you will find that a Service of NodePort type appears, and there is a pair of ports (80:31928/TC)
[root@master ~]# kubectl get svc  svc-nginx2  -n dev -o wide
NAME          TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)        AGE    SELECTOR
svc-nginx2    NodePort    10.100.94.0      <none>        80:31928/TCP   9s     run=nginx

# Next, you can access the node IP:31928 to access the service through the host outside the cluster
# For example, access the following address through a browser on the host computer
http://192.168.90.100:31928/
4.5.3 delete Service
[root@master ~]# kubectl delete svc svc-nginx-1 -n dev 
service "svc-nginx-1" deleted
4.5.4 configuration mode

Create an svc-nginx.yaml as follows:

apiVersion: v1
kind: Service
metadata:
  name: svc-nginx
  namespace: dev
spec:
  clusterIP: 10.109.179.231 #Fixed svc intranet ip
  ports:
  - port: 80
    protocol: TCP
    targetPort: 80
  selector:
    run: nginx
  type: ClusterIP

Then you can execute the corresponding create and delete commands:

Create: kubectl create -f svc-nginx.yaml

Delete: kubectl delete -f svc-nginx.yaml

Summary

So far, you have mastered the basic operations of Namespace, Pod, Deployment and Service resources. With these operations, you can realize the simple Deployment and access of a Service in kubernetes cluster. However, if you want to make better use of kubernetes, you need to deeply study the details and principles of these resources.

Keywords: Docker Kubernetes Container

Added by richmlpdx on Sun, 28 Nov 2021 19:48:30 +0200