当前位置:   article > 正文

DockerCompose - 微服务项目部署全过程(最佳实践)_docker-compose编排部署项目

docker-compose编排部署项目

目录

一、微服务项目部署

1.1、项目介绍

1.2、准备 MySQL 初始化文件

1.3、pom.xml 插件

1.4、测试工作

1.5、编写 Dockerflie 文件

1.6、编写 DockerCompose.yml 文件

1.7、修改 application.yml 文件

1.8、打包上传服务器

1.9、微服务,启动!

1.10、测试结果


一、微服务项目部署


1.1、项目介绍

a)技术选型:SpringCloud 2021.0.1 、SpringCloud Alibaba 2021.0.1.0、SpringBoot 2.6.3、Docker & DockerCompose、JDK 17.

b)软件环境:MySQL、Nacos.

c)服务拆分:blog、user、gateway.

d)其他模块:common(公共模块)、OpenFeign.

e)父项目 pom.xml 配置:

  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <project xmlns="http://maven.apache.org/POM/4.0.0"
  3. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  4. xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  5. <modelVersion>4.0.0</modelVersion>
  6. <groupId>com.cyk</groupId>
  7. <artifactId>cloud_blog</artifactId>
  8. <version>1.0-SNAPSHOT</version>
  9. <packaging>pom</packaging>
  10. <modules>
  11. <module>user</module>
  12. <module>blog</module>
  13. <module>openfeign</module>
  14. <module>common</module>
  15. <module>gateway</module>
  16. </modules>
  17. <parent>
  18. <groupId>org.springframework.boot</groupId>
  19. <artifactId>spring-boot-starter-parent</artifactId>
  20. <version>2.6.3</version>
  21. <relativePath/> <!-- lookup parent from repository -->
  22. </parent>
  23. <properties>
  24. <java.version>17</java.version>
  25. <mybatis-spring-boot.version>2.3.1</mybatis-spring-boot.version>
  26. <mysql.version>5.1.49</mysql.version>
  27. <spring-cloud.version>2021.0.1</spring-cloud.version>
  28. <spring-cloud-alibaba.version>2021.0.1.0</spring-cloud-alibaba.version>
  29. </properties>
  30. <!--维护依赖-->
  31. <dependencyManagement>
  32. <dependencies>
  33. <!-- spring-cloud -->
  34. <dependency>
  35. <groupId>org.springframework.cloud</groupId>
  36. <artifactId>spring-cloud-dependencies</artifactId>
  37. <version>${spring-cloud.version}</version>
  38. <type>pom</type>
  39. <scope>import</scope>
  40. </dependency>
  41. <!-- spring-cloud-alibaba -->
  42. <dependency>
  43. <groupId>com.alibaba.cloud</groupId>
  44. <artifactId>spring-cloud-alibaba-dependencies</artifactId>
  45. <version>${spring-cloud-alibaba.version}</version>
  46. <type>pom</type>
  47. <scope>import</scope>
  48. </dependency>
  49. <!--mybatis-->
  50. <dependency>
  51. <groupId>org.mybatis.spring.boot</groupId>
  52. <artifactId>mybatis-spring-boot-starter</artifactId>
  53. <version>${mybatis-spring-boot.version}</version>
  54. </dependency>
  55. <!--mysql-->
  56. <dependency>
  57. <groupId>mysql</groupId>
  58. <artifactId>mysql-connector-java</artifactId>
  59. <version>${mysql.version}</version>
  60. </dependency>
  61. <!--spring-boot-test-->
  62. <dependency>
  63. <groupId>org.springframework.boot</groupId>
  64. <artifactId>spring-boot-starter-test</artifactId>
  65. <scope>test</scope>
  66. </dependency>
  67. <!--mybatis-test-->
  68. <dependency>
  69. <groupId>org.mybatis.spring.boot</groupId>
  70. <artifactId>mybatis-spring-boot-starter-test</artifactId>
  71. <version>${mybatis-spring-boot.version}</version>
  72. <scope>test</scope>
  73. </dependency>
  74. </dependencies>
  75. </dependencyManagement>
  76. </project>

