当前位置: 首页 > news >正文

使用docker swarm搭建ruoyi集群环境

整体目标

项目背景

领导给到了我一个客户,客户商业模式为成本制作,成本核算。其中涉及到大量涉密数据,且与我们现有产品几乎没有兼容点(我们是一套低代码的框架,客户有很多业务二开)

测试环境给到了我6台业务机器,起初其中4台作为业务服务器,一台作为中间件,一台作为mysql。

6台机器均使用私有云部署,配置均为4c8G。

技术选型

直白的讲,物理器部署资源有限。

框架选型

开源框架:选型是ruoyi微服务框架,原因:开源免费,明星star项目,社区活跃,技术相对主流,自己也熟悉。

技术架构图

这是官方的架构图
在这里插入图片描述

系统架构图

这是我结合我们的系统 画的整体系统架构图
在这里插入图片描述

部署选型

部署方式:因为微服务框架和有限的物理机,我必然是选择集群部署的。市面上相对主流的集群部署毋庸置疑是k8s,但是作为一个之前只是后端的开发人员,在没有人指导的情况下,且有期返时间内,部署生产环境集群着实有点为难了。

K8S与docker swarm的横向对比
比较维度Docker SwarmKubernetes (k8s)
优点简单易用功能强大
与 Docker 集成紧密高度扩展性
快速部署广泛社区支持
轻量级多云支持
缺点功能相对有限学习曲线陡峭
扩展性差资源消耗大
社区和生态较少部署复杂
适用场景中小型项目大规模项目
简单应用复杂应用
初学者跨云部署
学习成本
快速上手深入掌握需要时间
拓展性
有限插件和工具丰富的插件和工具
社区完善度较小庞大
支持较少丰富的第三方支持

额外提一句:现实中,我们往往以结果为导向。虽然k8s不管是从扩展性,社区活跃度都远远超过docker swarm,但奈何学习成本高,我对于初学者不够友好(PS:国内好多站点被封了,之前用kubeadm部署,刷机后又没有资源站点了)。

学习东西是一个渐进的过程,阶段性的交付和成功,会给自己带来快乐。而一下子上来最难的,只能带来无穷的挫败和自我怀疑,最终陷入无限期的搁置(PS:难度因人而异)

docker swarm 介绍

Docker Swarm 是 Docker 提供的原生容器编排工具。它允许用户将多个 Docker 主机组合在一起,形成一个虚拟的 Docker 集群,并在这个集群上管理和部署容器。Swarm 使得用户可以通过熟悉的 Docker 命令和工具管理大规模的 Docker 容器部署。

部署方式就是一个master节点,其他worker节点加入。管理的最小单位是service,可以使用类似docker-compose的文件进行管理service。同时有多个stack,进行一组service的管理。

部署架构图

这是整体多机网络部署架构图
在这里插入图片描述

基于Redhat构建docker、docker-compose

repo配置

在这里插入图片描述

配置文件如下:

