从 Docker Compose 到 Kubernetes:物联网管理系统迁移实战

从 Docker Compose 到 Kubernetes:物联网管理系统迁移实战

本文记录一次真实的迁移实验过程,包含踩过的坑、解决的思路、以及复盘思考。适合正在学习 K8S 并希望理解"为什么"的读者。


一、背景与目标

为什么做这次迁移?

物联网管理系统原采用 Docker Compose 部署,结构简单:前端 Nginx + 后端 Spring Boot + MySQL。但单机部署存在单点故障、无法扩缩容、发布需停服等问题。

Kubernetes 正是为了解决这些问题而生。本次实验目标:将这套系统迁移到 K8S 集群,体验从"单机编排"到"集群调度"的转变。


二、环境准备

2.1 资源规划

角色 主机名 IP 地址
Master master 192.168.116.168
Node1 node1 192.168.116.169
Node2 node2 192.168.116.170

2.2 软件版本

  • 操作系统:CentOS 7.9

  • Docker:20.10.24

  • Kubernetes:v1.20.15(kubeadm + kubelet + kubectl)

  • 网络插件:Flannel

2.3 系统配置(所有节点)

关闭 SELinux、防火墙、Swap,配置主机名和 hosts 文件。

为什么不展开写? 这些是标准操作,网上一搜一大把,本文重点放在"卡住的地方"。有需要我后面可发出来


三、目录结构

复制代码
/root/k8s-experiment/
├── iot-1.0.0.jar              # 后端 JAR
├── iot.sql                    # 数据库 SQL
├── iot-manage-front/          # 前端静态文件
├── iot-project/               # 镜像构建目录
│   ├── backend/Dockerfile
│   ├── frontend/Dockerfile
│   ├── frontend/nginx.conf
│   └── database/Dockerfile
└── k8s/                       # K8S 部署文件
    ├── iot-backend-deploy.yaml
    ├── iot-database-deploy.yaml
    └── iot-frontend-deploy.yaml

四、核心挑战与解决方案

🔥 挑战 1:虚拟机无法拉取基础镜像

现象 :docker pull 始终超时,即使配置了国内镜像加速器。

原因:实验环境虚拟机完全无法访问外网(公司网络 + 网关双重限制)。

解决方案:离线导入

  • 在 Windows 上拉取镜像 → docker save 导出 .tar → 上传到 master → docker load 导入

复盘:网络隔离环境下,跳板机拉取 + 离线包传输是标准方案。


🔥 挑战 2:openjdk:11-jre-slim 镜像已废弃

现象 :not found

原因:OpenJDK 官方镜像已迁移到 Eclipse Temurin。

解决方案 :改用 eclipse-temurin:11-jre


🔥 挑战 3:kubeadm init 失败,kubelet 无法启动

现象:

执行 kubeadm init 后卡住,最终报错:

复制代码
[kubelet-check] The HTTP call equal to 'curl -sSL http://localhost:10248/healthz' failed
kubelet isn't running or healthy
timed out waiting for the condition

查看 kubelet 状态:

复制代码
systemctl status kubelet

查看详细日志:

复制代码
journalctl -xeu kubelet -n 50

关键错误信息:

复制代码
no such file or directory: /var/run/dockershim.sock
transport: Error while dialing dial unix /var/run/dockershim.sock

检查 Docker socket 是否存在:

