一、项目结构

docker compose 部署 fisco bcos docker compose 部署单个服务_mysql

我这里准备了一个微服务项目。

里面包含三个服务模块:

card-serviceuse-rservice以及网关gateway

一个公共模块:

fegin-api

其中fegin-apicard-serviceuser-service引用。

二、基于项目构建部署目录结构

docker compose 部署 fisco bcos docker compose 部署单个服务_mysql_02

这个springcloud-app目录中的全部内容,之后就是要上传到服务上进行部署的源文件。

springcloud-app一级目录下包含了放gatewaycard-serviceuser-service三个微服务的文件夹。

一个放mysql数据和配置文件的文件夹。

以及一个dockercompose配置文件。

关于它们的详解如下。

2.1 gateway目录构建详解

在我提供的项目中,gatewaycard-serviceuser-service都属于微服务,构建方式是一样的。

这里就以gateway为例,解析怎么构建文件目录。

1)进入gateway目录:

docker compose 部署 fisco bcos docker compose 部署单个服务_java_03

里面只有一个我提前写好的Dockerfile文件。

要使用Docker构建镜像肯定是需要编写Dockerfile,在其中编写构建规则的。

2)打开Dockerfile文件:

里面只需要三句话即可。

# 指定java:8-alpine作为基础镜像,它包含了java程序部署的基本环境依赖
FROM java:8-alpine	
# 把当前目录下的javaApp.jar移动到/soft目录下
COPY ./javaApp.jar /soft/javaApp.jar
# 程序运行入口,就是java项目的启动命令
# 这句话也是容器成功运行后,第一个执行的命令
ENTRYPOINT java -jar /soft/javaApp.jar

card-serviceuse-rservice两个文件夹下的内容和gateway中的一致。

并且Dockerfile文件的内容也一样。因为它们三种都是基于java开发的微服务,构建镜像的方式都是一致的。

2.2 mysql 目录构建详解

docker compose 部署 fisco bcos docker compose 部署单个服务_spring cloud_04

由于所有微服务都是使用的mysql数据库。

这样也就涉及到了Docker中运行mysql容器。

而为了mysql数据和配置的可移植性和可维护性。一般都会进行数据卷挂载或者磁盘挂载。

把自定义的mysql配置合并到容器中,以及把容器内被隔离的mysql数据与宿主机进行关联。

1)conf目录

docker compose 部署 fisco bcos docker compose 部署单个服务_mysql_05

hmy.cnf中存放着自定义mysql配置。可以是字符集配置,主从复制中的配置等等等。

如果暂时没有自定义配置,最好也先挂载上。由于容器启动后无法再挂载新的数据卷或者磁盘。

如果第一次不挂载,今后再想给mysql添加配置。

就只能删除容器再重新运行镜像生成新容器时再去挂载配置文件了。

2)data目录

docker compose 部署 fisco bcos docker compose 部署单个服务_java_06

里面包含着mysql数据库服务器下存放的所有数据库的数据。这些数据都以二进制文件的形式存储在本地磁盘。

每个电脑存放mysql本地二进制表格数据的位置不同,一般是安装的时候自己设定的。

只有找到那个文件夹,把需要的数据库二进制文件复制进来即可。

这个目录和容器磁盘进行挂载后,里面的数据会直接覆盖mysql容器中的数据。

之后容器中mysql的数据发生变化之后,也会同步更新到宿主机本地磁盘中的对应位置。

也就是说这里的data目录里的对应文件,也会随之修改。这属于Docker的基础知识了。

2.3 dcoker-compose.yml文件详解

# Compose 文件格式有3个版本,分别为1, 2.x 和 3.x
# 目前主流的为 3.x 其支持 docker 1.13.0 及其以上的版本
version: "3.0"