# CentOS-Base.repo
#
# The mirror system uses the connecting IP address of the client and the
# update status of each mirror to pick mirrors that are updated to and
# geographically close to the client.  You should use this for CentOS updates
# unless you are manually picking other mirrors.
#
# If the #mirrorlist= does not work for you, as a fall back you can try the 
# remarked out baseurl= line instead.
#
#[base]
name=CentOS-$releasever - Base - mirrors.aliyun.com
#failovermethod=priority
baseurl=http://mirrors.aliyun.com/centos/$releasever/BaseOS/$basearch/os/http://mirrors.aliyuncs.com/centos/$releasever/BaseOS/$basearch/os/http://mirrors.cloud.aliyuncs.com/centos/$releasever/BaseOS/$basearch/os/
gpgcheck=1
gpgkey=http://mirrors.aliyun.com/centos/RPM-GPG-KEY-CentOS-Official#additional packages that may be useful
[extras]
name=CentOS-$releasever - Extras - mirrors.aliyun.com
#failovermethod=priority
baseurl=http://mirrors.aliyun.com/centos/$releasever/extras/$basearch/os/http://mirrors.aliyuncs.com/centos/$releasever/extras/$basearch/os/http://mirrors.cloud.aliyuncs.com/centos/$releasever/extras/$basearch/os/
gpgcheck=1
gpgkey=http://mirrors.aliyun.com/centos/RPM-GPG-KEY-CentOS-Official#additional packages that extend functionality of existing packages
[centosplus]
name=CentOS-$releasever - Plus - mirrors.aliyun.com
#failovermethod=priority
baseurl=http://mirrors.aliyun.com/centos/$releasever/centosplus/$basearch/os/http://mirrors.aliyuncs.com/centos/$releasever/centosplus/$basearch/os/http://mirrors.cloud.aliyuncs.com/centos/$releasever/centosplus/$basearch/os/
gpgcheck=1
enabled=0
gpgkey=http://mirrors.aliyun.com/centos/RPM-GPG-KEY-CentOS-Official[PowerTools]
name=CentOS-$releasever - PowerTools - mirrors.aliyun.com
#failovermethod=priority
baseurl=http://mirrors.aliyun.com/centos/$releasever/PowerTools/$basearch/os/http://mirrors.aliyuncs.com/centos/$releasever/PowerTools/$basearch/os/http://mirrors.cloud.aliyuncs.com/centos/$releasever/PowerTools/$basearch/os/
gpgcheck=1
enabled=0
gpgkey=http://mirrors.aliyun.com/centos/RPM-GPG-KEY-CentOS-Official[AppStream]
name=CentOS-$releasever - AppStream - mirrors.aliyun.com
#failovermethod=priority
baseurl=http://mirrors.aliyun.com/centos/$releasever/AppStream/$basearch/os/http://mirrors.aliyuncs.com/centos/$releasever/AppStream/$basearch/os/http://mirrors.cloud.aliyuncs.com/centos/$releasever/AppStream/$basearch/os/
gpgcheck=1
gpgkey=http://mirrors.aliyun.com/centos/RPM-GPG-KEY-CentOS-Official
[docker-ce-stable]
name=Docker CE Stable - $basearch
baseurl=https://mirrors.aliyun.com/docker-ce/linux/rhel/$releasever/$basearch/stable
enabled=1
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/docker-ce/linux/rhel/gpg[docker-ce-stable-debuginfo]
name=Docker CE Stable - Debuginfo $basearch
baseurl=https://mirrors.aliyun.com/docker-ce/linux/rhel/$releasever/debug-$basearch/stable
enabled=0
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/docker-ce/linux/rhel/gpg[docker-ce-stable-source]
name=Docker CE Stable - Sources
baseurl=https://mirrors.aliyun.com/docker-ce/linux/rhel/$releasever/source/stable
enabled=0
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/docker-ce/linux/rhel/gpg[docker-ce-test]
name=Docker CE Test - $basearch
baseurl=https://mirrors.aliyun.com/docker-ce/linux/rhel/$releasever/$basearch/test
enabled=0
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/docker-ce/linux/rhel/gpg[docker-ce-test-debuginfo]
name=Docker CE Test - Debuginfo $basearch
baseurl=https://mirrors.aliyun.com/docker-ce/linux/rhel/$releasever/debug-$basearch/test
enabled=0
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/docker-ce/linux/rhel/gpg[docker-ce-test-source]
name=Docker CE Test - Sources
baseurl=https://mirrors.aliyun.com/docker-ce/linux/rhel/$releasever/source/test
enabled=0
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/docker-ce/linux/rhel/gpg[docker-ce-nightly]
name=Docker CE Nightly - $basearch
baseurl=https://mirrors.aliyun.com/docker-ce/linux/rhel/$releasever/$basearch/nightly
enabled=0
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/docker-ce/linux/rhel/gpg[docker-ce-nightly-debuginfo]
name=Docker CE Nightly - Debuginfo $basearch
baseurl=https://mirrors.aliyun.com/docker-ce/linux/rhel/$releasever/debug-$basearch/nightly
enabled=0
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/docker-ce/linux/rhel/gpg[docker-ce-nightly-source]
name=Docker CE Nightly - Sources
baseurl=https://mirrors.aliyun.com/docker-ce/linux/rhel/$releasever/source/nightly
enabled=0
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/docker-ce/linux/rhel/gpg

redhat因为客户买的没有注册 所以他的资源文件是空的

阿里云镜像