Ps:麻雀虽小,五脏俱全~   如果还有其他中间件(RabbitMQ、ES......)需要部署,如果人不是小傻瓜,都能配出来~

1.2、准备 MySQL 初始化文件

a)当我们把项目部署到云服务上之后,数据库可能是空的,因此强烈建议提前编写好 SQL 文件,之后就可以通过 docker-compose.yml 的 volumes 映射 docker 的 mysql 初始化脚本文件,完成初始化操作.

b)db.sql 文件如下

  1. create database if not exists demo;
  2. use demo;
  3. drop table if exists user;
  4. create table user (
  5. id bigint primary key auto_increment comment '自增主键id',
  6. username varchar(20) not null unique comment '用户名',
  7. password varchar(20) not null comment '密码',
  8. create_time datetime default now() comment '创建时间',
  9. update_time datetime default now() comment '修改时间'
  10. );
  11. drop table if exists blog;
  12. create table blog (
  13. id bigint primary key auto_increment comment '自增主键',
  14. userId bigint not null comment '用户id',
  15. title varchar(32) not null comment '标题',
  16. content varchar(256) not null comment '正文',
  17. read_count bigint default 0 comment '阅读量',
  18. create_time datetime default now() comment '创建时间',
  19. update_time datetime default now() comment '修改时间'
  20. );
  21. insert into user(username, password) values('cyk', '1111');
  22. insert into blog(userId ,title, content) values(1, '今天真开心', '今天真开行啊,我要好好学习,然后晚上出去玩!');

c)docker 根据别名创建目录默认在 /var/lib/docker/volumes/ 中,因此可以在此目录创建一个 mysql-init 文件夹(将来 docker-compose 文件需要挂载的宿主机数据卷),在将 db.sql 文件放入该文件夹中即可.

  1. ➜ mysql-init pwd
  2. /var/lib/docker/volumes/mysql-init
  3. ➜ mysql-init ll
  4. 总用量 4.0K
  5. -rw-r--r--. 1 root root 1.1K 1月 13 22:23 db.sql
  6. ➜ mysql-init cat db.sql
  7. create database if not exists demo;
  8. use demo;
  9. drop table if exists user;
  10. create table user (
  11. id bigint primary key auto_increment comment '自增主键id',
  12. username varchar(20) not null unique comment '用户名',
  13. password varchar(20) not null comment '密码',
  14. create_time datetime default now() comment '创建时间',
  15. update_time datetime default now() comment '修改时间'
  16. );
  17. drop table if exists blog;
  18. create table blog (
  19. id bigint primary key auto_increment comment '自增主键',
  20. userId bigint not null comment '用户id',
  21. title varchar(32) not null comment '标题',
  22. content varchar(256) not null comment '正文',
  23. read_count bigint default 0 comment '阅读量',
  24. create_time datetime default now() comment '创建时间',
  25. update_time datetime default now() comment '修改时间'
  26. );
  27. insert into user(username, password) values('cyk', '1111');
  28. insert into blog(userId ,title, content) values(1, '今天真开心', '今天真开行啊,我要好好学习,然后晚上出去玩!');

1.3、pom.xml 插件

所有需要运行的微服务都需要有这个插件(父工程不需要任何插件),否则找不到程序入口,没法编译运行(如下图).

插件如下:

  1. <build>
  2. <plugins>
  3. <plugin>
  4. <groupId>org.springframework.boot</groupId>
  5. <artifactId>spring-boot-maven-plugin</artifactId>
  6. </plugin>
  7. </plugins>
  8. </build>

1.4、测试工作

强烈建议,先把需要运行的微服务的 jar 包,都在本地通过 java -jar 运行一下,检查是否能运行成功,这是一个好习惯~

1.5、编写 Dockerflie 文件