services:							# 具体的服务定义
  nacos:							# nacos配置 nacos也是未来naocs服务的容器名称
    image: nacos/nacos-server		# nacos镜像名称
    environment:					# nacos环境变量
      MODE: standalone				# MODE相当于之前命令行的-m参数,指代运行模式。
      								# standalone单机运行(如果有nacos集群就不是这么写了)
    ports:							# 端口映射
      - "8848:8848"					# 把宿主机8848端口和nacos容器的8848端口相关联
      
  mysql:							# mysql配置 mysql也是未来mysql服务的容器名称
    image: mysql:5.7.25				# mysql镜像名称
    environment:					# mysql环境变量
      MYSQL_ROOT_PASSWORD: root		# mysql密码为root
    volumes:						# 数据卷挂载配置
      - "$PWD/mysql/data:/var/lib/mysql"	
      								# 宿主/mysql/data目录挂载到器/var/lib/mysql目录
      - "$PWD/mysql/conf:/etc/mysql/conf.d/"	
      								# 宿主/mysql/conf目录挂载到器/etc/mysql/conf.d/目录
      								# $PWD 代表运行Linux的pwd命令,获取当前文件的路径
      								# 这样可以确保在Linux中任意位置都能找到/mysql/conf目录
     ports:							# 端口映射
       - "3306:3306"				# 把宿主机3306端口和mysql容器的3306端口相关联
      									
  userservice:						# userservice微服务配置 userservice也是未来微服务的容器名称
    build: ./user-service			# 代表在当前目录下的user-service目录下构建userservice镜像
    
  cardservice:						# cardservice微服务配置 cardservice也是未来微服务的容器名称
    build: ./card-service			# 代表在当前目录下的card-service目录下构建cardservice镜像
    
  gateway:							# gateway微服务配置 gateway也是未来微服务的容器名称
    build: ./gateway				# 代表在当前目录下的gateway目录下构建gateway镜像
    ports:							# 端口映射
      - "9999:9999"					# 把宿主机9999端口和gateway容器的9999端口相关联

关于mysql端口映射的说明:

mysql只在微服务集群内部进行访问,只需要在userservicecardserviceapplication.yml文件中。

mysql的注册中心的地址,由ip格式改为dcoker-compose.yml文件中配置的服务命名称即可。

compose-file文件的官方文档:

https://docs.docker.com/compose/compose-file/

自定义的微服务配置可以在这里找配置怎么写。

nacos这种地三方镜像,就去它们对应的官网或者dockerHub上看看。

三、准备各个微服务的jar包

这里主要涉及了三个微服务userservicecardservicegateway

在打jar包前,需要先修改配置文件。

修改各个微服务的application.yml文件或者bootstrap.yml文件中的mysqlnacos的地址配置。

ip格式改为dcoker-compose.yml文件中配置的服务命名称。

这是因为使用dcoker-compose配置时。

所有的服务之间都可以直接使用dcoker-compose.yml文件中配置的服务命名称来访问对方。

这里就以打包user-service这个模块为例。

3.1 修改mysql和nacos地址

1)修改bootstrap.yml文件

docker compose 部署 fisco bcos docker compose 部署单个服务_docker_07

# 把红框处的localhost改为dcoker-compose.yml文件中配置的nacos
spring:
  application:
    name: userservice             # 服务名称
  profiles:
    active: dev                   #开发环境,这里是dev
  cloud:
    nacos:
      server-addr: nacos:8848 	  # Nacos地址
      config:                     # discovery 代表注册中心配置 config代表配置中心配置
        file-extension: yaml      # 文件后缀名

2)修改application.yml

docker compose 部署 fisco bcos docker compose 部署单个服务_mysql_08

server:
  port: 8081
spring:
  datasource:
    url: jdbc:mysql://mysql:3306/cloud_user?useSSL=false
    username: root
    password: root
    driver-class-name: com.mysql.jdbc.Driver

card-service和gateway模块中的配置也按上面的方式修改即可。

3.2 在pom.xml文件中添加打包插件

<!-- finalName中的配置就能确定打出来的jar包是什么名称 -->
<!-- plugins中配置的就是常规的maven打包插件 -->
<build>
    <finalName>javaApp</finalName>
    <plugins>
        <plugin>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-maven-plugin</artifactId>
        </plugin>
    </plugins>
</build>

3.3 使用Idea的Maven打包工具打包微服务

docker compose 部署 fisco bcos docker compose 部署单个服务_spring cloud_09

点击右侧Maven工具栏的package即可。