这个因为一些image在国外,配置一下阿里云镜像会拉取快很多

具体路径 https://cr.console.aliyun.com/cn-hangzhou/instances/mirrors
按照上面的配置就可以

在这里插入图片描述

部署操作

docker

sudo yum install -y yum-utils

sudo yum install docker-ce docker-ce-cli containerd.io

sudo systemctl start docker

sudo systemctl enable docker

docker-compose

sudo curl -L “https://github.com/docker/compose/releases/download/v2.x.x/docker-compose- ( u n a m e − s ) − (uname -s)- (unames)(uname -m)” -o /usr/local/bin/docker-compose

sudo chmod +x /usr/local/bin/docker-compose

docker-compose --version

docker swarm 初始化

docker swarm init

正常情况下,会出现token,如果你没有记录,也可以在manage节点

docker swarm join-token worker

查看对应的swarm的manage的token
在这里插入图片描述

然后再worker节点上 直接直接join就可以了

然后整体的一个node结构如下

在这里插入图片描述

这里我还对hostname做了修改

overlay 网络构建

十分重要

docker network create --driver overlay --subnet=10.10.0.0/24 --gateway=10.10.0.1 sangfor-network

docker中的网络是最为复杂的,同时因为我是跨机之间的网络通讯,这里使用了overlay的配置

然后再整个stack配置文件中,我使用了external: true,使用外部网络

网络查看

正常来说 当你构建完成一个service的构建之后,你要查看这个网络
docker network inspect sangfor-network
在这里插入图片描述

这里面会体现出你的container和对应的ip

需要注意是,当你的使用overlay网络的时候,如果你的某台woker机器上并没有service,那么这个overlay网络是不显示的

同时需要明确的是,查看网络中的container 只有当前机器的container才会显示

yml配置优先网段

需要明确的是,docker container内的网卡是有很多个的,他是哪个可以用就用哪个

所以这里需要结合程序的修改,就是这个preferred-networks,我写了10.10.0网段
在这里插入图片描述

通过这种方式,使得container的ip优先使用这个10.10.0网段

docker-stack部署

这里直接贴我两个的stack文件吧

docker-stack-basic.yml

version : '3.8'
services:cloud-mysql:image: mysql:5.7ports:- "3306:3306"volumes:- /data/cloud/mysql/conf:/etc/mysql/conf.d- ./mysql/logs:/logs- ./mysql/data:/var/lib/mysql- /etc/localtime:/etc/localtime:rocommand: ['mysqld','--innodb-buffer-pool-size=80M','--character-set-server=utf8mb4','--collation-server=utf8mb4_unicode_ci','--default-time-zone=+8:00','--lower-case-table-names=1','--default-authentication-plugin=mysql_native_password']environment:MYSQL_DATABASE: 'cloud_business'MYSQL_ROOT_PASSWORD: 'yourpassword'TZ: 'Asia/Shanghai'networks:- sangfor-networkdeploy:placement:constraints:- node.labels.mysql == truecloud-redis:container_name: cloud-redisimage: redisbuild:context: ./redisports:- "6379:6379"volumes:- ./redis/conf/redis.conf:/home/ruoyi/redis/redis.conf- ./redis/data:/datacommand: redis-server /home/ruoyi/redis/redis.confenvironment:- TZ=Asia/Shanghainetworks:- sangfor-networkdeploy:placement:constraints:- node.labels.middle == truenetworks:sangfor-network:external: true

docker-stack-sangfor.yml