a)user 微服务

  1. FROM openjdk:17
  2. # 指定容器工作目录为 apps
  3. WORKDIR /apps
  4. EXPOSE 9090
  5. # 将宿主机上的 ./user-1.0-SNAPSHOT.jar 文件拷贝到容器的工作目录下,并改名为 user.jar
  6. COPY ./user-1.0-SNAPSHOT.jar ./user.jar
  7. # --spring.profiles.active=prod 表示按照 application-prod.yml 配置文件加载
  8. ENTRYPOINT ["java", "-jar", "user.jar", "--spring.profiles.active=prod"]

b)blog 微服务

  1. FROM openjdk:17
  2. # 指定容器工作目录为 apps
  3. WORKDIR /apps
  4. # 将宿主机上的 ./blog-1.0-SNAPSHOT.jar 文件拷贝到容器的工作目录下,并改名为 blog.jar
  5. COPY blog-1.0-SNAPSHOT.jar blog.jar
  6. EXPOSE 9091
  7. # --spring.profiles.active=prod 表示按照 application-prod.yml 配置文件加载
  8. ENTRYPOINT ["java", "-jar", "/apps/blog.jar", "--spring.profiles.active=prod"]

c)gateway 微服务

  1. FROM openjdk:17
  2. # 指定容器工作目录为 apps
  3. WORKDIR /apps
  4. # 将宿主机上的 ./gateway-1.0-SNAPSHOT.jar 文件拷贝到容器的工作目录下,并改名为 gateway.jar
  5. COPY ./gateway-1.0-SNAPSHOT.jar ./gateway.jar
  6. EXPOSE 10010
  7. # --spring.profiles.active=prod 表示按照 application-prod.yml 配置文件加载
  8. ENTRYPOINT ["java", "-jar", "gateway.jar", "--spring.profiles.active=prod"]

1.6、编写 DockerCompose.yml 文件

a)强烈建议:学过 DockerCompose 的朋友可能都知道有个配置叫做 "depends_on",可以指定容器的启动顺序,但是并不能指定谁先启动完成!!! 是不稳定的!!!因此强烈建议编写两个 DockerCompose 文件,一个是 docker-compose.env.yml(运行必备环境),另一个是 docker-compose.service.yml(微服务),部署的时候只需要启动 env,完成后再启动 service 即可.

b)docker-compose.env.yml 文件如下:

  1. version: "3"
  2. networks:
  3. blog_net:
  4. volumes:
  5. data:
  6. init:
  7. services:
  8. nacos:
  9. image: nacos/nacos-server:1.4.2
  10. ports:
  11. - "8848:8848"
  12. environment:
  13. - "MODE=standalone"
  14. restart: always
  15. networks:
  16. - blog_net
  17. mysql:
  18. image: mysql:5.7
  19. ports:
  20. - "3306:3306"
  21. environment:
  22. - "MYSQL_ROOT_PASSWORD=1111"
  23. volumes:
  24. - /root/cyk/cloud_blog/mysql/data:/var/lib/mysql # 映射数据,防止容器重启丢失数据
  25. - /root/cyk/cloud_blog/mysql/init:/docker-entrypoint-initdb.d
  26. restart: always
  27. networks:
  28. - blog_net

Ps:docker-retrypoint-initdb.d 是 Docker 官方 MySQL 镜像的目录,用于初始化数据库和表,因此通过映射我们配置好的初始化文件 mysql-init,就可以实现自定义初始化数据库和表.

如果需要执行多个脚本文件(sql 文件)来初始化数据库,可以使用以下方法:

  1. 将 sql 文件以数字开头命名,例如 001_create_table.sql、002_insert_data.sql.
  2. 数字小的优先执行.

c)docker-compose.service.yml 文件如下:

  1. version: "3"
  2. networks:
  3. blog_net:
  4. services:
  5. gateway: # 网关
  6. build:
  7. context: ./gateway
  8. dockerfile: Dockerfile
  9. ports:
  10. - "10010:10010"
  11. networks:
  12. - blog_net
  13. blog: # 博客服务
  14. build:
  15. context: ./blog
  16. dockerfile: Dockerfile
  17. ports:
  18. - "9091:9091"
  19. networks:
  20. - blog_net
  21. user: # 用户服务
  22. build:
  23. context: ./user
  24. dockerfile: Dockerfile
  25. ports:
  26. - "9090:9090"
  27. networks:
  28. - blog_net

