【Kubernetes】k8s入门及使用(从零开始做实例)
总之,Pod 的启动流程是一个复杂的过程,涉及到 Pod 的创建、调度、容器创建、生命周期管理、容器状态监控和清理等多个方面。副本控制器replicaSet(rs): 作用就是监控pod副本的数量,如果某个node节点挂了,这个节点上的pod也会挂了,这个时候,副本控制器就会在其他的node节点上启动新的pod,数量总数达到副本控制器当时设置的数量。如果 Pod 包含多个容器,则会依次创建每个容器
目录
1. 需求分析
1.1 选择安装方式
1.minikube
2.使用kubeadm 是k8s官方推荐的安装k8s的方式 (推荐)
3.二进制安装
4.第3方的部署工具: rancher等
今天我们选择比较具有实用性的kubeadm的方式进行k8s的安装和部署。
1.2 集群的架构
1.单master多node
2.多master多node ——高可用( 3个master 3个node 1台负载均衡(nginx))
介于个人的硬件配置限制,今天进行第1种架构,希望以后有机会有能力和资源,我再来玩第二种架构。
1.3 实验环境
软件: CentOS 7.9 、Docker
硬件:2G/2C
1个master,2个node
2. 详细安装步骤(每台机器都要做!)
2.1 准备好三台虚拟机
1.重新创建虚拟机(可以先创建一台,再以此克隆两台,注意改名字)
2.配置静态ip
配置ip地址:vi /etc/sysconfig/network-scripts/ifcfg-ens33
配置好后,刷新网络服务:service network restart
3.改名字
hostnamectl set-hostname xxx
su - root
xxx:名字
su - root:重新登陆,切换刷新名字
jdmaster 192.168.1.7
jdnode-1 192.168.1.8
jdnode-2 192.168.1.9
使用固定的ip地址,防止后面因为ip地址的变化,导致整个集群异常。
2.2 关闭selinux和firewalld
1.这些步骤三台机器都是相同的,所以用XShell登入后,用一个工具,提高我们的操作效率(只需要在一台机器输入指令即可使三台机器执行相关指令)
2.关闭selinux和firewalld:
(1).永久关闭selinux:
vim /etc/selinux/config
SELINUX=disabled
(2).临时关闭selinux
setenforce 0
(3).关闭防火墙:
service firewalld stop
systemctl disable firewalld
(4).顺便升级下所有的能升级的软件,提高系统的安全性
yum update -y
2.3 安装Docker
1.安装yum相关的工具,下载docker-ce.repo文件,执行以下命令
yum remove docker \
docker-client \
docker-client-latest \
docker-common \
docker-latest \
docker-latest-logrotate \
docker-logrotate \
docker-engine
yum install -y yum-utils -y
yum-config-manager \
--add-repo \
https://download.docker.com/linux/centos/docker-ce.repo
2.安装docker-ce软件
执行:
yum install docker-ce docker-ce-cli containerd.io docker-compose-plugin -y
小讲解:
container engine 容器引擎
docker是一个容器管理的软件
docker-ce 是服务器端软件 server
docker-ce-cli 是客户端软件 client
docker-compose-plugin是compose插件,用来批量启动很多容器,在单台机器上 containerd.io 底层用来启动容器的
3.检查安装是否成功
[root@jdmaster ~]# docker version
Client: Docker Engine - Community
Version: 23.0.1
API version: 1.42
Go version: go1.19.5
Git commit: a5ee5b1
Built: Thu Feb 9 19:51:00 2023
OS/Arch: linux/amd64
Context: default
Cannot connect to the Docker daemon at unix:///var/run/docker.sock. Is the docker daemon running?
4.启动docker服务
启动:
systemctl start docker
通过查看进程,看看是否启动成功:
[root@jdmaster ~]# ps aux|grep docker
root 32922 0.1 2.6 1101972 50000 ? Ssl 15:39 0:00 /usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock
root 33051 0.0 0.0 112824 984 pts/0 S+ 15:41 0:00 grep --color=auto docker
5.设置docker服务开机启动
[root@jdmaster ~]# systemctl enable docker
Created symlink from /etc/systemd/system/multi-user.target.wants/docker.service to /usr/lib/systemd/system/docker.service.
2.4 配置Docker使用systemd作为默认Cgroup驱动
每台服务器上都要操作,master和node上都要操作执行下面的脚本,会产生 /etc/docker/daemon.json文件。
执行:
cat <<EOF > /etc/docker/daemon.json
{
"exec-opts": ["native.cgroupdriver=systemd"]
}
EOF
重启docker:
[root@jdnode-1 ~]# systemctl restart docker
查看:
[root@jdnode-1 ~]# cd /etc/docker
[root@jdnode-1 docker]# ls
daemon.json
2.5 关闭swap分区
因为k8s不想使用swap分区来存储数据,使用swap会降低性能。
swapoff -a # 临时关闭
执行:
永久修改:
方法1:
sed -i '/ swap / s/^\(.*\)$/#\1/g' /etc/fstab
方法2:修改/etc/fstab,把SWAP那一行注释即可。
2.6 修改hosts文件
执行:
cat >> /etc/hosts << EOF
192.168.1.7 jdmaster
192.168.1.8 jdnode-1
192.168.1.9 jdnode-2
EOF
[root@jdmaster docker]# cat /etc/hosts
127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4
::1 localhost localhost.localdomain localhost6 localhost6.localdomain6
192.168.1.7 jdmaster
192.168.1.8 jdnode-1
192.168.1.9 jdnode-2
2.7 修改内核参数
修改内核参数,每台机器上(master和node),永久修改 追加到内核会读取的参数文件里。
执行:
cat <<EOF >>/etc/sysctl.conf
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_nonlocal_bind = 1
net.ipv4.ip_forward = 1
vm.swappiness=0
EOF
让内核重新读取数据,加载生效
执行:
sysctl -p
2.8 安装kubeadm,kubelet和kubectl
集群里的每台服务器都需要安装。
kubeadm --》k8s的管理程序–》在master上运行的–》建立整个k8s集群,背后是执行了大量的脚本,帮助我们去启动k8s。
kubelet --》在node节点上用来管理容器的–》管理docker,告诉docker程序去启动容器。管理docker容器的,告诉docker程序去启动pod 一个在集群中每个节点(node)上运行的代理。它保证容器(containers)都 运行在 Pod 中。
kubectl–》在master上用来给node节点发号施令的程序,用来控制node节点的,告诉它们做什么事情的,是命令行操作的工具
2.8.1 添加kubernetes YUM软件源
执行:
cat > /etc/yum.repos.d/kubernetes.repo << EOF
[kubernetes]
name=Kubernetes
baseurl=https://mirrors.aliyun.com/kubernetes/yum/repos/kubernetes-el7-x86_64
enabled=1
gpgcheck=0
repo_gpgcheck=0
gpgkey=https://mirrors.aliyun.com/kubernetes/yum/doc/yum-key.gpg https://mirrors.aliyun.com/kubernetes/yum/doc/rpm-package-key.gpg
EOF
2.8.2 安装并指定版本
最好指定版本,因为1.24的版本默认的容器运行时环境不是docker了。
yum install -y kubelet-1.23.6 kubeadm-1.23.6 kubectl-1.23.6
2.8.3 设置开机自启
因为kubelet是k8s在node节点上的代理,必须开机要运行的。
systemctl enable kubelet
3. 部署Kubernetes Master
3.1 准备coredns:1.8.4的镜像
提前准备coredns:1.8.4的镜像,后面需要使用,需要在每台机器上下载镜像。
执行以下两条命令:
[root@jdmaster docker]# docker pull coredns/coredns:1.8.4
[root@jdmaster docker]# docker tag coredns/coredns:1.8.4 registry.aliyuncs.com/google_containers/coredns:v1.8.4
3.2 初始化
1.初始化操作只在master服务器上执行!!!
执行:
kubeadm init \
--apiserver-advertise-address=192.168.1.7 \
--image-repository registry.aliyuncs.com/google_containers \
--service-cidr=10.1.0.0/16 \
--pod-network-cidr=10.244.0.0/16
小讲解:
192.168.1.7 是master的ip。
–service-cidr string
(Use alternative range of IP address for service VIPs. )(default “10.96.0.0/12”) 服务发布暴露–》dnat
–pod-network-cidr string
( Specify range of IP addresses for the pod network. If set, the control plane will automatically allocate CIDRs for every node.)
2.完成初始化的新建文件和目录的操作,在master上完成。
耐心吧等几分钟,装好之后,按照提示:
执行这三条命令:
mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
[root@jdmaster docker]# mkdir -p $HOME/.kube
[root@jdmaster docker]# sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
[root@jdmaster docker]# sudo chown $(id -u):$(id -g) $HOME/.kube/config
4. node节点部署
1.测试node节点能否和master通信:
[root@jdnode-1 docker]# ping jdmaster
PING jdmaster (192.168.1.7) 56(84) bytes of data.
64 bytes from jdmaster (192.168.1.7): icmp_seq=1 ttl=64 time=1.00 ms
64 bytes from jdmaster (192.168.1.7): icmp_seq=2 ttl=64 time=1.59 ms
64 bytes from jdmaster (192.168.1.7): icmp_seq=3 ttl=64 time=1.87 ms
^C
--- jdmaster ping statistics ---
3 packets transmitted, 3 received, 0% packet loss, time 2004ms
rtt min/avg/max/mdev = 1.005/1.492/1.875/0.365 ms
2.执行:
[root@jdnode-1 docker]# kubeadm join 192.168.1.7:6443 --token xv2cjr.d0win422go1bf2km \
> --discovery-token-ca-cert-hash sha256:7a2c5fcf9acd321a0bccd13333e3430004e158988b272b60459b1cf6ed48dea0
[preflight] Running pre-flight checks
[WARNING SystemVerification]: this Docker version is not on the list of validated versions: 23.0.1. Latest validated version: 20.10
[preflight] Reading configuration from the cluster...
[preflight] FYI: You can look at this config file with 'kubectl -n kube-system get cm kubeadm-config -o yaml'
[kubelet-start] Writing kubelet configuration to file "/var/lib/kubelet/config.yaml"
[kubelet-start] Writing kubelet environment file with flags to file "/var/lib/kubelet/kubeadm-flags.env"
[kubelet-start] Starting the kubelet
[kubelet-start] Waiting for the kubelet to perform the TLS Bootstrap...
This node has joined the cluster:
* Certificate signing request was sent to apiserver and a response was received.
* The Kubelet was informed of the new secure connection details.
Run 'kubectl get nodes' on the control-plane to see this node join the cluster.
3.所有的node节点都需要加入到k8s集群里,查看集群里的机器:
[root@jdmaster docker]# kubectl get node
NAME STATUS ROLES AGE VERSION
jdmaster NotReady control-plane,master 15m v1.23.6
jdnode-1 NotReady <none> 2m33s v1.23.6
jdnode-2 NotReady <none> 2m33s v1.23.6
NotReady 说明master和node节点之间的通信还是有问题的,容器之间通信还没有准备好
5. 安装网络插件flannel(在master节点执行)
网络插件flannel实现master上的pod和node节点上的pod之间通信。
k8s里的网络插件:作用就是实现不同的宿主机之间的pod的通信
1.flannel—overlay
2.calico
注意:k8s在不停的升级更新,我们所使用的组件也需要使用比较新的版本,不然会导致安装和使用的过程出现异常!!!
需要索要kube-flannel.yaml 配置文件,代码太长。下载最新版本的flannel网络插件:https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
执行:
kubectl apply -f kube-flannel.yml
过程:
[root@jdmaster ~]# kubectl apply -f kube-flannel.yml
namespace/kube-flannel created
clusterrole.rbac.authorization.k8s.io/flannel created
clusterrolebinding.rbac.authorization.k8s.io/flannel created
serviceaccount/flannel created
configmap/kube-flannel-cfg created
daemonset.apps/kube-flannel-ds created
root@jdmaster ~]# kubectl get node
NAME STATUS ROLES AGE VERSION
jdmaster Ready control-plane,master 140m v1.23.6
jdnode-1 Ready <none> 127m v1.23.6
jdnode-2 Ready <none> 127m v1.23.6
[root@jdmaster ~]# kubectl get ns
NAME STATUS AGE
default Active 140m
kube-flannel Active 81s
kube-node-lease Active 140m
kube-public Active 140m
kube-system Active 140m
[root@jdmaster ~]# kubectl get pod -n kube-system
NAME READY STATUS RESTARTS AGE
coredns-6d8c4cb4d-cdvnk 0/1 ContainerCreating 0 140m
coredns-6d8c4cb4d-s6tjq 0/1 ContainerCreating 0 140m
etcd-jdmaster 1/1 Running 0 140m
kube-apiserver-jdmaster 1/1 Running 0 140m
kube-controller-manager-jdmaster 1/1 Running 0 140m
kube-proxy-6k7r8 1/1 Running 0 127m
kube-proxy-jplmn 1/1 Running 0 140m
kube-proxy-pdjqm 1/1 Running 0 127m
kube-scheduler-jdmaster 1/1 Running 0 140m
[root@jdmaster ~]# kubectl get pod -n kube-flannel
NAME READY STATUS RESTARTS AGE
kube-flannel-ds-9h229 0/1 Init:1/2 0 50s
kube-flannel-ds-x44k8 0/1 Init:1/2 0 50s
kube-flannel-ds-zh298 0/1 Init:1/2 0 50s
[root@jdmaster ~]# kubectl get pod -n kube-flannel -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
kube-flannel-ds-9h229 1/1 Running 0 5m4s 192.168.1.7 jdmaster <none> <none>
kube-flannel-ds-x44k8 1/1 Running 0 5m4s 192.168.1.9 jdnode-2 <none> <none>
kube-flannel-ds-zh298 1/1 Running 0 5m4s 192.168.1.8 jdnode-1 <none> <none>
命名空间: namespace 用来做资源隔离的
default 是默认存放业务pod的,业务pod在创建的时候,可以自己去指定到那个命名空间,如果不指定就会在default
6 使用pod
6.1 使用pod(一)
deployment 控制器:专门负责在k8s里安装部署pod。
kubectl create deployment 创建部署控制器:
举个栗子:
kubectl create deployment k8s-nginx --image=nginx -r 8
k8s-nginx 是控制器的名字
–image=nginx 指定控制器去启动pod使用的镜像
-r 8 启动8个nginx的pod
-r, --replicas=1: Number of replicas to create. Default is 1.
副本控制器replicaSet(rs): 作用就是监控pod副本的数量,如果某个node节点挂了,这个节点上的pod也会挂了,这个时候,副本控制器就会在其他的node节点上启动新的pod,数量总数达到副本控制器当时设置的数量 。即,高可用。
[root@jdmaster ~]# kubectl create deployment k8s-nginx --image=nginx -r 4
deployment.apps/k8s-nginx created
[root@jdmaster ~]# kubectl get pod -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
k8s-nginx-6d779d947c-6ndll 1/1 Running 0 26s 10.244.1.5 jdnode-2 <none> <none>
k8s-nginx-6d779d947c-f2ngw 1/1 Running 0 26s 10.244.1.6 jdnode-2 <none> <none>
k8s-nginx-6d779d947c-jhl5t 1/1 Running 0 26s 10.244.2.5 jdnode-1 <none> <none>
k8s-nginx-6d779d947c-xzm9x 1/1 Running 0 26s 10.244.2.4 jdnode-1 <none> <none>
若要删除pod:
[root@scmaster flannel]# kubectl delete deployment k8s-nginx
deployment.apps "k8s-nginx" deleted
[root@scmaster flannel]# kubectl get pod
No resources found in default namespace.
[root@scmaster flannel]#
6.2 使用pod(二)
一个简单示例
[root@jdmaster pod]# vim nginx.yaml
内容如下:
apiVersion: v1
kind: Pod
metadata:
name: jdnginx
spec:
containers:
- name: nginx
image: nginx:1.14.2
ports:
- containerPort: 80
启动pod:
[root@jdmaster pod]# kubectl apply -f nginx.yaml
pod/jdnginx created
[root@jdmaster pod]# kubectl get pod -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
jdnginx 1/1 Running 0 2m8s 10.244.2.6 jdnode-1 <none> <none>
进入容器内部:
[root@jdmaster pod]# kubectl exec -it jdnginx -- bash
root@jdnginx:/#
root@jdnginx:/# exit
exit
7. 流程详解
Pod 是 Kubernetes 中最小的可部署单元,通常包含一个或多个容器。Pod 的启动流程通常可以分为以下几个步骤:
创建 Pod:通过 Kubernetes API 或命令行工具创建 Pod 对象,并指定 Pod 的名称、标签、容器等信息。
Pod 调度:Kubernetes 调度器会将 Pod 调度到集群中的某个节点上。调度器会考虑节点的资源、标签、Pod 的需求等因素,选择最合适的节点。
创建容器:一旦 Pod 被调度到节点上,Kubernetes 就会创建容器并启动应用程序。如果 Pod 包含多个容器,则会依次创建每个容器。
Pod 生命周期:Pod 有三种生命周期阶段,分别是 Pending、Running 和 Succeeded/Failed。在 Pending 阶段,Kubernetes 正在为 Pod 分配资源。在 Running 阶段,Pod 中的容器正在运行。在 Succeeded/Failed 阶段,Pod 中的所有容器已经完成或失败。
容器状态:在 Pod 运行期间,Kubernetes 会监控容器的状态,例如容器的运行状态、资源使用情况、日志输出等信息。如果容器出现故障或崩溃,Kubernetes 会自动重启容器。
Pod 清理:当一个 Pod 不再需要时,Kubernetes 会自动清理 Pod 对象及其关联的资源,例如容器、存储卷等。
总之,Pod 的启动流程是一个复杂的过程,涉及到 Pod 的创建、调度、容器创建、生命周期管理、容器状态监控和清理等多个方面。Kubernetes 提供了丰富的工具和功能,可以帮助用户轻松地管理和部署 Pod,提高应用程序的可用性和稳定性。
8. 可发布的案例(可访问的serevice)
启动pod,然后创建service发布出去
第一大步:
[root@jdmaster pod]# vim my_nginx.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: my-nginx
spec:
selector:
matchLabels:
run: my-nginx
replicas: 3
template:
metadata:
labels:
run: my-nginx
spec:
containers:
- name: my-nginx
image: nginx
ports:
- containerPort: 80
[root@jdmaster pod]# kubectl apply -f my_nginx.yaml
deployment.apps/my-nginx created
[root@jdmaster pod]# kubectl get pod
NAME READY STATUS RESTARTS AGE
jdnginx 1/1 Running 0 128m
k8s-nginx-6d779d947c-6ndll 1/1 Running 0 146m
k8s-nginx-6d779d947c-f2ngw 1/1 Running 0 146m
k8s-nginx-6d779d947c-jhl5t 1/1 Running 0 146m
k8s-nginx-6d779d947c-xzm9x 1/1 Running 0 146m
my-nginx-cf54cdbf7-4lcx4 1/1 Running 0 8s
my-nginx-cf54cdbf7-b6tw7 1/1 Running 0 8s
my-nginx-cf54cdbf7-fh5ws 0/1 ContainerCreating 0 8s
[root@jdmaster pod]#
第二大步:
[root@jdmaster pod]# vim my_service.yaml
apiVersion: v1
kind: Service
metadata:
name: my-nginx
labels:
run: my-nginx
spec:
type: NodePort
ports:
- port: 8080
targetPort: 80
protocol: TCP
name: http
selector:
run: my-nginx
[root@jdmaster pod]# kubectl apply -f my_service.yaml
service/my-nginx created
[root@jdmaster pod]# kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.1.0.1 <none> 443/TCP 5h25m
my-nginx NodePort 10.1.162.15 <none> 8080:32581/TCP 100s
访问发布的pod
我们只要随便访问k8s集群里的任何一台node节点服务器,包括master
浏览器访问 http://192.168.1.7:32581
访问 http://192.168.1.8:32581
访问 http://192.168.1.5:32581(尽管master没有启动pod,引出负载均衡)
都访问成功:
更多推荐
所有评论(0)