复制代码
ls -la /var/run/*.sock

输出显示只有 /var/run/docker.sock,没有 dockershim.sock

确认版本:

复制代码
kubelet --version   # Kubernetes v1.22.4
docker --version    # Docker version 20.10.24

原因:

Kubernetes v1.22 正式移除了内置的 dockershim 组件。实验手册的配置方式(通过 /var/run/dockershim.sock 连接 Docker)在该版本中已失效。

解决方案:

降级到最后一个原生支持 dockershim 的版本 v1.20.15:

复制代码
# 清理失败状态
kubeadm reset -f
# 卸载 1.22
yum remove -y kubelet-1.22.4 kubeadm-1.22.4 kubectl-1.22.4
# 安装 1.20.15
yum install -y kubelet-1.20.15 kubeadm-1.20.15 kubectl-1.20.15
# 锁定版本
yum versionlock kubelet kubeadm kubectl
# 重启服务
systemctl restart docker kubelet
#重新初始化
kubeadm init --image-repository=registry.aliyuncs.com/google_containers --pod-network-cidr=10.244.0.0/16

验证:

复盘:

K8S v1.22 已移除 dockershim,实验手册的版本要求与实际配置存在偏差。降级到 v1.20.15 可保持与手册一致。遇到类似问题,建议先确认 Kubernetes 与容器运行时的版本兼容性矩阵。

🔥 挑战 4:Pod 镜像拉取失败与存储卷问题

现象:

原因:

  1. ImagePullBackOff / ErrImagePull:镜像只存在于 master 节点,Pod 被调度到 node2,K8S 无法跨节点拉取

  2. Pending:数据库 Pod 使用了 PVC,但集群中没有匹配的 PV

解决过程:

复制代码
# 步骤1:将镜像分发到 node2
docker save iot-backend:1.0 -o iot-backend.tar
docker save iot-database:1.0 -o iot-database.tar
docker save iot-frontend:1.0 -o iot-frontend.tar
scp *.tar root@192.168.116.170:/root/
ssh root@192.168.116.170 "docker load -i /root/iot-backend.tar && docker load -i /root/iot-database.tar && docker load -i /root/iot-frontend.tar"
# 步骤2:创建 PV 解决数据库存储问题
ssh root@192.168.116.170 "mkdir -p /data/mysql"
cat <<EOF | kubectl apply -f -
apiVersion: v1
kind: PersistentVolume
metadata:
  name: mysql-pv
spec:
  capacity:
    storage: 5Gi
  accessModes:
    - ReadWriteOnce
  hostPath:
    path: /data/mysql
EOF

# 步骤3:删除旧 Pod 触发重建
kubectl delete pod --all

结果:成功访问前端页面

复盘:

  1. K8S 集群中每个 worker 节点都需要有镜像,离线环境需手动分发

  2. Deployment 使用 PVC 前必须确保 PV 存在,否则 Pod 无法调度

  3. 三个问题相互独立但同时出现,解决顺序:先分发镜像 → 再创建 PV → 重建 Pod

今日进度:集群搭建完成,后端和前端服务已成功运行,数据库存储问题正在排查中。

本实验从零开始,所有操作均为本人手搓。由于环境(CentOS 7.9 + 内网隔离)和手册版本偏差,踩了不少坑。文中记录的每一个错误、每一行命令,都是真实复现而非预演。

如果觉得内容对你有帮助,欢迎 点赞 + 关注,你的支持是我持续输出的动力。有任何问题或更好的思路,也请在评论区指正交流

相关推荐
小白的码BUG之路1 小时前
Docker -- No space left on device
运维·docker·容器
悟天特斯1 小时前
AI驱动的楼宇节能:从“经验省电“到“算法能效“的进化之路
人工智能·物联网
wzq11_6662 小时前
Kubernetes集群——Service篇(详细讲解!!!)
云原生·容器·kubernetes
wuyk5552 小时前
《WiFi 嵌入式物联网开发全套实战》| 第 29 章 WiFi 长连接保活机制:无线层 + 应用层双重心跳
物联网
程序员老陆2 小时前
Docker 命令全景指南:从镜像构建到生产运维
运维·docker·容器
乐讯通物联网服务商2 小时前
外勤执法记录仪接入物联网:间歇联网终端通信方案选型分析
物联网·执法记录仪·物联网卡
微三云马玮均—GEO源码系统 私有化部署11 小时前
消费返物业费:消费+服务趋势的必然产物!
大数据·人工智能·物联网·区块链·生活
笨笨饿13 小时前
140_AI新手村MCP与Skills是干嘛的
开发语言·人工智能·python·stm32·单片机·嵌入式硬件·物联网
小神兵18 小时前
对电压源与电流源的的简单理解
单片机·嵌入式硬件·物联网
智鸟科技GemeOpen开发者智能设备1 天前
MQTT智能插座GSPM1B2 · 开发者实战指南
java·开发语言·python·物联网