version : '3.8'
services:cloud-portainer:image: portainer/portainer-ce:latestenvironment:- TZ=Asia/Shanghaivolumes:- ./portainer/data/:/data- /var/run/docker.sock:/var/run/docker.sockports:- "9000:9000"deploy:placement:constraints:- node.labels.portainer == trueresources:limits:cpus: '0.50'memory: 500Mnetworks:- sangfor-networkcloud-nacos:image: nacos/nacos-serverbuild:context: ./nacosenvironment:- MODE=standalone- TZ=Asia/Shanghaivolumes:- ./nacos/logs/:/home/nacos/logs- ./nacos/conf/application.properties:/home/nacos/conf/application.properties- /etc/localtime:/etc/localtime:roports:- "8848:8848"- "9848:9848"- "9849:9849"healthcheck:test: ["CMD", "curl", "-f", "http://localhost:8848/nacos/v1/console/health/liveness"]interval: 30stimeout: 10sretries: 5networks:- sangfor-networkdeploy:placement:constraints:- node.labels.middle == truecloud-nginx:image: nginx:1.0ports:- "80:80"volumes:- ./nginx/html/dist:/home/cloud/projects/cloud-ui- ./nginx/conf/nginx.conf:/etc/nginx/nginx.conf- ./nginx/logs:/var/log/nginx- ./nginx/conf.d:/etc/nginx/conf.denvironment:- TZ=Asia/Shanghainetworks:- sangfor-networkdeploy:placement:constraints:- node.labels.master == truecloud-gateway:image: registry.cn-hangzhou.aliyuncs.com/sangfor_authine/cloud_gateway:1.0ports:- "8080:8080"environment:TZ: Asia/Shanghaideploy:placement:constraints:- node.labels.master == truenetworks:- sangfor-networkcloud-auth:image: registry.cn-hangzhou.aliyuncs.com/sangfor_authine/cloud_auth:1.0ports:- "9200:9200"environment:- TZ=Asia/Shanghainetworks:- sangfor-networkcloud-modules-system:image: registry.cn-hangzhou.aliyuncs.com/sangfor_authine/cloud_system:1.0ports:- "9201:9201"environment:- TZ=Asia/Shanghainetworks:- sangfor-networkcloud-modules-gen:image: registry.cn-hangzhou.aliyuncs.com/sangfor_authine/cloud_gen:1.0ports:- "9202:9202"environment:- TZ=Asia/Shanghainetworks:- sangfor-networkcloud-modules-job:image: registry.cn-hangzhou.aliyuncs.com/sangfor_authine/cloud_job:1.0ports:- "9203:9203"environment:- TZ=Asia/Shanghainetworks:- sangfor-networkcloud-modules-file:image: registry.cn-hangzhou.aliyuncs.com/sangfor_authine/cloud_file:1.0ports:- "9300:9300"environment:- TZ=Asia/Shanghaivolumes:- ./cloud/uploadPath:/home/cloud/uploadPathnetworks:- sangfor-networkcloud-visual-monitor:image: registry.cn-hangzhou.aliyuncs.com/sangfor_authine/cloud_monitor:1.0ports:- "9100:9100"environment:- TZ=Asia/Shanghainetworks:- sangfor-networknetworks:sangfor-network:external: true

label标签固定

这里可以看到有些service我是固定在某些机器上的,当然前提是你要给你的机器打标签

标签这么打就行了

docker node update --label-add work_node3=true work_node3

我这边打标签分为几种常见场景

1.外部异构系统需要公用redis和mysql

2.portainer 需要在master节点上监控

3.nacos配置我是固定ip的(这里面应该是可以直接使用service名称代替ip的)

端口开放

有些端口需要对外开放,docker swarm中部分port也要打开

开放端口如下

sudo firewall-cmd --zone=public --add-port=8080/tcp --permanent

sudo firewall-cmd --reload

在这里插入图片描述

image托管

我这里偷懒了 我不想搭建harbor了

我直接把我的阿里云镜像仓库贡献出来了

这些相关的操作文档还是很多的

portainer可视化构建

portainer的构建方式在之前的stack中有

他的最大意义在于可视化的操作,降低scale和查看日志都比较方便

贴几张图

在这里插入图片描述

这里面service和stack他会自动抓取的
在这里插入图片描述

对于容器也可以做一些调配
在这里插入图片描述

查看nacos 内网ip

这个很重要,之前我一直跨机服务的时候 调度不通

查到最后是我的内网nacos ip注册的有问题,这也是前面网络声明网段和我使用preferred-networks的原因

记得在服务列表里面查看自己的ip
在这里插入图片描述

异常情况与排查思路

遇到了太多了卡点和异常了,我现在只记得一些关键卡点和排查思路了

Overlay网络问题

最一开始部署的时候,redis和mysql其实使用docker-compose部署的,然后发现我业务内部调用mysql网络不通。

我不服气,我把swarm集群中的网络改成了外部可以访问 增加了–attachable,但最后发现不行。

