k8s学习记录01
文章目录
最近在本机macOS安装了开发用的k8s集群之后,花了些时间研究k8s,在这个过程中有一些零零星星的实操技巧,在这里记录一下,这些实际操作技巧均是在之前搭建的单机环境验证过的,可以作为其它环境的参考。
利其器
发现两个工具可以极大提高效率,这里首先提一下。
kube-ps1
为命令行终端增加k8s相关的$PROMPT
字段,安装方法如下:
brew install kube-ps1
# 然后在~/.zshrc最后添加以下两行
# source "/usr/local/opt/kube-ps1/share/kube-ps1.sh"
# PROMPT='$(kube_ps1)'$PROMPT
# 重新加载一下zshrc的配置
source ~/.zshrc
然后在执行kubectl
命令里就可以明确地知道上下文及命名空间了。
kube-shell
这个就更强大了,交互式带命令提示的kubectl终端。不过官方最新版本有问题,可以安装我这里准备好的稳定版本:
git clone https://github.com/jeremyxu2010/kube-shell.git
cd kube-shell
git checkout stable
pip install . --user -U
然后就可以敲kube-shell
命令使用了,功能很强大,使用文档见这里。
k8s里的基本概念
k8s里的基本概念比较多,不过设计上还是比较简单的,大概浏览下Jimmy Song写的kubernetes-handbook这些章节3.1.** Kubernetes架构、3.4. Pod状态与生命周期管理、3.5. 集群资源管理、3.6. 控制器、3.7. 服务发现、3.8. 身份与权限控制、3.9. 存储,就差不多了。
Ingress Controller
部署在k8s里的服务总要想办法让外部访问到,不可能每次都是用type:NodePort
来解决问题,这里我用traefik-ingress-controller
及nginx-ingress-controller
,分别解决http和tcp协议服务的外部暴露问题。
traefik-ingress-controller
安装起来参考官方文档就好了,这里简要列一下步骤:
# 创建相关服务帐户及集群角色、集群角色绑定
kubectl apply -f https://raw.githubusercontent.com/containous/traefik/master/examples/k8s/traefik-rbac.yaml
# 以DaemonSet方式部署
kubectl apply -f https://raw.githubusercontent.com/containous/traefik/master/examples/k8s/traefik-ds.yaml
# 这里再编辑一下traefik-ingress-service,去掉nodePort, 将port修改为80, type修改为LoadBalancer
kubectl edit service traefik-ingress-service
# 最后重启一下Docker for macOS
docker ps -q | xargs -L1 docker stop
test -z "$(docker ps -q 2>/dev/null)" && osascript -e 'quit app "Docker"'
open --background -a Docker
等docker
及k8s
都启动完成,这时会发现本机的80端口处于监听状态了,用浏览器直接访问,当然是看不到正常的页面的,因为还要提交Ingress,也比较简单:
$ cat traefik-web-ui.yml
apiVersion: v1
kind: Service
metadata:
name: traefik-web-ui
namespace: kube-system
spec:
selector:
k8s-app: traefik-ingress-lb
ports:
- port: 80
targetPort: 8080
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: traefik-web-ui
namespace: kube-system
annotations:
kubernetes.io/ingress.class: traefik
spec:
rules:
- host: traefik-ui.local
http:
paths:
- backend:
serviceName: traefik-web-ui
servicePort: 80
# 用上述描述文件部署
$ kubectl apply -f traefik-web-ui.yml
再在/etc/hosts
文件中把traefik-ui.local
这个域名指向本机,然后就可以在浏览器中访问http://traefik-ui.local/
了。
类似的,其它http协议的service以后type
都可以只设为ClusterIP
,然后配置一个Ingress
通过traefik-ingress-controller
暴露出去了。比如现在暴露kubernetes-dashboard
就很方便了:
# 将hostPort删除, 将type修改为ClusterIP
$ kubectl edit service kubernetes-dashboard
$ cat kubernetes-dashboard.yml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
annotations:
kubernetes.io/ingress.class: traefik
name: k8s-dashboard
namespace: kube-system
spec:
rules:
- host: k8s-dashboard.local
http:
paths:
- backend:
serviceName: kubernetes-dashboard
servicePort: 443
path: /
# 用上述描述文件部署
$ kubectl apply -f kubernetes-dashboard.yml
再在/etc/hosts
文件中把k8s-dashboard.local
这个域名指向本机,然后就可以在浏览器中访问http://k8s-dashboard.local/
了。
这里有一个小插曲,因为本机安装的k8s-dashboard
的证书不合法,为了让traefik-ingress-controller
可正常反向代理到它,需要修改traefik-ingress-controller
的一个参数:
# 给容器添加一个--insecureSkipVerify=true的启动参数
kubectl edit daemonset traefik-ingress-controller
nginx-ingress-controller
假设k8s集群中有一个mysql服务需要暴露给外部访问,这时就用得上nginx-ingress-controller
了,安装方法也很类似:
# 部署nginx-ingress-controller相关的服务帐户、集群角色、集群角色绑定、Deployment、ConfigMap
$ kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/master/deploy/mandatory.yaml
# 暴露某些端口
$ cat nginx-ingress-service.yml
kind: Service
apiVersion: v1
metadata:
name: ingress-nginx
namespace: ingress-nginx
labels:
app: ingress-nginx
spec:
externalTrafficPolicy: Local
type: LoadBalancer
selector:
app: ingress-nginx
ports:
- name: mysql
port: 3306
targetPort: 3306
# 用上述描述文件部署
$ kubectl apply -f nginx-ingress-service.yml
# 等一会儿后,重启Docker for macOS后,应该有进程监听3306端口了
$ lsof -i :3306
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
com.docke 36484 jeremy 37u IPv4 0xe746861636421a57 0t0 TCP *:mysql (LISTEN)
com.docke 36484 jeremy 39u IPv6 0xe7468616205d110f 0t0 TCP localhost:mysql (LISTEN)
# 然后创建tcp服务相关的ConfigMap,其中mysql是mysql服务的名称,如要反向代理其它tcp服务,相应地修改data里的定义
$ cat nginx-tcp-configmap.yml
apiVersion: v1
kind: ConfigMap
metadata:
name: nginx-tcp-configmap
namespace: kube-system
data:
"3306": default/mysql:3306
# 最后修改nginx-ingress-controller运行时的参数,指定tcp服务反向代理的configmap,添加--tcp-services-configmap=kube-system/nginx-tcp-configmap启动参数
kubectl edit deployment nginx-ingress-controller
这时在本机就可以访问mysql服务了:
mysql -uroot -p -h127.0.0.1 -P3306
至此,无论是http协议还是tcp协议的服务,都可以很方便地暴露给外部使用了。
部署基础服务
常规的基础服务都已经用别人已经打好的包,可以通过helm来安装,helm的安装方法也比较简单:
$ brew install kubernetes-helm
# helm在k8s里初始化
$ helm init
# 查询mq相关的包
$ helm search mq
NAME CHART VERSION APP VERSION DESCRIPTION
stable/prometheus-rabbitmq-exporter 0.1.1 v0.28.0 Rabbitmq metrics exporter for prometheus
stable/rabbitmq 1.1.2 3.7.5 Open source message broker software that implem...
stable/rabbitmq-ha 1.5.0 3.7.4 Highly available RabbitMQ cluster, the open sou...
# 这样就会将别人打好的rabbitmq包部署起来
$ helm install stable/rabbitmq -n testmq
安装的时候还可以指定定制的参数,参见这里。
使用命令helm search
可以看到目前仓库里别人打好的helm chart,发现redis, mysql, rabbitmq等常用基础组件都有了,真的是很方便。即使有一些组件比较特殊没有,也可以参考kubernets/charts及Developing Templates模仿写一个chart。
参考
文章作者 Jeremy Xu
上次更新 2018-05-20
许可协议 © Copyright 2020 Jeremy Xu