最近接触了 Kubernetes 的部署,最早看的是基于 ansible 的部署方案 https://github.com/easzlab/kubeasz,后经 leader 提示改看 rancher,发现 rancher 更加方便,遂作此文以记录。同时,此项目也值得一看 https://github.com/opsnull/follow-me-install-kubernetes-cluster
常用命令
- 查看 Kubernetes 状态
kubectl version
正常应该显示
1 | Client Version: version.Info{Major:"1", Minor:"14", GitVersion:"v1.14.3", GitCommit:"5e53fd6bc17c0dec8434817e69b04a25d8ae0ff0", GitTreeState:"clean", BuildDate:"2019-06-07T09:55:27Z", GoVersion:"go1.12.5", Compiler:"gc", Platform:"darwin/amd64"} |
- 查看所有容器的状态
kubectl get pods --all-namespaces
- 一次性测试工具,可以用于模拟基础容器内的环境,用完会自动删除
kubectl run --generator=run-pod/v1 test --rm -it --image=alpine /bin/sh
发布服务的注意点
硬盘
vSphere 下支持自动创建硬盘,但不支持扩大已经指定好的硬盘大小。因此指定最大硬盘大小时,可以尽可能给大。因为不会全部用完,是按需使用的。实测如果给 10Ti,那么初始会用掉 1Ti,之后缓慢增加
需要在部署 Kubernetes 后,手工创建 StorageClass,具体命令参见 [部署步骤] - [vSphere] 一节
发布需要存储的 docker 服务后,如果想删除,需要手工去 vSphere 的硬盘里自行删除自动创建的硬盘。这是因为 StorageClass 的
reclaimPolicy被设置成了Retain。这是为了避免移除服务时数据被自动清空PersistentVolumeClaim指定的StorageClass应为eudicssd或者eudichdd,具体需要看情况按需使用StatefulSet如果设置了replicas > 1,且配置了volumeClaimTemplates,那么新建的硬盘内是没有任何数据的。如果只是配置了volumeClaim,那么replicas > 1时,第二个 Pod 创建会永远失败,因为目前 vSphere 的硬盘策略是只允许ReadWriteOnce
亲和性调度
对于硬件要求,可用性要求较高的服务,需要配置亲和性调度。避免 Kuberneters 将服务部署到硬件条件不足的 Node 上
Node 不可用后,会在大约5分钟后才调度到新的 Node 上,具体参见 https://kubernetes.io/zh/docs/concepts/architecture/nodes/
gRPC
只能通过 NodePort 部署,不支持 Ingress,但由于 NodePort 的特性是会在每个 worker 上开同样的端口,因此问题不大,可以通过之前在 pfsense 里绑定的域名 test.local 直接访问
NodePort 端口范围: 30000-32767,可以在刚刚的 cloud-config.yml 里修改范围,但最好不要太低
部署
部署机器的最佳实践
1 台运行 rancher 的机器,这台机器里不要部署 Kuberneters,因为 rancher 在部署 Kuberneters 时会新建许多 docker container,导致混乱
3 台 etcd,其中硬盘最好给ssd,内存尽可能给多,因为 Kuberneters 内几乎所有数据都会存放在 etcd 节点里,它是维持高可用的必须条件。这 3 台最好分别位于不同的机器,避免一台主机的停止导致整个 Kuberneters 不可用
2 台 master,最好分别位于不同的机器
若干 worker
部署步骤
vSphere
- 配置 deploy 机器,设定好 deploy 机器的 IP 地址,以及计算机名后,运行脚本
start_deploy.sh,脚本内容如下
1 | ansible-playbook -i ./inventory playbook.yml |
- 通过 ssh 登录到 deploy 机器上,运行以下命令,假设 deploy 机器位于 192.168.1.199
docker run -d --restart=unless-stopped --name=rancher-server --log-driver json-file --log-opt max-size=5g -p 80:80 -p 443:443 -v 192.168.1.199:/var/lib/rancher/ -v /root/var/log/auditlog:/var/log/auditlog -e AUDIT_LEVEL=3 rancher/rancher:v2.2.4
等待一段时间后在内网任意机器上,直接访问 https://192.168.1.199
右上角头像账户 -> Cloud Credentials -> Add Cloud Credential,以下假设 vSphere 的地址为 192.168.1.140
Name:
credential(可任意填)Cloud Credential Type:
VMware vSpherevCenter or ESXi Server:
192.168.1.140Port:
443Username:
***Password:
***
点击
Create右上角头像账户 -> Node Template -> Add Template -> 选择 vSphere
Account Access 选择刚刚创建的
credentialInstance Options
配置按需填写
- Scheduling
这里的填写模式,应该去看 vSphere Client -> Shortcuts -> Global Inventory Lists 里的详细列表。不要看
rancher的提示注意
Host与Pool互斥,写了一个就不要写第二个Folder:
/rancher-k8s(指定虚拟机文件夹,仅是为了方便管理,可以不填)
创建完毕一个
Node Template后,可以按需要 Clone 多个,然后只是微调下硬件配置,或调整 Host 配置,以便达到开设不同硬件类型机器、强制部署不同主机的目的返回
rancher首页,点击Add Cluster,选择vSphere按需设置
Node Pools,注意Name Prefix里不可以带下划线,建议使用rancher-k8s-worker、rancher-k8s-master等。并且,按最佳实践,应该在刚刚一步 Clone 多个Node Template,保证 etcd 位于不同机器,保证 master 位于不同机器。后续需要添加 Node 时,也是以不同的Node Template为单位新增的设置 Cluster Options
Kubernetes Version:
1.13.5-rancher1-3Network Provider:
Flannel(这种网络格式比较简单且稳定)Cloud Provider:
Custom,然后点击Edit,将本项目内的文件cloud-config.yml里的内容复制进去注意部署完毕后,需要再次去检查
cloud-config.yml,曾经遇到过 insecure_flag 被重新设置为 false 的情况,如果发生此情况则集群无法成功创建,需要重新 Edit Cluster。以下是 cloud-config.yml 内容
1 | addon_job_timeout: 30 |
点击
Create,进入首页 -> rancher -> Nodes,查看创建进程,可能需要等待数分钟。也可以登录到deploy机器,使用docker logs rancher-server -f命令,实时查看rancher当前的创建进度一旦修改集群配置,集群内所有服务将不可用,但添加Node节点不影响,尽可能避免删除Node节点
当集群成功运行时,运行命令
kubectl apply -f ./k8s-storageclass.yaml(如果没有安装并配置kubectl, 请参见后面的 [macOS 的配置] 一节),该命令会添加自动请求磁盘空间的 StorageClass:eudicssd和eudichdd。可以让服务后续自由的选择硬盘性质
普通机器
将需要部署的机器的IP地址全部填入
inventory文件的[deploy]下,这些机器必须满足能够在本机直接免密码登录root账户,且互相之间支持免密码登录root账户在 macOS 环境下,运行
start_deploy.sh脚本。它需要ansible作为基础。如果没有ansible,则可以pip install ansible
start_deploy.sh的作用是给每台机器配置可以完美运行 rancher 的环境,包括安装指定的 Docker、设定 Host 等
start_deploy.sh是基于 Ubuntu 18.04 LTS 制作的如果后续需要添加新的机器,则这些新机器也必须要跑一遍
start_deploy.sh,然后再做下面的操作
- 指定一台机器为运行
rancher的机器。在这台机器里运行以下指令,假设它位于 192.168.1.199
docker run -d --restart=unless-stopped -p 80:80 -p 443:443 -v 192.168.1.199:/var/lib/rancher/ -v /root/var/log/auditlog:/var/log/auditlog -e AUDIT_LEVEL=3 rancher/rancher:v2.2.4
等待一段时间后直接访问 https://192.168.1.199
点击
Add Cluster,选择Custom设置 Cluster Options
Kubernetes Version:
1.13.5-rancher1-3Network Provider:
Flannel
如果不是云服务器,保持
Cloud Provider为空点击 Next
此时会出现一段命令,需要手工选择节点的角色,会自动出现需要的命令,此时需要自己手工登录这些机器,并运行指定命令。Rancher 会自动检测内网里已运行命令的机器
观察
rancher,直到所有 Node 状态都是已完成
外部服务发现的必要操作
由于目前常规服务(非 gRPC 服务)是通过 Ingress -> Service -> Deployment/StatefulSet -> Pod 的流程来找到具体的服务并发送接收流量的。Ingress 会根据域名来跳转。因此需要配置内置 DNS 服务,支持通配符匹配域名并跳转指定 IP,以下是 pfsense 的配置方法
需要注意的是:直接在 Host Overrides 里,让 Host 留空并只写 Parent domain of host 是无法起到通配符匹配的效果的
进入 pfsense -> Services -> DNS Resolver -> General Settings -> Custom options
在 Custom opptions 中输入以下内容,以便 test.local 的流量指向
worker
1 | server: |
安装组件
Kubernetes Dashboard
可以直接在 Rancher 的
App内安装注意 Dashboard 必须安装在
System命名空间内。可以打开 Enable Dashboard Cluster Admin Role,这样可以避免查询 Token 才能再次登录的问题
Helm(可选,暂时不需要)
进入
Global,点击 Tools -> Catalogs,开启Helm Stable,不开启Helm Incubator,保证安装的都是 stable。安装 Helm CLI
1 | snap install helm --classic |
- 完成后,做一下验证
helm version
应该显示
1 |
|
macOS 的配置
- 安装 kubectl,这样可以本地运行 kubectl 直接部署需要的服务
brew install kubernetes-cli
- 安装 kompose,这样可以将现存的 docker-compose.yml 直接转换成 Kubernetes 支持的 yaml
brew install kompose
本地开设一个文件位于
~/.kube/config,然后进入这里找到配置好的 config 文件: Cluster -> Kubeconfig File 内。配置成功后,本地调用kubectl get nodes进行验证。如果出现了服务器里的 nodes 则说明一切正常。注意在使用
kubectl之前,必须确保关闭了Terminal代理(代理软件可以保持打开)。否则会反复报EOF错误。如有必要,运行以下命令清空环境变量
1 | unset http_proxy |
已知问题
目前常规服务(非 gRPC 服务)是通过 Ingress -> Service -> Deployment/StatefulSet -> Pod 的流程来找到具体的服务并发送接收流量的。Ingress 会根据域名来跳转到合适的服务里,如果 pfsense 绑定的 IP 地址所在的 Node 不可用,那么将会导致域名解析到已经停止的机器上,进而导致服务无法访问。但实际上是可以访问的
如果某个服务需要开设大量端口给 Kubernetes 外部使用,那么必须使用 NodePort 来实现,不太友好
目前 Node 不可用后,需要等待 5 分钟才能调度该 Node 里的 Pod 到新的 Node 里去,时间太长
vSphere 不支持增大硬盘空间,一旦创建则不可修改。云服务则是可以的。目前只能通过指定较大的硬盘空间,来规避此问题
目前创建会提示
Error creating machine: Error in driver during machine creation: The host does not have sufficient CPU resources to satisfy the reservation.