还是要放在一个网络里面,所以最后我把之前docker-compose build的mysql和redis 切换为stack部署了(切换代价很小,因为都做了挂载,数据不会丢失)

服务无法调度问题

通俗的讲就是我服务到了nginx,做完转发进入gateway 调不通auth权限。

第一反应其实也是网路问题,最后排查思路是 进入到gateway的容器内部

docker exec -it a927a4a68b2d /bin/bash

然后curl auth服务
在这里插入图片描述

这就是ping的通的

但是真实调研的时候 因为使用的是fegin

他们用的是这个serviceName
在这里插入图片描述

这里面的service名称 要等于nacos的名称
在这里插入图片描述

然后域名访问如下:
在这里插入图片描述

这样服务就基本没啥问题了

naocs 配置

这个完全是我因为我不太熟悉导致的问题

这个yml配置里面 就是cloud-auth-dev配置
在这里插入图片描述

naocs配置中心里面配置保持一致就可以‘

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • nosql--redis
  • 100个python的基本语法知识【上】
  • 2019年9月全国英语等级考试第三级笔试真题
  • 接口自动化测试框架实战-4-日志方法封装
  • 大屏数据看板一般是用什么技术实现的?
  • LC617-合并二叉树
  • 【11】微服务链路追踪SkyWalking
  • Django cursor()增删改查和shell环境执行脚本
  • 分享从零开始学习网络设备配置--任务6.1 实现计算机的安全接入
  • 【数据治理】隐私计算:数据治理中的安全守护者
  • 【Spring Boot 自定义配置项详解】
  • 操作系统:文件
  • SQL Server查询计划阅读及分析
  • 【c++刷题笔记-动态规划】day45: 115.不同的子序列 、583. 两个字符串的删除操作 、 72. 编辑距离
  • Chat-REC——基于 LLM 的推荐系统算法解析
  • [js高手之路]搞清楚面向对象,必须要理解对象在创建过程中的内存表示
  • 〔开发系列〕一次关于小程序开发的深度总结
  • AzureCon上微软宣布了哪些容器相关的重磅消息
  • ES10 特性的完整指南
  • HTTP那些事
  • JavaScript DOM 10 - 滚动
  • JavaScript中的对象个人分享
  • laravel with 查询列表限制条数
  • Quartz初级教程
  • React16时代,该用什么姿势写 React ?
  • React-flux杂记
  • Spring Boot快速入门(一):Hello Spring Boot
  • thinkphp5.1 easywechat4 微信第三方开放平台
  • 翻译:Hystrix - How To Use
  • 使用agvtool更改app version/build
  • 小李飞刀:SQL题目刷起来!
  • 怎么将电脑中的声音录制成WAV格式
  • shell使用lftp连接ftp和sftp,并可以指定私钥
  • Unity3D - 异步加载游戏场景与异步加载游戏资源进度条 ...
  • # Redis 入门到精通(一)数据类型(4)
  • # Spring Cloud Alibaba Nacos_配置中心与服务发现(四)
  • # SpringBoot 如何让指定的Bean先加载
  • # 数仓建模:如何构建主题宽表模型?
  • (13)Latex:基于ΤΕΧ的自动排版系统——写论文必备
  • (Charles)如何抓取手机http的报文
  • (LNMP) How To Install Linux, nginx, MySQL, PHP
  • (附源码)springboot掌上博客系统 毕业设计063131
  • (附源码)ssm教师工作量核算统计系统 毕业设计 162307
  • (个人笔记质量不佳)SQL 左连接、右连接、内连接的区别
  • (六)激光线扫描-三维重建
  • (三)mysql_MYSQL(三)
  • (一)项目实践-利用Appdesigner制作目标跟踪仿真软件
  • (转)JVM内存分配 -Xms128m -Xmx512m -XX:PermSize=128m -XX:MaxPermSize=512m
  • (转)项目管理杂谈-我所期望的新人
  • (转载)Linux网络编程入门
  • .equal()和==的区别 怎样判断字符串为空问题: Illegal invoke-super to void nio.file.AccessDeniedException
  • .htaccess 强制https 单独排除某个目录
  • .NET Standard 的管理策略
  • .NET 反射 Reflect
  • .NET 项目中发送电子邮件异步处理和错误机制的解决方案