CentOS7中使用Docker部署SpringBoot+Nginx实现负载均衡
前言使用 Docker 部署应用的方式有多种,如每个应用单独部署再连接容器,如 docker-compose...本博客是单独部署的每一个容器。本篇博客的操作有:① 在本地创建两个 SpringBoot 项目(8090 端口和 8091 端口);分别配置 Dockerfile② 把 SpringBoot 项目传输到服务器;打包成 Docker 镜像③ 拉...
前言
使用 Docker 部署应用的方式有多种,如每个应用单独部署再连接容器,如 docker-compose...
本博客是单独部署的每一个容器。
本篇博客的操作有:
① 在本地创建两个 SpringBoot 项目(8090 端口和 8091 端口);分别配置 Dockerfile
② 把 SpringBoot 项目传输到服务器;打包成 Docker 镜像
③ 拉取官方 Nginx 镜像;配置 Nginx 在宿主机上的配置文件
④ 创建网络
⑤ 运行 SpringBoot 容器
⑥ 运行 Nginx 容器
⑦ 访问输出 'Hello Docker !!!server.port:'
源码
GitHub 地址:https://github.com/intomylife/Docker
Docker Hub 地址:
① https://hub.docker.com/r/intomylife/docker-springboot8090
② https://hub.docker.com/r/intomylife/docker-springboot8091
本地创建 SpringBoot 项目
POM 文件
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<!-- 继承父 -->
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.3.RELEASE</version>
</parent>
<!-- 三坐标 -->
<groupId>com.zwc</groupId>
<artifactId>docker-springboot8090</artifactId>
<version>1.0</version>
<!-- 工程名称和描述 -->
<name>docker-springboot8090</name>
<description>使用 Docker 部署 SpringBoot + Nginx 实现负载均衡</description>
<!-- 打包方式 -->
<packaging>jar</packaging>
<!-- 在properties下声明相应的版本信息,然后在dependency下引用的时候用${spring-version}就可以引入该版本jar包了 -->
<properties>
<!-- jdk -->
<java.version>1.8</java.version>
<!-- docker 前缀名,通常用在上传镜像 -->
<docker.image.prefix>intomylife</docker.image.prefix>
<!-- docker 镜像名称 -->
<docker.image.name>docker-springboot8090</docker.image.name>
</properties>
<!-- 加入依赖 -->
<dependencies>
<!-- springboot 依赖 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!-- springboot 测试依赖 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<!-- 插件依赖 -->
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
<!-- Docker 插件 -->
<plugin>
<!-- 三坐标 -->
<groupId>com.spotify</groupId>
<artifactId>docker-maven-plugin</artifactId>
<version>1.1.1</version>
<!-- 配置信息 -->
<configuration>
<!-- 镜像名称 -->
<imageName>${docker.image.prefix}/${docker.image.name}:${project.version}</imageName>
<!-- Dockerfile 文件的位置 -->
<dockerDirectory>src/main/docker</dockerDirectory>
<!-- 文件资源 -->
<resources>
<resource>
<targetPath>/</targetPath>
<directory>${project.build.directory}</directory>
<include>${project.build.finalName}.jar</include>
</resource>
</resources>
<!-- 打包后的名称 -->
<buildArgs>
<JAR_FILE>${project.build.finalName}.jar</JAR_FILE>
</buildArgs>
</configuration>
</plugin>
</plugins>
</build>
</project>
- <docker.image.prefix> Docker 镜像前缀 :一般会被镜像名称节点引用在前面。为仓库的用户名
- <docker.image.name> Docker 镜像名称:为此仓库的名称
- <imageName> 镜像名称:仓库用户名/镜像名称:镜像版本号
- 如果想接下来把打包好的镜像传输到仓库中,那么这里 <imageName> 镜像名称要按照格式来
application.properties
server.port=8090
- 配置了端口
Dockerfile 文件
FROM openjdk:8-jdk-alpine
VOLUME /tmp
ARG JAR_FILE
ADD ${JAR_FILE} app.jar
ENTRYPOINT ["java","-Djava.security.egd=file:/dev/./urandom","-jar","/app.jar"]
- 注意此文件的路径为 :src/main/docker/
- 此文件是构建 Docker 的核心文件
- FROM openjdk:8-jdk-alpine:基础镜像环境 JDK1.8
- VOLUME /tmp:指定了挂载目录
- ARG JAR_FILE:和上面 POM 文件中配置的 buildArgs 对应,动态获取打包后的名称
- ADD ${JAR_FILE} app.jar:把生成的 jar 包拷贝到 Docker 容器中并命名为 app.jar
- 最后一行是修改 Tomcat 随机数生成方式,加快 Tomcat 启动
Controller 前端控制器
package com.zwc.controller;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
/**
* @ClassName HelloDockerController
* @Desc TODO say hello - 前端控制器
* @Date 2019/5/3 17:18
* @Version 1.0
*/
@RestController
public class HelloDockerController {
@Value("${server.port}")
private String port;
/*
* @ClassName HelloDockerController
* @Desc TODO say hello
* @Date 2019/5/3 17:21
* @Version 1.0
*/
@RequestMapping("/")
public String say(){
return "Hello Docker !!!server.port:" + port ;
}
}
- 读取配置文件中的端口,并输出
注:此次部署有两个 SpringBoot 项目,上面只是简单介绍了其中一个,还有另一个只是端口不一样,
其他基本一致。有兴趣可以下载源码查看。
服务器上部署环境
CentOS7中安装Maven3.6.0
CentOS7中安装Docker
传输
1. 打开下载好的 MobaXterm,使用 SSH 连接方式
2. 连接成功后默认到 root 目录
3. MobaXterm 左边是目录,在左边目录的最底部,有个选择框(Follow terminal folder)把它勾选上。
勾选上它后,目录就会跟着你的命令动态发生变化
4. 输入命令 cd /usr/local/ -> 进入目录
5. 输入命令 mkdir JavaWork -> 新建文件夹
6. 输入命令 cd JavaWork -> 进入目录
7. 把本地的 SpringBoot 项目文件夹拖拽到 MobaXterm 左边目录中
8. 传输需要一点点时间,也可以在 MobaXterm 左边目录底部看到传输进度
SpringBoot 项目打包 Docker 镜像
1. 输入命令 cd /usr/local/JavaWork/docker-springboot-nginx/ -> 进入目录
注意: docker-springboot-nginx 是从本地传输到服务器上的 SpringBoot 项目
2. 如果是直接使用我上传的项目源码,这时会有两个文件夹,是两个单独的项目
3. 输入命令 cd docker-springboot8090/ -> 进入工程目录
4. 输入命令 mvn clean -> 清除 target
5. 输入命令 mvn install -> 打 jar 包
6. 输入命令 mvn package docker:build -> 使用 Maven 打包 Docker 镜像
7. 输入命令 cd ../docker-springboot8091/ -> 进入另一个工程目录
8. 输入命令 mvn clean -> 清除 target
9. 输入命令 mvn install -> 打 jar 包
10. 输入命令 mvn package docker:build -> 使用 Maven 打包 Docker 镜像
11. 第一次打包需要一点时间,最后看到 'BUILD SUCCESS' 等字样就证明打包成功了
拉取官方 Nginx 镜像
1. 输入命令 systemctl start docker.service -> 启动 Docker 服务
2. 输入命令 docker pull nginx:1.8 -> 拉取 Nginx 镜像
配置 Nginx 在宿主机上的配置文件
1. 输入命令 cd /usr/local/ -> 进入目录
2. 输入命令 mkdir docker -> 创建文件夹
3. 输入命令 cd docker/ -> 进入目录
4. 轮流输入命令 mkdir nginx、cd nginx、mkdir conf -> 创建 nginx 目录以及 conf 目录
5. 输入命令 cd /usr/local/docker/nginx/conf/ -> 进入目录
6. 输入命令 touch nginx.conf -> 新建文件
7. 输入命令 vim nginx.conf -> 编辑文件,粘贴下面内容
#user nobody;
worker_processes 1;
#error_log logs/error.log;
#error_log logs/error.log notice;
#error_log logs/error.log info;
#pid logs/nginx.pid;
events {
worker_connections 1024;
}
http {
include mime.types;
default_type application/octet-stream;
#log_format main '$remote_addr - $remote_user [$time_local] "$request" '
# '$status $body_bytes_sent "$http_referer" '
# '"$http_user_agent" "$http_x_forwarded_for"';
#access_log logs/access.log main;
sendfile on;
#tcp_nopush on;
#keepalive_timeout 0;
keepalive_timeout 65;
#gzip on;
upstream dispense {
server springboot-8090:8090 weight=1;
server springboot-8091:8091 weight=2;
}
server {
listen 8080;
server_name localhost;
#charset koi8-r;
#access_log logs/host.access.log main;
location / {
proxy_pass http://dispense;
index index.html index.htm;
}
#error_page 404 /404.html;
# redirect server error pages to the static page /50x.html
#
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}
# proxy the PHP scripts to Apache listening on 127.0.0.1:80
#
#location ~ \.php$ {
# proxy_pass http://127.0.0.1;
#}
# pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
#
#location ~ \.php$ {
# root html;
# fastcgi_pass 127.0.0.1:9000;
# fastcgi_index index.php;
# fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name;
# include fastcgi_params;
#}
# deny access to .htaccess files, if Apache's document root
# concurs with nginx's one
#
#location ~ /\.ht {
# deny all;
#}
}
# another virtual host using mix of IP-, name-, and port-based configuration
#
#server {
# listen 8000;
# listen somename:8080;
# server_name somename alias another.alias;
# location / {
# root html;
# index index.html index.htm;
# }
#}
# HTTPS server
#
#server {
# listen 443 ssl;
# server_name localhost;
# ssl_certificate cert.pem;
# ssl_certificate_key cert.key;
# ssl_session_cache shared:SSL:1m;
# ssl_session_timeout 5m;
# ssl_ciphers HIGH:!aNULL:!MD5;
# ssl_prefer_server_ciphers on;
# location / {
# root html;
# index index.html index.htm;
# }
#}
}
- 通过配置 upstream 节点分发请求,达到负载均衡的效果
- 注意 springboot-8090 和 springboot-8091 都是等会启动的 SpringBoot 容器的名称
- 使用 weight 设置权重
- location 节点中配置代理 proxy_pass 为 http://dispense; 即为上面配置 upstream 的名称
- 注意我把默认端口 80 更改为 8080 了,因为我的服务器上 80 端口有别的应用在使用
8. 轮流输入命令 esc -> shift + 冒号 -> wq -> 回车
运行 Docker 镜像
创建网络
1. 输入命令 docker network create --driver bridge nginx_bridge -> 创建网络
2. 输入命令 docker network ls -> 查看网络
运行 SpringBoot 容器
1. 输入命令 docker images -> 查看构建的镜像
2. 输入命令
docker run -p 8090:8090 --name springboot-8090 --network nginx_bridge -d intomylife/docker-springboot8090:1.0
- -p:端口映射(宿主机端口:容器端口)
- --name:启动后的容器名称
- --network:连接到网络
- -d:后台启动
- intomylife/docker-springboot8090:1.0:启动的镜像
3. 输入命令
docker run -p 8091:8091 --name springboot-8091 --network nginx_bridge -d intomylife/docker-springboot8091:1.0
- -p:端口映射(宿主机端口:容器端口)
- --name:启动后的容器名称
- --network:连接到网络
- -d:后台启动
- intomylife/docker-springboot8091:1.0:启动的镜像
运行 Nginx 容器
1. 输入命令 docker images -> 查看构建的镜像
2. 输入命令
docker run -p 8080:8080 --network nginx_bridge --env springboot-8090=springboot-8090 --env springboot-8091=springboot-8091 -v /usr/local/docker/nginx/conf/nginx.conf:/etc/nginx/nginx.conf -d nginx:1.8
- -p:端口映射(宿主机端口:容器端口)
- --network:连接到网络
- --env:配置 Nginx 镜像中 nginx.conf 配置文件中的 SpringBoot 容器名
- springboot-8090:等号前面的为 nginx.conf 配置文件中的 SpringBoot 容器名
- springboot-8090:等号后面的为上面启动的 SpringBoot 容器 --name 名称
- springboot-8091:与 springboot-8090 一致
- -v:映射配置文件(宿主机目录:容器目录)
3. 使用 ip + 8080 访问,看到 'Hello Docker !!!server.port:' + 端口,多刷新几次页面,会发现
8091 端口和 8090 端口出现的频率是 2:1,
如果是这样的话就证明整个部署过程就成功了(注意安全组和端口)
安全组
注:如果服务器是在阿里云租用的需要设置安全组
1. 登录到阿里云
2. 进入到 '云服务器 ECS' 控制台
3. 左侧栏中选择 '实例'
4. 进入实例详情,点击左侧栏中 '本实例安全组'
5. 点击安全组中的 '配置规则'
6. 点击 '添加安全组规则' 按钮
7. 配置 8080 、 8090 和 8091 端口
防火墙
注:如果服务器是在阿里云租用的需要开启防火墙。服务器是默认不开启防火墙的,感觉不安全
1. 输入命令 systemctl status firewalld -> 查看防火墙状态
2. 输入命令 systemctl start firewalld -> 开启防火墙
3. 如果你不想开防火墙的话,那就输入命令 systemctl stop firewalld -> 关闭防火墙
4. 输入命令 systemctl restart firewalld.service -> 重启防火墙
端口
注:端口操作需要在开启防火墙的情况下才能执行成功。如下两条命令只需要执行一组即可
1. 输入命令 firewall-cmd --permanent --zone=public --add-port=8080/tcp -> 永久开放 8080 端口
输入命令 firewall-cmd --permanent --zone=public --add-port=8090/tcp -> 永久开放 8090 端口
输入命令 firewall-cmd --permanent --zone=public --add-port=8091/tcp -> 永久开放 8091 端口
2. 输入命令 firewall-cmd --zone=public --add-port=8080/tcp -> 临时开放 8080 端口
输入命令 firewall-cmd --zone=public --add-port=8090/tcp -> 临时开放 8090 端口
输入命令 firewall-cmd --zone=public --add-port=8091/tcp -> 临时开放 8091 端口
把打包好的镜像传输到仓库中
注:这里选择 Docker Hub 官方仓库
1. 如果没有账号的话先注册一个,填写用户名邮箱及密码等信息提交,到邮箱中确认即可
2. 确保 Docker 服务已经启动:systemctl start docker.service -> 启动 Docker 服务
3. 输入命令 docker login -> 登录 Docker Hub
4. 出现 'Login Succeeded' 等字样就证明登录成功了
5. 输入命令 docker push intomylife/docker-springboot8090:1.0 -> 把镜像传输到仓库中
intomylife 为 Docker Hub 仓库用户名
docker-springboot8090 为 镜像名称
1.0 为镜像版本
6. 在自己的仓库中就可以看到此镜像了,注意此时镜像为公开的
7. 因为我此次打包的 SpringBoot 项目是样例,里面没有很隐私的信息,所以公开的也没关系
如果你不想被别人下载你的镜像,你也可以设置为私有的(貌似有费用),当然也可以搭建私库
把仓库中的公有镜像拉取到服务器中
1. 输入命令 docker pull intomylife/docker-springboot8090:1.0 -> 把镜像拉取到服务器中
intomylife 为 Docker Hub 仓库用户名
docker-springboot8090 为 镜像名称
1.0 为镜像版本
扩展
希望能够帮助到你
over
更多推荐
所有评论(0)