打包完成后到对应模块的target目录下获取jar包。

card-service和gateway模块的jar包也按上面的方式打出来即可,jar包名字都叫javaApp。

四、把jar包复制到springdata-app下的对应子目录中

user-service为例。

idea中的user-service模块下,找到target目录。

把打好的jar包复制到springdata-app目录下的userservice目录里。

docker compose 部署 fisco bcos docker compose 部署单个服务_java_10

card-service和gateway模块的jar包也按上面的方式制到springdata-app下的对应子目录中。

五、使用finallshell上传文件夹到服务器

docker compose 部署 fisco bcos docker compose 部署单个服务_java_11


可以选择任意自己想放的位置。只要便于查找即可。

六、compose相关命令

1)部署命令

# 对命令不熟悉可以查看命令文档
docker-compose --help
# docker-compose 是有非常多命令选项参数的,这里涉及到的两个
# up 创建并启动一个容器
# -d 后台运行
docker-compose up -d

2)停止命令

docker-compose stop

3)停止并删除

docker-compose down

4)重启

docker-compose restart
# 重启某些具体服务的写法
docker-compose restart gateway userservice

5)查看日志

docker-compose logs
# 查看具体的服务日志
# -f 持续更新日志变化,按ctrl+c可以结束
docker-compose logs -f userservice

上述都是常用命令,还有更多操作,不一一列举。

使用docker-compose --help就能知道所有docker-compose的用法。

七、具体部署操作

1)进入springdata-app文件目录

# 这个位置看自己把东西放哪,是不固定的
cd /usr/local/composrApp

2)执行部署命令

docker-compose up -d

3)部署后查看日志

docker-compose logs

4)部署问题解决方案

首次部署时日志中会出现如下错误:

docker compose 部署 fisco bcos docker compose 部署单个服务_微服务_12

主要是因为nacos容器启动速度比其他依赖nacos的微服务慢。

其它微服务已经启动了却连接不上nacos,也获取不到nacos中的配置信息。

解决方案:重启所有依赖nacos的微服务

docker-compose restart gateway userservice cardservice

重启完成后查看cardservice的日志

docker-compose logs -f cardservice

发现新出现的日志已经没有任何错误了。

八、基于自定义的jdk镜像部署微服务(推荐)

上面的方式有的人可能会觉得繁琐,每个微服务都有一个单独的文件夹,而且里面都有一个Dockerfile文件。

确实文件有点多。

还有一种方法可以让所有jar包放在一个文件夹中,并且不需要这么多重复的Dockerfile文件。

越来越多人也会选用这种方式来部署,并且这种方式,未来如果使用portainer管理docker时会很容易移植。

具体选择哪种方式,可以结合自己实际情况决定。

1)新建存放目录和文件

# 进入目录/usr/local/
cd /usr/local
# 新建app目录
mkdir app
# 新建Dockerfile文件
touch Dockerfile

存放位置可以根据部署需求自行指定

2)编写Dockerfile文件

# 构建镜像,执行命令:【docker build -t openjdk:8 .】
FROM openjdk:8u212-jre  # 基础镜像
MAINTAINER xxx			# 作者

# 设置时区
RUN ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
RUN echo 'Asia/Shanghai' >/etc/timezone

ENTRYPOINT ["java", "-server", "-Xms512M", "-Xmx512M", "-Djava.security.egd=file:/dev/./urandom", "-Dfile.encoding=UTF-8", "-XX:+HeapDumpOnOutOfMemoryError", "-jar", "/app/app.jar" ]

3)使用Dockerfile文件构建一个openjdk镜像

docker build -t openjdk:8 .

4)编写docker-compose.yml文件