1.7、修改 application.yml 文件

a)强烈建议:提供两个配置文件,一个处理开发环境,另一个处理生产环境(线上环境). 这样本地测试和线上测试就不用老去修改配置文件,关键不小心还容易改错~

b)例如 user 微服务,当前项目需要修改的就是 nacos 和 mysql 连接地址,都修改为 docker-compose 文件中配置的服务Id 名称即可(前提是配置了 networks 在同一网络下):

开发环境如下

  1. server:
  2. port: 9090
  3. spring:
  4. application:
  5. name: user-server
  6. cloud:
  7. nacos:
  8. server-addr: localhost:8848
  9. datasource:
  10. url: jdbc:mysql://localhost:3306/demo?characterEncoding=utf8&useSSL=false
  11. username: root
  12. password: 1111
  13. driver-class-name: com.mysql.jdbc.Driver
  14. # 时间处理
  15. jackson:
  16. date-format: yyyy-MM-dd
  17. time-zone: GMT+8
  18. # mybatis xml save path
  19. mybatis:
  20. mapper-locations: classpath:mapper/*Mapper.xml
  21. configuration:
  22. log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
  23. logging:
  24. pattern:
  25. dateformat: HH:mm:ss
  26. level:
  27. com:
  28. cyk: debug

生产环境如下

  1. server:
  2. port: 9090
  3. spring:
  4. application:
  5. name: user-server
  6. cloud:
  7. nacos:
  8. server-addr: nacos:8848
  9. datasource:
  10. url: jdbc:mysql://mysql:3306/demo?characterEncoding=utf8&useSSL=false
  11. username: root
  12. password: 1111
  13. driver-class-name: com.mysql.jdbc.Driver
  14. # 时间处理
  15. jackson:
  16. date-format: yyyy-MM-dd
  17. time-zone: GMT+8
  18. # mybatis xml save path
  19. mybatis:
  20. mapper-locations: classpath:mapper/*Mapper.xml
  21. configuration:
  22. log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
  23. logging:
  24. pattern:
  25. dateformat: HH:mm:ss
  26. level:
  27. com:
  28. cyk: debug

1.8、打包上传服务器

a)强烈建议:打包前先 clean,避免一些不必要的缓存 class 干扰.

b)打包

b)上传时,建议按服务名称分包,因为每个 Dockerfile 构建成镜像时会把所有工作目录下的所有 Dockerfile 文件都加载一遍,因此不要都放一个目录下,而是分开放.

1.9、微服务,启动!

a)先启动 env 环境容器.

  1. ➜ cloud_blog docker-compose -f docker-compose.env.yml up -d
  2. [+] Running 24/24
  3. ⠿ mysql Pulled 57.7s
  4. ⠿ 72a69066d2fe Pull complete 31.9s
  5. ⠿ 93619dbc5b36 Pull complete 31.9s
  6. ⠿ 99da31dd6142 Pull complete 32.1s
  7. ⠿ 626033c43d70 Pull complete 32.2s
  8. ⠿ 37d5d7efb64e Pull complete 32.2s
  9. ⠿ ac563158d721 Pull complete 36.7s
  10. ⠿ d2ba16033dad Pull complete 36.7s
  11. ⠿ 0ceb82207cd7 Pull complete 36.7s
  12. ⠿ 37f2405cae96 Pull complete 56.7s
  13. ⠿ e2482e017e53 Pull complete 56.7s
  14. ⠿ 70deed891d42 Pull complete 56.7s
  15. ⠿ nacos Pulled 64.8s
  16. ⠿ 5ad559c5ae16 Pull complete 23.7s
  17. ⠿ aa9bf71274b4 Pull complete 23.7s
  18. ⠿ 039d8b3d6a90 Pull complete 62.4s
  19. ⠿ c96722e52477 Pull complete 62.8s
  20. ⠿ 93185cc2628e Pull complete 63.6s
  21. ⠿ 6ddaf1829637 Pull complete 63.8s
  22. ⠿ af68d9507f36 Pull complete 63.9s
  23. ⠿ 2684f86bd7ff Pull complete 63.9s
  24. ⠿ b3c841104577 Pull complete 63.9s
  25. ⠿ a0643cc92b59 Pull complete 63.9s
  26. ⠿ a6a1256662e3 Pull complete 63.9s
  27. [+] Running 5/5
  28. ⠿ Network cloud_blog_blog_net Created 0.1s
  29. ⠿ Volume "cloud_blog_mysqlData" Created 0.0s
  30. ⠿ Volume "cloud_blog_mysql-init" Created 0.0s
  31. ⠿ Container cloud_blog-mysql-1 Started 1.3s
  32. ⠿ Container cloud_blog-nacos-1 Started 1.2s

b)启动 service 服务容器

  1. ➜ cloud_blog docker-compose -f docker-compose.service.yml up -d
  2. [+] Building 44.8s (18/18) FINISHED
  3. => [cloud_blog_user internal] load .dockerignore 0.0s
  4. => => transferring context: 2B 0.0s
  5. => [cloud_blog_blog internal] load .dockerignore 0.0s
  6. => => transferring context: 2B 0.0s
  7. => [cloud_blog_gateway internal] load build definition from Dockerfile 0.0s
  8. => => transferring dockerfile: 511B 0.0s
  9. => [cloud_blog_gateway internal] load .dockerignore 0.0s
  10. => => transferring context: 2B 0.0s
  11. => [cloud_blog_user internal] load build definition from Dockerfile 0.0s
  12. => => transferring dockerfile: 491B 0.0s
  13. => [cloud_blog_blog internal] load build definition from Dockerfile 0.0s
  14. => => transferring dockerfile: 499B 0.0s
  15. => [cloud_blog_blog internal] load metadata for docker.io/library/openjdk:17 16.3s
  16. => [cloud_blog_blog 1/3] FROM docker.io/library/openjdk:17@sha256:74bad65c9e59d6410bdd67d71a14e14175ddd33d654419ecfabf03ddbe70fff4 27.6s
  17. => => resolve docker.io/library/openjdk:17@sha256:74bad65c9e59d6410bdd67d71a14e14175ddd33d654419ecfabf03ddbe70fff4 0.0s
  18. => => sha256:74bad65c9e59d6410bdd67d71a14e14175ddd33d654419ecfabf03ddbe70fff4 1.29kB / 1.29kB 0.0s
  19. => => sha256:ab43cabb2140ecf2fc1b32b4981ead56960a59e5b64f742ad30ada7e47bb8870 954B / 954B 0.0s
  20. => => sha256:5f94f53bbced4225dbe770cd98834716ed540315bf131b38a648378c418a6012 4.45kB / 4.45kB 0.0s
  21. => => sha256:155aced2666332ddff5a741b0236f360820e7aa3fc3dde2224fc17a91fc48db6 42.11MB / 42.11MB 15.0s
  22. => => sha256:ac5901c58ecb29b61159b5e3a63dfbb0fb520b2de1d33c9fb038d9b697e3fcd4 13.52MB / 13.52MB 7.6s
  23. => => sha256:6b1076e441ffb58eee60f1bab40db6ca69a01e33346eff212eac1191e6b754bd 187.17MB / 187.17MB 23.7s
  24. => => extracting sha256:155aced2666332ddff5a741b0236f360820e7aa3fc3dde2224fc17a91fc48db6 2.4s
  25. => => extracting sha256:ac5901c58ecb29b61159b5e3a63dfbb0fb520b2de1d33c9fb038d9b697e3fcd4 0.6s
  26. => => extracting sha256:6b1076e441ffb58eee60f1bab40db6ca69a01e33346eff212eac1191e6b754bd 3.9s
  27. => [cloud_blog_gateway internal] load build context 1.0s
  28. => => transferring context: 37.22MB 1.0s
  29. => [cloud_blog_blog internal] load build context 1.1s
  30. => => transferring context: 42.58MB 1.1s
  31. => [cloud_blog_user internal] load build context 0.9s
  32. => => transferring context: 42.58MB 0.9s
  33. => [cloud_blog_gateway 2/3] WORKDIR /apps 0.2s
  34. => [cloud_blog_blog 3/3] COPY blog-1.0-SNAPSHOT.jar blog.jar 0.5s
  35. => [cloud_blog_gateway 3/3] COPY ./gateway-1.0-SNAPSHOT.jar ./gateway.jar 0.5s
  36. => [cloud_blog_user 3/3] COPY ./user-1.0-SNAPSHOT.jar ./user.jar 0.5s
  37. => [cloud_blog_user] exporting to image 0.1s
  38. => => exporting layers 0.1s
  39. => => writing image sha256:c339d5ec9b3dc9cb81d033b31eafab456e534527923f5df7c479e4e383d19c28 0.0s
  40. => => naming to docker.io/library/cloud_blog_user 0.0s
  41. => [cloud_blog_gateway] exporting to image 0.1s
  42. => => exporting layers 0.1s
  43. => => writing image sha256:b06ecc27be3690c5d345bd042143ca7d72cf1e55f165e46678f92ea2bc39914b 0.0s
  44. => => naming to docker.io/library/cloud_blog_gateway 0.0s
  45. => [cloud_blog_blog] exporting to image 0.1s
  46. => => exporting layers 0.1s
  47. => => writing image sha256:75d36043551d0200ab71694078530806f3b5846e03551f06042771597bb07179 0.0s
  48. => => naming to docker.io/library/cloud_blog_blog 0.0s
  49. WARN[0044] Found orphan containers ([cloud_blog-nacos-1 cloud_blog-mysql-1]) for this project. If you removed or renamed this service in your compose file, you can run this command with the --remove-orphans flag to clean it up.
  50. [+] Running 3/3
  51. ⠿ Container cloud_blog-blog-1 Started 0.9s
  52. ⠿ Container cloud_blog-user-1 Started 0.8s
  53. ⠿ Container cloud_blog-gateway-1 Started 0.8s
  54. ➜ cloud_blog docker ps -a
  55. CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
  56. af78c01da9fd cloud_blog_user "java -jar user.jar …" 50 seconds ago Up 48 seconds 0.0.0.0:9090->9090/tcp, :::9090->9090/tcp cloud_blog-user-1
  57. 9b1e12367d13 cloud_blog_gateway "java -jar gateway.j…" 50 seconds ago Up 48 seconds 0.0.0.0:10010->10010/tcp, :::10010->10010/tcp cloud_blog-gateway-1
  58. 74a33d6ecd62 cloud_blog_blog "java -jar /apps/blo…" 50 seconds ago Up 48 seconds 0.0.0.0:9091->9091/tcp, :::9091->9091/tcp cloud_blog-blog-1
  59. 32c9be5f7372 nacos/nacos-server:1.4.2 "bin/docker-startup.…" About a minute ago Up About a minute 0.0.0.0:8848->8848/tcp, :::8848->8848/tcp cloud_blog-nacos-1
  60. 74830ac95115 mysql:5.7 "docker-entrypoint.s…" About a minute ago Up About a minute 0.0.0.0:3306->3306/tcp, :::3306->3306/tcp, 33060/tcp cloud_blog-mysql-1

c)注意:如果在此过程中,操作失误了,例如上传了错误的 jar 包,并且还运行过了,但你知道他是错误的,接着你重新上传 jar 包.

此时!!!一定要执行一次 build 命令重新构建!!!否则执行的还是旧的 jar 包(docker 会把执行执行过的容器的镜像保存下载,下次执行会直接通过之前运行过的镜像来运行)

例如是 service 容器中的 jar 重新上传了,那么就执行以下指令重新构建,之后再运行即可.

docker-compose -f docker-compose.service.yml build

1.10、测试结果

通过网关访问以下:

声明:本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:【wpsshop博客】
推荐阅读
相关标签
  

闽ICP备14008679号