实战指南:在指定 IP 配置下搭建私有 Docker Registry 与 Kubernetes 集群
随着容器技术的不断发展,Docker 和 Kubernetes 已成为现代应用部署和管理的核心工具。本指南将带您一步步搭建一个包含私有 Docker Registry、Kubernetes 集群(包含 Master 和多个 Worker 节点)的完整容器化环境,同时介绍如何部署应用、配置网络和安全、以及实施监控与管理。
前言
假设您的基础设施 IP 配置如下:
- Docker Registry:
192.168.0.180:5000
- Master 节点:
192.168.0.181
- Worker 节点:
192.168.0.182
192.168.0.183
192.168.0.184
本指南将涵盖以下内容:
- 设置私有 Docker Registry
- 配置 Kubernetes 集群
- 构建并推送 Docker 镜像到私有 Registry
- 在 Kubernetes 上部署应用
- 配置网络与安全
- 监控与管理
- 备份与恢复
- 常见问题与故障排除
- 进一步优化与扩展
- 结语
一、设置私有 Docker Registry
1.1 部署 Docker Registry
在 192.168.0.180
服务器上部署官方 Docker Registry:
# 拉取官方 Docker Registry 镜像
docker pull registry:2# 运行 Docker Registry 容器
docker run -d \-p 5000:5000 \--restart=always \--name registry \registry:2
1.2 配置 TLS 以确保安全通信
为确保与 Docker Registry 的通信安全,配置 TLS:
-
生成自签名证书:
mkdir -p certs openssl req -newkey rsa:4096 -nodes -sha256 \-keyout certs/domain.key -x509 -days 365 \-out certs/domain.crt
提示:在生成证书时,
Common Name (CN)
应设置为192.168.0.180
。 -
运行 Docker Registry 并使用 TLS:
docker stop registry docker rm registrydocker run -d \-p 5000:5000 \--restart=always \--name registry \-v "$(pwd)/certs:/certs" \-e REGISTRY_HTTP_TLS_CERTIFICATE=/certs/domain.crt \-e REGISTRY_HTTP_TLS_KEY=/certs/domain.key \registry:2
-
在各 Kubernetes 节点上信任自签名证书:
将
domain.crt
拷贝到每个节点的/etc/docker/certs.d/192.168.0.180:5000/ca.crt
:mkdir -p /etc/docker/certs.d/192.168.0.180:5000/ cp domain.crt /etc/docker/certs.d/192.168.0.180:5000/ca.crt# 重启 Docker 服务 systemctl restart docker
二、配置 Kubernetes 集群
2.1 安装 Kubernetes 组件
在所有节点(Master 和 Workers)上安装 Docker、kubeadm
、kubelet
和 kubectl
,可参考 官方文档。
2.2 初始化 Master 节点
在 Master 节点 (192.168.0.181
) 上执行:
kubeadm init \--apiserver-advertise-address=192.168.0.181 \--pod-network-cidr=10.244.0.0/16
完成后,按照提示配置 kubectl
:
mkdir -p $HOME/.kube
sudo cp /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
2.3 部署网络插件
以 Flannel 为例:
kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
2.4 添加 Worker 节点
在每个 Worker 节点上执行 kubeadm join
命令(在初始化时生成):
kubeadm join 192.168.0.181:6443 --token <token> --discovery-token-ca-cert-hash sha256:<hash>
2.5 验证集群状态
在 Master 节点上查看节点状态:
kubectl get nodes
应看到所有节点均为 Ready
状态。
三、构建并推送 Docker 镜像到私有 Registry
3.1 编写 Dockerfile
创建 Dockerfile
:
# 基于官方 Node.js 镜像
FROM node:14-alpine# 设置工作目录
WORKDIR /app# 安装依赖
COPY package.json .
RUN npm install# 复制源代码
COPY . .# 暴露端口
EXPOSE 3000# 启动应用
CMD ["npm", "start"]
3.2 构建镜像
docker build -t 192.168.0.180:5000/my-app:v1.0 .
3.3 推送镜像到私有 Registry
docker push 192.168.0.180:5000/my-app:v1.0
注意:确保 Docker 已信任 Registry 的 TLS 证书。
四、在 Kubernetes 上部署应用
4.1 创建 Deployment 配置
创建 my-app-deployment.yaml
:
apiVersion: apps/v1
kind: Deployment
metadata:name: my-app-deployment
spec:replicas: 3selector:matchLabels:app: my-apptemplate:metadata:labels:app: my-appspec:imagePullSecrets:- name: regcredcontainers:- name: my-app-containerimage: 192.168.0.180:5000/my-app:v1.0ports:- containerPort: 3000
4.2 应用 Deployment
kubectl apply -f my-app-deployment.yaml
4.3 创建 Service
创建 my-app-service.yaml
:
apiVersion: v1
kind: Service
metadata:name: my-app-service
spec:selector:app: my-apptype: NodePortports:- protocol: TCPport: 80targetPort: 3000nodePort: 30007
4.4 应用 Service
kubectl apply -f my-app-service.yaml
4.5 访问应用
通过任一 Worker 节点的 IP 及端口访问:
http://192.168.0.182:30007
五、配置网络与安全
5.1 设置网络策略
创建 db-network-policy.yaml
,仅允许特定 Pod 访问数据库:
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:name: allow-my-appnamespace: database
spec:podSelector:matchLabels:app: postgresingress:- from:- podSelector:matchLabels:app: my-appports:- protocol: TCPport: 5432
应用网络策略:
kubectl apply -f db-network-policy.yaml
5.2 配置 RBAC 权限
创建角色和角色绑定 role.yaml
:
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:name: pod-readernamespace: default
rules:- apiGroups: [""]resources: ["pods"]verbs: ["get", "watch", "list"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:name: read-podsnamespace: default
subjects:- kind: Username: demo-userapiGroup: rbac.authorization.k8s.io
roleRef:kind: Rolename: pod-readerapiGroup: rbac.authorization.k8s.io
应用配置:
kubectl apply -f role.yaml
5.3 安全最佳实践
- 最小权限原则:仅授予必要的权限。
- 限制特权容器:避免使用特权模式。
- 定期更新:保持镜像和组件的最新安全补丁。
六、监控与管理
6.1 部署 Prometheus 和 Grafana
使用 Helm 部署
-
添加 Helm 仓库:
helm repo add prometheus-community https://prometheus-community.github.io/helm-charts helm repo update
-
安装 Prometheus:
helm install prometheus prometheus-community/prometheus
-
安装 Grafana:
helm install grafana prometheus-community/grafana
-
访问 Grafana:
获取初始密码:
kubectl get secret grafana -o jsonpath="{.data.admin-password}" | base64 --decode ; echo
端口转发:
kubectl port-forward svc/grafana 3000:80
在浏览器访问
http://localhost:3000
。
6.2 部署 Kubernetes Dashboard
-
部署 Dashboard:
kubectl apply -f https://raw.githubusercontent.com/kubernetes/dashboard/v2.6.0/aio/deploy/recommended.yaml
-
创建管理员账户:
创建
dashboard-admin.yaml
:apiVersion: v1 kind: ServiceAccount metadata:name: admin-usernamespace: kubernetes-dashboard --- apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRoleBinding metadata:name: admin-user subjects:- kind: ServiceAccountname: admin-usernamespace: kubernetes-dashboard roleRef:kind: ClusterRolename: cluster-adminapiGroup: rbac.authorization.k8s.io
应用配置:
kubectl apply -f dashboard-admin.yaml
-
获取登录令牌:
kubectl -n kubernetes-dashboard get secret $(kubectl -n kubernetes-dashboard get sa/admin-user -o jsonpath="{.secrets[0].name}") -o go-template="{{.data.token | base64decode}}"
-
访问 Dashboard:
运行代理:
kubectl proxy
在浏览器访问:
http://localhost:8001/api/v1/namespaces/kubernetes-dashboard/services/https:kubernetes-dashboard:/proxy/
七、备份与恢复
7.1 备份 etcd
备份命令:
ETCDCTL_API=3 etcdctl snapshot save backup.db \--endpoints=https://127.0.0.1:2379 \--cacert=/etc/kubernetes/pki/etcd/ca.crt \--cert=/etc/kubernetes/pki/etcd/server.crt \--key=/etc/kubernetes/pki/etcd/server.key
7.2 恢复 etcd(如有必要)
恢复命令:
ETCDCTL_API=3 etcdctl snapshot restore backup.db \--data-dir=/var/lib/etcd-from-backup
注意:恢复 etcd 涉及停机操作,请谨慎执行,并参考 官方文档。
八、常见问题与故障排除
8.1 Pod 无法拉取镜像
解决方式:
- 检查
imagePullSecrets
:确保已正确创建和引用。 - 验证 TLS 证书:确保节点信任 Registry 证书。
- 确认镜像存在:使用
curl
检查镜像仓库。
8.2 节点状态为 NotReady
解决方式:
-
检查 kubelet:
systemctl status kubelet
-
验证网络连接:确保节点间网络通畅。
-
查看日志:
journalctl -u kubelet
8.3 应用性能问题
解决方式:
- 资源分配:检查 Pod 的资源请求和限制。
- 日志查看:通过
kubectl logs
查看应用日志。 - 监控分析:使用 Prometheus 和 Grafana 分析性能瓶颈。
九、进一步优化与扩展
9.1 使用 Helm 简化部署
创建 Helm Chart:
helm create my-app
配置 values.yaml
:
image:repository: 192.168.0.180:5000/my-apptag: v1.0imagePullSecrets:- name: regcred
安装 Chart:
helm install my-app-release my-app
9.2 集成 CI/CD 流水线
示例:GitLab CI/CD
在 .gitlab-ci.yml
中配置:
stages:- build- deploybuild:stage: buildscript:- docker build -t 192.168.0.180:5000/my-app:${CI_COMMIT_SHA} .- docker push 192.168.0.180:5000/my-app:${CI_COMMIT_SHA}deploy:stage: deployscript:- kubectl set image deployment/my-app-deployment my-app-container=192.168.0.180:5000/my-app:${CI_COMMIT_SHA}
9.3 配置自动伸缩(HPA)
安装 Metrics Server:
kubectl apply -f https://github.com/kubernetes-sigs/metrics-server/releases/latest/download/components.yaml
创建 HPA:
kubectl autoscale deployment my-app-deployment --cpu-percent=50 --min=1 --max=5
9.4 部署 Ingress 控制器
安装 Nginx Ingress Controller:
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/main/deploy/static/provider/cloud/deploy.yaml
创建 Ingress 资源:
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: my-app-ingress
spec:rules:- host: myapp.localhttp:paths:- path: /pathType: Prefixbackend:service:name: my-app-serviceport:number: 80
更新本地 Hosts 文件:
echo "192.168.0.182 myapp.local" | sudo tee -a /etc/hosts
十、结语
通过本指南,您已成功搭建了一个包含私有 Docker Registry 和 Kubernetes 集群的完整容器化环境,实现了:
- 安全的镜像管理:通过配置私有 Registry 和 TLS,确保镜像分发的安全性。
- 高效的应用部署:利用 Kubernetes 的自动化能力,实现应用的快速部署和扩展。
- 完善的监控与运维:采用 Prometheus、Grafana 等工具,实现集群的可观测性。
- 持续集成与交付:集成 CI/CD 流水线,提高开发和部署效率。
最佳实践建议
- 持续更新:定期升级 Kubernetes 和相关组件,应用最新的安全补丁。
- 加强安全:遵循最小权限原则,定期审计权限设置,使用镜像签名等技术。
- 优化资源:监控资源使用,合理设置请求和限制,避免资源浪费。
- 完善文档与自动化:记录操作流程,使用工具自动化部署,提高运维效率。
通过持续的优化与实践,您可以打造一个高性能、高可用的容器化平台,为业务发展提供坚实的基础。