version: '3'
services:
  mysql:
    image: mysql:8
    container_name: gddst-mysql-dev
    environment:
      - TZ=Asia/Shanghai
      - MYSQL_ROOT_PASSWORD=89225300
      - MYSQL_DATABASE=nacos_config
      - MYSQL_USER=gddst
      - MYSQL_PASSWORD=123456
    ports:
      - "3306:3306"
    volumes:
      - /usr/local/workspace/mysql/data:/var/lib/mysql
      - /usr/local/workspace/mysql/mysql.cnf:/etc/mysql/conf.d/mysql.cnf
      
  nacos:
    image: nacos/nacos-server:v2.1.1-slim
    container_name: gddst-nacos-dev
    environment:
      - MODE=standalone
      - PREFER_HOST_MODE=hostname
      - SPRING_DATASOURCE_PLATFORM=mysql
      - MYSQL_SERVICE_HOST=mysql
      - MYSQL_SERVICE_PORT=3306
      - MYSQL_SERVICE_DB_NAME=nacos_config
      - MYSQL_SERVICE_USER=root
      - MYSQL_SERVICE_PASSWORD=89225300
      - MYSQL_SERVICE_DB_PARAM=characterEncoding=utf8&connectTimeout=1000&socketTimeout=3000&autoReconnect=true&useSSL=false&allowPublicKeyRetrieval=true
    ports:
      - "8848:8848"
      - "9848:9848"
      - "9555:9555"
    volumes:
      - /usr/local/workspace/nacos/logs:/home/nacos/logs
      - /usr/local/workspace/nacos/data:/home/nacos/data
    depends_on:
      - mysql
      
 gateway:
    image: openjdk:8
    container_name: gateway
    ports:
      - 8080:8080
    environment:
      - nacos_host=nacos
      - nacos_port=8848
    volumes:
      - /usr/local/workspace/app/gddst-cloud-gateway.jar:/app/app.jar
     
  userservice:
    image: openjdk:8
    container_name: userservice
    environment:
      - nacos_host=nacos
      - nacos_port=8848
    volumes:
      - /usr/local/workspace/app/userservice.jar:/app/app.jar
    depends_on:
      - mysql
      - nacos
      
  cardservice:
    image: openjdk:8
    container_name: cardservice
    environment:
      - nacos_host=nacos
      - nacos_port=8848
    volumes:
      - /usr/local/workspace/app/cardservice.jar:/app/app.jar
    depends_on:
      - mysql
      - nacos

如文件中所示:

执行编排容器命令时,会创建一个mysqlnacosuserservicecardservice四个容器。

其中userservicecardservice是自己编写的基于SpringBoot的微服务项目。

这里的部署配置会复杂一些,和文章上部分有所不同,更偏向于实际开发。

按照这个配置,微服务中的pom文件中mysql的依赖需要改成8的版本,同时yml文件的驱动也需要更改。

这些都属于项目基本配置,就不再这里缀述了。

这样编写docker-compose.yml有一些明显的好处:

  • 更容易管理每个微服务的端口、容器名称、环境变量、数据卷等何种参数,可维护性是大大提升的
  • 不再需要把每个微服务的jar搞成一样的名字,可以通过直接看jar包名称就知道是哪个微服务了
  • 不再有那么多重复的Dockerfile文件
  • 今后部署只有在docker-compose.yml中按userservice新增一项配置,并且把它的jar包上传到/usr/local/app下即可

5)上传需要部署的jar文件

根据docker-compose的配置内容,把网关和业务模块所的jar包,

gddst-cloud-gateway.jaruserservice.jarcardservice.jar的三个jar包上传到以下目录:

/usr/local/workspace/app/

6)执行部署命令

docker-compose.yml文件所在目录下执行:

docker-compose up -d

即可完成部署。

写这步更多的是为了这套步骤的完整性、实际一般会使用portainer来进行微服务的可视化部署管理

九、拓展

1)关于能否在一个文件中配置多个相同服务的问题

关于userservicecardservice在一个dcoker-compose.yml文件里也是可以配置多个的。

只需要打出不同端口号的jar包即可。

包括mysql也是,这里只使用了一个,是最简单的格式。即使以后有了主从复制,也可以配置多个mysql

这样就能完成一个更完善一些的集群配置。

2)关于fegin-api模块为什么不需要部署

fegin-api模块只是一个公共模块,被其它微服务所引用。

使用Maven打包SpringBoot项目的时候,有关的Maven依赖会自动打包进当前微服务项目的jar包中。

也就是说,每个依赖了fegin-api模块的微服务的jar包中内部,就已经有了fegin-api模块的内容。