关键词:
Docker 学习 | 第八篇:Docker + Jenkins单机部署Spring Boot项目
前言
最近学了一段时间的jenkins
以及Docker
之后,自己进行了一些自动持续集成的相关实践。
在这里记录一下。
环境
本文所需环境如下:
CentOs 7
系统- 已安装
Docker
- 已安装配置完毕
jenkins
。包括全局工具配置中的JDK
、Git
、Maven
实现思路
通过在项目根目录下面维护一个Dockerfile
以及一个shell
脚本来完成以下工作:
- 构建项目
- 停止旧版本容器
- 移除旧版本容器
- 移除旧版本镜像
- 使用Dockerfile构建新的镜像
- 运行新的容器
Dockerfile内容
在项目根目录有一个Dockerfile
文件:
# 以 java8镜像为基础构建
FROM java:8-jre
# 描述信息
MAINTAINER wangjianfeng <xxxx@qq.com>
# 声明变量代表jar包的名字和端口号
ARG jarname
ARG port
# 添加当前目录下的jar文件到容器中的目录下
COPY ./target/$jarname /app/
# 指定容器内部时间
COPY /localtime /etc/localtime
# 指定容器内部时区
RUN echo "Asia/Shanghai" > /etc/timezone
# 声明暴露的端口
EXPOSE $port
# 声明启动容器的执行命令
ENTRYPOINT ["java","-Xmx200m", "-jar"]
通过上面的注释可以理解大概的意思。
通过传进来的参数指定应用程序的端口号,以及jar
包的文件名,以便于将jar
包复制到镜像中。
额外的配置了容器的时区以及时间(使用本机的),最后声明了容器启动的命令。
Shell脚本内容
在项目根目录中有一个start.sh
文件:
set +e
# 本脚本负责构建,移除旧的docker镜像,使用Dockfile构建镜像,创建容器
# 脚本接受2个参数,第一个为工作目录 第二个为profile
# 项目名称
name="xxxxxx"
# 项目版本
version="1.0"
# 工作目录为第一个参数
log_dir=$1;
# 环境为第二个参数
profile=$2
# 端口
port=8115
#jar包的文件名
jar_name=$name"-"$version".jar"
# 容器名字
container_name=$profile"-"$name
# 镜像名字
image_name=$profile"-"$name":v"$version
echo "Build Project......"
# 构建
mvn clean package -D maven.test.skip=true
runningContainer=`docker ps -a | grep $name`
# 检查容器是否在运行,停止容器,移除容器,删除镜像
if [ -n "$runningContainer" ]; then
echo "Stop container "$container_name
docker stop $container_name
echo "Remove container "$container_name
docker rm $container_name
echo "Remove image "$image_name
docker rmi $image_name
fi
echo "Build container from Dockerfile."
# 拷贝当前时间到工作目录,便于docker构建
cp /usr/share/zoneinfo/Asia/Shanghai ./localtime
# 构建
docker build --build-arg jarname=$jar_name --build-arg port=$port -t $image_name .
#删除文件
rm -f ./localtime
echo "Run the container for image name:"$image_name
# 运行容器指定暴露的端口和挂载的目录
docker run -d --name $container_name --net=host -v $log_dir/logs:/logs $image_name /app/$jar_name --spring.profiles.active=$profile
# 移除无用的镜像
if [ ! -n "$(docker images -f "dangling=true" -q)" ]; then
docker rmi $(docker images -f "dangling=true" -q);
else
echo "Not exists unused Images.";
fi;
该脚本声明了项目名称以及版本号,同时接受两个参数来指定log
的目录以及SpringBoot
项目的profiles
。
上面代码也挺简单,就是指定了一些基本参数之后,停止容器,然后删除容器,移除镜像。
接着拷贝本机时间到当前目录,然后执行Dockerfile
的构建。
构建的时候会传进去两个参数,分别为jar
包名称以及log
的目录。(这里要根据项目不同的日志配置修改哦。我的日志默认是打在容器的/logs
目录,所以就挂载该目录)
构建镜像完毕之后,移除时间文件,然后直接启动容器,把相应的目录挂载到容器,容器的网络模式我这里为了方便直接使用host
模式,在镜像名字后面跟着的是运行容器的参数。因为我声明的运行命令为:
ENTRYPOINT ["java","-Xmx200m", "-jar"]
所以最终容器运行的命令会变成:
java -Xmx200m -jar /app/$jar_name --spring.profiles.active=$profile
配置jenkins
配置jenkins
也非常简单,只需要在构建栏添加Execute shell
,然后填入一下内容:
chmod 777 start.sh
./start.sh /var/log/xxxx staging
上面命令会修改start.sh
的文件权限,然后执行它,后面两个参数分别代表log文件的目录,以及SpringBoot
的profiles
参数。
这样配置起来整个流程就能工作了。
总结
本文记录了使用jenkins
配合Docker
持续集成SpringBoot
项目的一些实践。
python学习第八篇:requests库学习(代码片段)
Python学习第八篇:requests库学习活动地址:CSDN21天学习挑战赛——这里主要学习requests这个http模块,该模块主要用于发送请求获取响应urlib模块也可以实现request模块s能实现的功能,但是用的最多的还是requests模... 查看详情
jenkis+svn+docker(代码片段)
安装jenkis下载jenkins镜像 wget-0/etc/yum.repos.d/jenkins.repohttps://pkg.jenkins.io/redhat/jenkins.repo下载jenkins密钥 rpm--importhttps://pkg.jenkins.io/redhat/jenkins.io.key安装jdk环境tarzxvfjdk1.8.0_131 查看详情
vue.js学习笔记第八篇组件
全局注册组件<!DOCTYPEhtml><html><head><metacharset="utf-8"><title></title><scriptsrc="https://unpkg.com/vue"></script></head><body><divid="app- 查看详情
springcloud学习第八篇:stream学习(greenwich.sr1版本)
一、Stream简介 应用程序通过inputs或者outputs来与SpringCloudStream中binder交互,通过我们配置来binding,而SpringCloudStream的binder负责与消息中间件交互。所以,我们只需要搞清楚如何与SpringCloudStream交互就可以方便使用消息驱动的方... 查看详情
springcloud学习第八篇:gateway学习(hoxton.sr4)
网关的主要作用协议转换,路由转发流量聚合,对流量进行监控,日志输出作为整个系统的前端工程,对流量进行控制,有限流的作用作为系统的前端边界,外部流量只能通过网关才能访问系统可以在网关层做权限的判断可以在... 查看详情
linux学习第八篇之文件搜索命令find
一、find命令:(Windows搜索小工具推荐——Everything) 命令名称:find 命令所在路径:/bin/find 执行权限:所有用户 语法:find[搜索范围][匹配条件] 功能描述:文件搜索二、find命令的例子: 1、find/etc-na... 查看详情
第八篇css定位
...两个字,同学们应该就能清楚,它能够做什么。 在刚学习的时候,我也经常使用定位,来控制元素的位置,但是初学的同学可能会注意不到定位的一些“内涵”!所以会出现一些明显的错误,也不知道怎么去修正它,那么下... 查看详情
第八篇:异常处理
第八篇:异常处理 PYTHON-异常处理 查看详情
python学习第八篇:requests库学习(代码片段)
Python学习第八篇:requests库学习活动地址:CSDN21天学习挑战赛——这里主要学习requests这个http模块,该模块主要用于发送请求获取响应urlib模块也可以实现request模块s能实现的功能,但是用的最多的还是requests模... 查看详情
深入学习jquery选择器系列第八篇——过滤选择器之伪子元素选择器
×目录[1]通用形式[2]反向形式[3]首尾元素[4]唯一元素前面的话 本文是子元素选择器的续篇,主要介绍关于nth-of-type()选择器的内容。该部分内容并非没有出现在《锋利的jQuery》一书中,nth-of-type()选择器参照CSS中的nth-of-type... 查看详情
第八篇vggnet——网络实战
文章目录摘要1项目结构 查看详情
vue学习之路第八篇:事件修饰符(代码片段)
学习准备:①、顾名思义,“事件修饰符”那么肯定是用来修饰事件,既然和事件有关系,那么肯定和“v-on”指令(也可简写为:@)有关系了。②、事件修饰符有以下几类: .stop:阻止冒泡 .prevent:阻止默认事件 .ca... 查看详情
activemq学习第八篇:messaage(代码片段)
MessaageProperties:??ActiveMQ支持很多消息属性,具体可以参考http://activemq.apache.org/activemq-message-properties.html??常见得一些属性说明:queue得消息默认是持久化得消息得优先级默认是4.消息发送时设置了时间戳。消息的过期时间默认是永... 查看详情
第八篇vggnet——网络实战
文章目录摘要1项目结构2划分训练集和测试集3计算mean和Standard3.1标准化的作用3.2归一化的作用4训练4.1导入项目使用的库4.2设置随机因子 查看详情
第八篇vggnet——网络实战
文章目录摘要1项目结构2划分训练集和测试集3计算mean和Standard3.1标准化的作用3.2归一化的作用4训练4.1导入项目使用的库4.2设置随机因子 查看详情
第八篇:grub加密
1.grub加密是为了阻止在开机时用户进入单用户模式,任意键进入下图,【e】进入修改init值=1加密方法: (1)比如密码123456,生成它的密文方法: (2)在/etc/grub.conf文件中加入密码123456的密文,如图: 查看详情
第八篇:socket网络编程
一、网络编程简绍二、socket连接过程三、socket文件传输四、socket循环接收五、socket粘包处理六、FTP文件传输七、socketServer实战练习:FTP服务器编写 查看详情
第八篇测试
sublime使用技巧1:安装漂亮的编程字体http://pan.baidu.com/s/1xMex9下载"程序编写字体–YaheiConsolasHybrid",双击安装2:解压sublime到你的程序目录,如D:/programefiles/3:ctrl+b打开浏览器,如果你已经安装apache,nginx等,并假设你的www目录为D:\www\编辑subl... 查看详情