jenkins介绍与操作
Jenkins使用
1.1 Jenkins介绍
JENKINS 是一个用 JAVA 编写的开源的持续集成工具。在与 ORACLE 发生争执后,项目从HUDSON 项目独立出来。 • JENKINS 提供了软件开发的持续集成服务。它运行在 SERVLET 容器中(例如 APACHE TOMCAT)。它支持软件配置管理(SCM)工具(包括 ACCUREV SCM、CVS、SUBVERSION、GIT、PERFORCE、CLEARCASE 和 RTC) ,可以执行基于 APACHE ANT 和 APACHE MAVEN的项目,以及任意的 SHELL 脚本和 WINDOWS 批处理命令。JENKINS 的主要开发者是川口耕介。JENKINS 是在 MIT 许可证下发布的自由软件。
官方网站:https://jenkins.io/
清华镜像地址:https://mirrors.tuna.tsinghua.edu.cn/jenkins
1.2 企业代码上线发展史
代码发布上线是每一个 IT 企业必须要面临的,而且不管是对开发或者是运维来说,代码上线本身就是一个件非常痛苦的事情,很多时候每一次发布都是一次考验。为了提高上线的效率,代码上线的方式,方法,工具也不断的发展,基本上可以分为以下几个阶段:
阶段 1-没有构建服务器
软件在开发者的机器上通过 Ant 或其它脚本手动构建,代码保存在中央源码仓库中,但是开发者不是经常提交本地的修改。每次需要发布的时候,开发者手动合并修改,这个过程是相当痛苦的。
阶段 2-晚上进行构建
在这个阶段,团队有构建服务器,自动化的构建在晚上进行。构建过程只是简单的编译代码,没有可靠的和可重复的单元测试。然而,开发人员每天提交代码。如果某个开发人员提的代码和其他人的代码冲突的话,构建服务器会在第二天通过邮件通知团队。所以又一段时间构建是处于失败状态的。
阶段 3-晚上进行构建并进行自动化测试
团队对 CI 和自动化测试越来越重视。无论什么时候版本管理系统中的代码改变了都会触发编译构建过程,团队成员可以看到是代码中的什么改变触发了这个构建。并且,构建脚本会编译应用并且会执行一系列的单元测试或集成测试。除了邮件,构建服务器还可以通过其他方式通知团队成员,如:IM。失败的构建被快速的修复。
阶段 4-代码质量度量
自动化的代码质量和测试覆盖率的度量手段有助于评价代码的质量和测试的有效性。代码质量的构建会产生 API 文档。
阶段 5-更加认真地对待测试
CI 和测试紧密相关。如今,像测试驱动开发被广泛地使用,使得对自动化的构建更加有信心。应用不仅仅是简单地编译和测试,而是如果测试成功会被自动的部署到一个应用服务器上来进行更多的综合的 end-to-end 测试和性能测试。
阶段 6-验收测试和更加自动化的部署
验收测试驱动的开发被使用,使得我们能够了解项目的状态。这些自动化的测试使用行为驱动的开发和测试驱动的开发工具来作为交流和文档工具,发布非开发人员也能读懂的测试结果报告。由于测试在开发的早起就已经被自动化的执行了,所以我们能更加清楚地了解到什么已经做了,什么还没有做。每当代码改变或晚上,应用被自动化地部署到测试环境中,以供 QA 团队测试。当测试通过之后,软件的一个版本将被手工部署到生产环境中,团队也男孩IT教育可以在出现问题的时候回滚之前的发布。
阶段 7-持续部署
对自动化的单元测试,集成测试和验收测试的信心使得我们可以使用自动化的部署技术将软件直接部署到生产环境中。但是测试还是有可能不能真正的反映现实的环境
1.3 Jenkins安装
1.3.1 环境准备
小硬件需求:256M 内存、1G 磁盘空间,通常根据需要 Jenkins 服务器至少 1G 内存,50G+磁盘空间。
软件需求:由于 jenkins 是使用 java 语言编写的,所以需要安装 java 运行时环境(jdk)
1.3.1 安装JDK
下载JDK https://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html
在/etc/profile中添加
tar xf jdk-8u201-linux-x64.tar.gz
mv jdk1.8.0_201/ /application/
ln -s jdk1.8.0_201/ /application/jdk
编辑/etc/profile文件,进行添加
export JAVA_HOME=/application/jdk
export PATH=$PATH:$JAVA_HOME/bin;
export CLASSPATH=.:$JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jar
source /etc/profile
java -version
下载jenkins
wget https://mirrors.tuna.tsinghua.edu.cn/jenkins/redhat/jenkins-2.170-1.1.n
oarch.rpm
安装jenkins
[root@ci-node2 tools]# rpm -ivh jenkins-2.170-1.1.noarch.rpm
warning: jenkins-2.170-1.1.noarch.rpm: Header V4 DSA/SHA1 Signature, key ID d50582e6: NOKEY
Preparing... ################################# [100%]
Updating / installing...
1:jenkins-2.170-1.1 ################################# [100%]
[root@ci-node2 tools]#
1.3.2 启动、配置jenkins
[root@ci-node2 tools]# systemctl start jenkins
[root@ci-node2 tools]# systemctl enable jenkins
jenkins.service is not a native service, redirecting to /sbin/chkconfig.
Executing /sbin/chkconfig jenkins on
[root@ci-node2 tools]# systemctl status jenkins
● jenkins.service - LSB: Jenkins Automation Server
Loaded: loaded (/etc/rc.d/init.d/jenkins; bad; vendor preset: disabled)
Active: active (running) since Mon 2019-04-01 16:22:16 CST; 23s ago
Docs: man:systemd-sysv-generator(8)
CGroup: /system.slice/jenkins.service
└─10395 /etc/alternatives/java -Dcom.sun.akuma.Daemon=daemonized -Djava.awt.headless=...
Apr 01 16:22:15 ci-node2 systemd[1]: Starting LSB: Jenkins Automation Server...
Apr 01 16:22:15 ci-node2 runuser[10380]: pam_unix(runuser:session): session opened for user j...=0)
Apr 01 16:22:16 ci-node2 jenkins[10375]: Starting Jenkins [ OK ]
Apr 01 16:22:16 ci-node2 systemd[1]: Started LSB: Jenkins Automation Server.
Hint: Some lines were ellipsized, use -l to show in full.
Jenkins 默认监听 8080,服务启动后我们可以在浏览器中输入 http://您服务器的 ip地址:8080 访问 jenkins 服务
此页面要用户选择初始化安装的插件,我们选择跳过此步,后面我们采用其他方式安装插件。进入主页后进行修改admin的密码
1.4 Jenkins插件管理
Jenkins 本身是一个引擎、一个框架,只是提供了很简单功能,其强大的功能都是通过
插件来实现的,jenkins 有一个庞大的插件生态系统,为 Jenkins 提供丰富的功能扩展。下
面我们来介绍常用的几种插件安装方式
1.4.1 自动安装插件
jenkins 主页面,点击系统管理,进入系统管理面面,在右侧选择管理插件:
进入插件管理页面,点击可选插件,选择你需要安装的插件,安装完成后,一般情况下不需要重启Jenkins,具体根据提示操作。
1.4.2 手动安装插件
除了上面的插件安装方法,Jenkins 还为我们提供了手工安装插件的方式,特别是在国内,由于网络的原因,有时候我们使用上述方法安装插件会经常不成功,所以我们可以采用下载插件,然后再上传的方式来安装插件。
官方的插件下载地址:http://updates.jenkins-ci.org/
国内源:https://mirrors.tuna.tsinghua.edu.cn/jenkins/plugins/
如果是在官方网站下载插件,好下载与你 jenkins 版本对应的插件,如果是在清华镜像下载插件,则不存在版本的问题。下载后得到的一个以.hpi 为扩展名的文件
下载 ssh.hpi 后,我们手动安装 ssh 插件,进入到插件管理页面,上传完成后,重新启动 jenkins,完成插件的安装
1.4.3 覆盖插件目录
可以备份已经安装好插件的Jenkins服务器上的/var/lib/jenkins/plugins目录,然后把备份文件上传到我们需要安装插件的新 Jenkins 服务器的对应目录上,然后重启Jenkins。
先在百度网盘中下载 plugins.tar.gz 包,将 plugins.tar.gz 上传至服务器,进行解压后复制到/var/lib/jenkins/plugins目录,重启jenkins
[root@ci-node2 ~]# tar xf plugins.tar.gz
[root@ci-node2 plugins]# mv * /var/lib/jenkins/plugins/
[root@ci-node2 plugins]# systemctl restart jenkins
重启完毕后,查看插件管理,发现已经多了很多的插件
1.5 Jenkins的常用目录及文件
jenkins下一切兼文件,也就是说 jenkins 没有数据库,所有的数据都是以文件的形式存在
查看jenkins目录及文件位置
[root@ci-node2 plugins]# rpm -ql jenkins
/etc/init.d/jenkins
/etc/logrotate.d/jenkins
/etc/sysconfig/jenkins
/usr/lib/jenkins
/usr/lib/jenkins/jenkins.war
/usr/sbin/rcjenkins
/var/cache/jenkins
/var/lib/jenkins
/var/log/jenkins
1.5.1 Jenkins主配置文件
/etc/sysconfig/jenkins 是 Jenkins 的主配置文件:我们在这里主要配置 Jenkins 的工作目录、启动用户、启动端口
Jenkins 默认的用户为 jenkins,生产环境建议使用 jenkins 用户,然后使用 sudo 进行授权,为了避免各种权限问题,改为 root 用户
1.5.2 Jenkins的主目录
/var/lib/jenkins 是 Jenkins 默认配置的主工作目录,我们可以在主配置文件进行设置
[root@ci-node2 plugins]# cd /var/lib/jenkins/
[root@ci-node2 jenkins]# ll
..........
drwxr-xr-x 3 jenkins jenkins 20 Apr 1 17:45 jobs # 存放jobs的配置及每次构建的结果
drwxr-xr-x 121 jenkins jenkins 12288 Apr 2 10:07 plugins # Jenkins的插件目录,存放已安装的插件
drwxr-xr-x 3 jenkins jenkins 56 Apr 1 16:23 users # 存放用户相关的配置文件
drwxr-xr-x 3 jenkins jenkins 20 Apr 1 19:06 workspace # 工作区目录,每次job执行构建的工作目录
1.5.3 Jenkins主程序目录
/usr/lib/jenkins/jenkins.war 是 Jenkins 的主程序
1.5.4 其它目录及文件
/var/log/Jenkins Jenkins 日志文件目录
/etc/init.d/Jenkins Jenkins 启动文件
1.6 Jenkins创建自由风格项目
在 Jenkins 主页面,点击左侧菜单栏的“新建”或者“New job”
进入创建 job 页面
注:1、job 名称需要有规划,以便于后面的权限管理;2、创建 job 后不要轻易更改名称,因为 jenkins 一切皆文件,很多关于 job 的文件,都是以该名称命名,当你改名后,一般不会删除旧文件,而是会再重新创建一份新的文件。
输入 job 名称,选择类型后,点击 OK 后创建 job,进入 job 配置页面,此时在 Jenkins的主目录下的 jobs 目录已经生成了以你 Job 名称命名的文件夹
Job 配置页面,主要包括通用配置、源码管理、构建触发器、构建环境、构建、构建后操作等几个部分,根据你选择的构建类型不同,可能配置项会有一些小的差别
1.6.1 执行linux命令、脚本
通用配置选项卡
勾选“丢弃旧的构建”,这是我们必须提前考虑的重要方面,就是我们如何处理构建历史,构建作业会消耗大理的磁盘空间,尤其是你存储的构建产物(比如执行 java 构建时会生成的 JAR、WAR 等)该选项允许你限制在构建历史记录的作业数。你可以告诉 Jenkins 只保留近的几次构建,或者只保留指定数量的构建,此外,Jenkins 永远不会删除后一个稳定和成功的构建。具体数据的指定要根据你项目的实际情况而定,我一般设置为 5、5
构建部分,选择execute shell
查看输出信息
1.6.2 连接gitlab获取仓库代码
先复制gitlab中的代码地址
然后回到 Jenkins 上 My-web 配置页面,下拉到“源码管理”部分,勾选 git选项
粘贴完仓库地址后,出现如下图所示错误提示
根据提示信息显示为 key 认证失败,因为我们使用的 SSH 方式连接仓库,所以需要配置SSH认证,实际上在前面我们学习Gitlab的时候,我们已经配置ci-node2这台机子的root用户的公钥在 Gitlab 上的 dev 用户,因为jenkins服务启动的用户是jenkins
我们在gitlab上配置的是root用户的公钥,现在有两个种方式可以解决这个问题,1、在jenkins上配置使用root用户的私钥连接gitlab2、配置root用户启动jenkins
第一种方法:
根据提示添加用户认证后,回到配置仓库页面,选择认证方式为新添加的认证,错误消失。
第二种方法:
修改配置/etc/sysconfig/jenkins 文件,配置 Jenkins 的启动用户为 root,然后重启 Jenkins 服务
回到源码管理界面,此时也看不到任何的报错信息
保存配置,点击立即构建,在工作空间里可以看到从gitlab拉取的代码信息
在“源码管理”配置部分,我们可以配置从分支获取代码,也可以配置从标签获取代码、还可以配置从某一次 commit 获取代码,如下图所示
1.6.3 利用linux脚本实现部署
在上面的示例中,我们已经将代码获取至我们 Jenkins 服务器上,由于我们的项目是使用 html 编写的,不需要编译,直接可以打包发布(实际工作中,可能需要更换配置文件)。
1.6.3.1 安装httpd服务
我们在 ci-node1 机子上安装 httpd 服务,并配置服务端口为 10001
[root@ci-node1 git_data]# yum -y install httpd
[root@ci-node1 git_data]# vim /etc/httpd/conf/httpd.conf
........
#Listen 12.34.56.78:80
Listen 10001
[root@ci-node1 git_data]# systemctl start httpd
使用10.0.0.11:10001进行访问
1.6.3.2 配置ssh认证
因为我们要使用脚本将 ci-node2 上的程序代码推送到 ci-node1 上,所以需要配置ci-node2 到 ci-node1 的 ssh 免密码登录
[root@ci-node2 git_data]# ssh-copy-id -i /root/.ssh/id_rsa.pub root@172.16.1.11
/usr/bin/ssh-copy-id: INFO: Source of key(s) to be installed: "/root/.ssh/id_rsa.pub"
/usr/bin/ssh-copy-id: INFO: attempting to log in with the new key(s), to filter out any that are al
ready installed/usr/bin/ssh-copy-id: INFO: 1 key(s) remain to be installed -- if you are prompted now it is to ins
tall the new keysroot@172.16.1.11's password:
Number of key(s) added: 1
Now try logging into the machine, with: "ssh 'root@172.16.1.11'"
and check to make sure that only the key(s) you wanted were added.
[root@ci-node2 git_data]# ssh 172.16.1.11
Last login: Tue Apr 2 14:32:26 2019 from 10.0.0.253
1.6.3.3 编写部署脚本
[root@ci-node2 scripts]# vim deploy.sh
#!/bin/bash
#主机的ip地址
HOST=$1
#job的名称
JOB_NAME=$2
#文件名称
NAME=web-$(date +%F)-$(($RANDOM+10000))
#压缩
cd /var/lib/jenkins/workspace/${JOB_NAME} && tar zcf /opt/${NAME}.tar.gz ./*
#发送到服务器
ssh ${HOST} "cd /var/www && mkdir ${NAME}"
scp /opt/${NAME}.tar.gz ${HOST}:/var/www/${NAME}
#解压
ssh ${HOST} "cd /var/www/${NAME} && tar xf ${NAME}.tar.gz && rm -rf ${NAME}.tar.gz"
#使用软链接进行部署服务
ssh ${HOST} "rm -rf /var/www/html && ln -s /var/www/${NAME} /var/www/html"
1.6.3.4 Jenkins配置构建
在jenkins上进行配置,上面的链接可以查看所有的环境变量
点击立即构建,就会发现web项目已部署好了
1.6.4 Git push 自动触发构建
在上面的 job 中,我们已经成功实现了将 Gitlab 中 monitor 仓库的代码部署到 httpd服务中,但是每次部署需要我们手动去点击“立即构建”,下面我们将实现当 Gitlab 收到push 请求后,就触发 Jenkins 构建,将仓库的变化部署到 httpd 服务中。
1.6.4.1 Jenkins配置构建解发器
在My-web配置界面下
1.6.4.2 gitlab仓库配置
进入 Gitlab 中 monitor 仓库的设置页面
进入集成配置页面,复制 jenkins 触发器配置页面的 url及Token
如遇到以下报错
解决方法
配置完成后,在页面下面测试触发设置
我们在 jenkins job 主页面看到构建任务被触发
接着我们将仓库克隆到客户端,在客户端测试触发 push 操作
[root@ci-node2 test]# git clone git@10.0.0.11:oldboy/monitor.git
Cloning into 'monitor'...
remote: Enumerating objects: 435, done.
remote: Counting objects: 100% (435/435), done.
remote: Compressing objects: 100% (372/372), done.
remote: Total 435 (delta 53), reused 435 (delta 53)
Receiving objects: 100% (435/435), 8.78 MiB | 8.42 MiB/s, done.
Resolving deltas: 100% (53/53), done.
[root@ci-node2 monitor]# vim index.html
[root@ci-node2 monitor]# git add .
[root@ci-node2 monitor]# git commit -m "modify index"
[root@ci-node2 monitor]# git remote add gitlab http://10.0.0.11/oldboy/monitor.git
[root@ci-node2 monitor]# git push -u gitlab
warning: push.default is unset; its implicit value is changing in
Git 2.0 from 'matching' to 'simple'. To squelch this message
and maintain the current behavior after the default changes, use:
git config --global push.default matching
To squelch this message and adopt the new behavior now, use:
git config --global push.default simple
See 'git help config' and search for 'push.default' for further information.
(the 'simple' mode was introduced in Git 1.7.11. Use the similar mode
'current' instead of 'simple' if you sometimes use older versions of Git)
Username for 'http://10.0.0.11': root
Password for 'http://root@10.0.0.11':
Counting objects: 9, done.
Compressing objects: 100% (7/7), done.
Writing objects: 100% (7/7), 2.53 KiB | 0 bytes/s, done.
Total 7 (delta 4), reused 0 (delta 0)
To http://10.0.0.11/oldboy/monitor.git
f6070e1..ff82fb9 master -> master
Branch master set up to track remote branch master from gitlab.
Gitlab 收到本次推送的内容
Jenkins 对应的 job 已经触发构建
网站内容已被更新
同时我们在 jenkins 中 job 主页面的“新修改记录”部分可以看到我们的修改日志
1.6.5 配置构建后操作
1.6.5.1 配置构建后通知gitlab
构建完成后,jenkins 可以把构建的结果反馈给 Gitlab,这样在 Gitlab 上就可以查看每一次 push 后构建的执行结果。
首先在 Jenkins 上配置,可以访问 Gitlab,打开jenkins 系统管理---系统设置页面,下拉找到 Gitlab 部分
添加认证,先在gitlab上生成TOKEN码
复制生成好的TOKEN码Jenkins上
选择TEST进行测试
在my-web的配置页面上进行配置
保存 job 配置,回到 job 主页面,执行“立即构建”。构建成功后,在 Gitlab 仓库,commits
列表页面
可以看到jenkins的日志输出信息
1.6.5.2 配置构建后发送邮件
每次执行完构建任务后,我们都可以通过邮件来通知相关人员构建的执行情况,具体配置如下:
在 jenkins 系统管理—>系统设置
在系统设置中找到 Jenkins Locaction 填好 JenkinsURL 跟系统管理员的邮件地址,注意必填
下拉到下面“邮件通知”部分
进入到my-web配置界面
E-mail Notification 选项配置比较简
当构建失败后,会发邮件通知
Editable Email Notification 配置
2.1 Jenkins创建maven项目
2.1.1 什么是Maven?
Maven 是一个项目管理和综合工具。Maven 提供了开发人员构建一个完整的生命周期框架。开发团队可以自动完成项目的基础工具建设,Maven 使用标准的目录结构和默认构建生命周期。
Maven 简化和标准化项目建设过程。处理编译,分配,文档,团队协作和其他任务的无缝连接。 Maven 增加可重用性并负责建立相关的任务。
Maven 项目的结构和内容在一个 XML 文件中声明,pom.xml 项目对象模型(POM),这是整个 Maven 系统的基本单元。用来管理项目的构建,相关性和文档。强大的功能就是能够自动下载项目依赖库
2.1.2 centos 7下安装maven
2.1.2.1 安装jdk
下载JDK https://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html
在/etc/profile中添加
tar xf jdk-8u201-linux-x64.tar.gz
mv jdk1.8.0_201/ /application/
ln -s jdk1.8.0_201/ /application/jdk
编辑/etc/profile文件,进行添加
export JAVA_HOME=/application/jdk
export PATH=$PATH:$JAVA_HOME/bin;
export CLASSPATH=.:$JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jar
source /etc/profile
java -version
2.1.2.2 获取并安装maven
官网:http://maven.apache.org/download.cgi
清华镜像:https://mirrors.tuna.tsinghua.edu.cn/apache/maven/
[root@ci-node1 tools]# wget https://mirrors.tuna.tsinghua.edu.cn/apache/maven/maven-3/3.6.0/binaries/apache-maven-3.6.0-bin.tar.gz
[root@ci-node1 tools]# tar xf apache-maven-3.6.0-bin.tar.gz
[root@ci-node1 tools]# mv apache-maven-3.6.0 /application/
[root@ci-node1 tools]# cd /application/
[root@ci-node1 application]# ln -s /application/apache-maven-3.6.0/ /application/maven
[root@ci-node1 application]# /application/maven/bin/mvn -v
Apache Maven 3.6.0 (97c98ec64a1fdfee7767ce5ffb20918da4f719f3; 2018-10-25T02:41:47+08:00)
Maven home: /application/maven
Java version: 1.8.0_201, vendor: Oracle Corporation, runtime: /usr/java/jdk1.8.0_201-amd64/jre
Default locale: en_US, platform encoding: UTF-8
OS name: "linux", version: "3.10.0-957.el7.x86_64", arch: "amd64", family: "unix"
#加入环境变量配置
[root@ci-node1 application]# vim /etc/profile
export PATH=/application/maven/bin/:$PATH
[root@ci-node1 application]# source /etc/profile
2.1.3 认识maven安装目录
[root@ci-node1 application]# cd /application/maven/
[root@ci-node1 maven]# ll
total 28
lrwxrwxrwx 1 root root 32 Apr 2 18:49 apache-maven-3.6.0 -> /application/apache-maven-3.6.0/
drwxr-xr-x 2 root root 97 Apr 2 18:48 bin # 这些脚本用来配置 java 命令,准备好 classpath和相关的 Java 系统属性,然后执行 Java 命令。其中 mvn 是基于 UNIX 平台的脚本,mvn.bat是基于 Windows 平台的脚本
drwxr-xr-x 2 root root 42 Apr 2 18:48 boot # 该目录只包含一个文件,该文件是一个类加载器框架,Maven 使用该框架加载自己的类
drwxr-xr-x 3 501 games 63 Oct 25 02:38 conf # 该目录包含了一个非常重要的文件settings.xml。用于全局定义 Maven 的行为。也可以将该文件复制到~/.m2/目录下,在用户范围内定制 Maven 行为
drwxr-xr-x 4 501 games 4096 Apr 2 18:48 lib # 该目录包含了所有 Maven 运行时需要的 Java 类库
-rw-r--r-- 1 501 games 13439 Oct 25 02:43 LICENSE
-rw-r--r-- 1 501 games 182 Oct 25 02:43 NOTICE
-rw-r--r-- 1 501 games 2530 Oct 25 02:38 README.txt
[root@ci-node1 maven]#
2.1.4 maven常用命令
mvn clean:命令用于清理项目生产的临时文件,一般是模块下的target目录
mvn package:命令用于项目打包,会在模块下的 target 目录生成 jar 或者 war 等文件
mvn test:命 令 用 于 测 试 , 用 于 执 行 src/test/java/ 下 的 测 试 用 例 , 使 用-Dmaven.test.skip=true
mvn install:命令用于模块安装,将打包好的 jar/war 文件复制到你的本地仓库中,供其它模块使用
2.1.5 Maven仓库
在 Maven 中,任何一个依赖、插件或者项目构建的输出,都可以称之为构件。Maven 在某个统一的位置存储所有项目的共享的构件,这个统一的位置,我们就称之为仓库。(仓库就是存放依赖和插件的地方)任何的构件都有唯一的坐标,Maven 根据这个坐标定义了构件在仓库中的唯一存储路径。
Maven 仓库分为两类:本地仓库和远程仓库。远程仓库又可以大致分为以下三类:中央仓库,这是 Maven 核心自带的远程仓库,它包含了绝大部分开源的构件;私服是一种特殊的远程仓库,一般是为了节省带宽和时间,在企业局域网内架设的一个私有仓库服务器(如nexus)用其代理所有外部的远程仓库,内部的项目还可以部署到私服上供其他项目使用;还有就是其他的公开的远程仓库,常见的有 Java.net Maven 库、JBoss Maven 库等
默认配置下,Maven 根据坐标寻找构件的时候,首先他会查看本地仓库,如果本地仓库存在,则直接使用;如果本地仓库不存在,则 Maven 就会去远程仓库查找,存在则先下载到本地仓库使用,不存在 Maven 就会报错。
2.1.5.1 本地仓库
顾名思义,就是 Maven 在本地存储构件的地方。maven 的本地仓库,在安装 maven 后并不会创建,它是在第一次执行 maven 命令的时候才被创建。maven 本地仓库的默认位置:无论是 Windows 还是 Linux,在用户的目录下都有一个.m2/repository/的仓库目录,这就是Maven 仓库的默认位置。这个可以通过修改.m2/settings.xml 文件(不存在可以创建)或者maven 安装目录/conf/settings.xml 进行配置
在 settings.xml 文件中,设置localRepository 元素的值为想的仓库地址即可
<settings>
<localRepository>/opt/maven_repository</localRepository>
</settings>
建议修改.m2 目录下的 setting.xml 文件,修改只针对用户
2.1.5.2 远程仓库
说到远程仓库先从核心的中央仓库开始,中央仓库是默认的远程仓库,maven 在安装的时候,自带的就是中央仓库的配置,所有的 maven 项目都会继承超级 pom,具体的说,包含了下面配置的 pom 我们就称之为超级 pom
<repositories>
<repository>
<id>central</id>
<name>CentralRepository</name> <url>http://repo.maven.apache.org/maven2</url>
<layout>default</layout>
<snapshots>
<enabled>false</enabled>
</snapshots>
</repository>
</repositories>
中央仓库包含了绝大多数流行的开源 Java 构件,以及源码、作者信息、SCM、信息、许可证信息等。一般来说,简单的 Java 项目依赖的构件都可以在这里下载得到。
私服是一种特殊的远程仓库,它是架设在局域网内的仓库服务,私服代理广域网上的远程仓库,供局域网内的 Maven 用户使用。当 Maven 需要下载构件的时候,它从私服请求,如果私服上不存在该构件,则从外部的远程仓库下载,缓存在私服上之后,再为 Maven 的下载请求提供服务。我们还可以把一些无法从外部仓库下载到的构件上传到私服上。
Maven 私服的 个特性:
1.节省自己的外网带宽:减少重复请求造成的外网带宽消耗
2.加速 Maven 构件:如果项目配置了很多外部远程仓库的时候,构建速度就会大大降低
3.部署第三方构件:有些构件无法从外部仓库获得的时候,我们可以把这些构件部署到内部仓库(私服)中,供内部 maven 项目使用
4.提高稳定性,增强控制:Internet 不稳定的时候,maven 构建也会变的不稳定,一些私服软件还提供了其他的功能
5.降低中央仓库的负荷:maven 中央仓库被请求的数量是巨大的,配置私服也可以大大降低中央仓库的压力当前主流的 maven 私服:1.Apache的Archiva、2.JFrog 的 Artifactory3.Sonatype
的Nexus
2.1.5.3 配置使用远程仓库
在平时的开发中,我们往往不会使用默认的中央仓库,默认的中央仓库访问的速度比较慢,访问的人或许很多,有时候也无法满足我们项目的需求,可能项目需要的某些构件中央仓库中是没有的,而在其他远程仓库中有,如 JBoss Maven 仓库。这时,可以在 pom.xml中配置该仓库,代码如下:
<!-- 配置远程仓库 -->
<repositories>
<repository>
<id>jboss</id>
<name>JBoss Repository</name>
<url>http://repository.jboss.com/maven2/</url>
<releases>
<enabled>true</enabled>
<updatePolicy>daily</updatePolicy>
</releases>
<snapshots>
<enabled>false</enabled>
<checksumPolicy>warn</checksumPolicy>
</snapshots>
<layout>default</layout>
</repository>
</repositories>
repository:在 repositories 元素下,可以使用 repository 子元素声明一个或者多个远程仓库。
id:仓库声明的唯一 id,尤其需要注意的是,Maven 自带的中央仓库使用的 id 为 central,如果其他仓库声明也使用该 id,就会覆盖中央仓库的配置。
name:仓库的名称,让我们直观方便的知道仓库是哪个,暂时没发现其他太大的含义。
url:指向了仓库的地址,一般来说,该地址都基于 http 协议,Maven 用户都可以在浏览器中打开仓库地址浏览构件。
releases 和 snapshots:用来控制 Maven 对于发布版构件和快照版构件的下载权限。需要注意的是 enabled 子元素,该例中 releases 的 enabled 值为 true,表示开启 JBoss 仓库的发布版本下载支持,而 snapshots 的 enabled 值为 false,表示关闭 JBoss 仓库的快照版本的下载支持。根据该配置,Maven 只会从 JBoss 仓库下载发布版的构件,而不会下载快照版的构件。
layout:元素值default表示仓库的布局是Maven2及Maven3的默认布局,而不是Maven1的布局。基本不会用到 Maven1 的布局。
其他:对于 releases 和 snapshots 来说,除了 enabled,它们还包含另外两个子元素updatePolicy 和 checksumPolicy。
元素 updatePolicy 用来配置 Maven 从远处仓库检查更新的频率,默认值是 daily,表示 Maven 每天检查一次。其他可用的值包括:never-从不检查更新;always-每次构建都检查更新;interval:X-每隔 X 分钟检查一次更新(X 为任意整数)。
元素 checksumPolicy 用来配置 Maven 检查校验和文件的策略。当构建被部署到 Maven仓库中时,会同时部署对应的检验和文件。在下载构件的时候,Maven 会验证校验和文件,如果校验和验证失败,当 checksumPolicy 的值为默认的 warn 时,Maven 会在执行构建时输出警告信息,其他可用的值包括:fail-Maven 遇到校验和错误就让构建失败;ignore-使Maven 完全忽略校验和错误
3.1 利用Nexus搭建Maveny库
3.1.1 Nexus介绍
Nexus 是一个强大的 Maven 仓库管理器,它极大地简化了本地内部仓库的维护和外部仓库的访问。
Nexus 在代理远程仓库的同时维护本地仓库,以降低中央仓库的负荷,节省外网带宽和时间。
Nexus 是一套“开箱即用”的系统不需要数据库,它使用文件系统加 Lucene 来组织数据。
Nexus 使用 ExtJS 来开发界面,利用 Restlet 来提供完整的 REST APIs,通过 m2eclipse与 Eclipse 集成使用。
Nexus 支持 WebDAV 与 LDAP 安全身份认证。
Nexus 还提供了强大的仓库管理功能,构件搜索功能,它基于 REST,友好的 UI 是一个
extjs 的 REST 客户端,它占用较少的内存,基于简单文件系统而非数据库。
3.1.2 安装JDK
因上一次安装过了,此处略
[root@ci-node2 ~]# java -version
java version "1.8.0_201"
Java(TM) SE Runtime Environment (build 1.8.0_201-b09)
Java HotSpot(TM) 64-Bit Server VM (build 25.201-b09, mixed mode)
3.1.3 安装nexus
下载地址:https://www.sonatype.com/download-oss-sonatype
[root@ci-node2 tools]# tar xf nexus-3.15.2-01-unix.tar.gz
[root@ci-node2 tools]# mv nexus-3.15.2-01 /application/
[root@ci-node2 tools]# cd /application/
[root@ci-node2 application]# ln -s nexus-3.15.2-01/ /application/nexus
[root@ci-node2 application]# /application/nexus/bin/nexus start
WARNING: ************************************************************
WARNING: Detected execution as "root" user. This is NOT recommended!
WARNING: ************************************************************
Starting nexus
[root@ci-node2 application]# /application/nexus/bin/nexus status
WARNING: ************************************************************
WARNING: Detected execution as "root" user. This is NOT recommended!
WARNING: ************************************************************
nexus is running.
上面启动成功后会警告不要使用 root 用户启动,这里可以新建一个用户,也可以指定root 用户启动,使他不出现警告,下面配置指定 root 用户启动,编辑 bin 目录下的 nexus.rc文件,修改内容为:run_as_user="root"
3.1.4 配置Maven项目使用Nexus仓库
在 maven 的 setting.xml 文件中配置私服配置,这种方式配置后所有本地使用该配置的maven 项目的 pom 文件都无需配置私服下载相关配置
在<profiles></profiles>之间加入下面的配
<profile>
<id>my-nexus</id>
<repositories>
<!-- 私有库地址-->
<repository>
<id>nexus</id>
<name>nexus</name>
<url>http://10.0.0.12:8081/repository/maven-public/</url>
<snapshots>
<enabled>true</enabled>
</snapshots>
<releases>
<enabled>true</enabled>
</releases>
</repository>
</repositories>
<pluginRepositories>
<!--插件库地址-->
<pluginRepository>
<id>nexus</id>
<url>http://10.0.0.12:8081/repository/maven-public/</url>
<releases>
<enabled>true</enabled>
</releases>
<snapshots>
<enabled>true</enabled>
</snapshots>
</pluginRepository>
</pluginRepositories>
</profile>
</profiles>
在<settings></settings>之间加入下面的配置,激活使用上面的配置
<activeProfiles>
<activeProfile>my-nexus</activeProfile>
</activeProfiles>
注:profile 名字要对应
在<mirros></mirros>之间加入如下配置
<mirror>
<id>nexus-myself</id>
<!--*指的是访问任何仓库都使用我们的私服-->
<mirrorOf>*</mirrorOf>
<name>Nexus myself</name>
<url>http://10.0.0.12:8081/repository/maven-public/</url>
</mirror>
配置完成后,当我们再次执行 mvn 命令时,下载构件的地址变为我们的私服地址
我们的私服也缓存了相应的构件在本地
4.1 创建Maven Job
1、在 Gitlab 创建一个 java 的代码仓库,我们把前面在命令使用的 helloword 项目初始化为一个 git 仓库,然后 push 到我们的 Gitlab 上
[root@ci-node2 tools]# cd hello-world/
[root@ci-node2 hello-world]# git init
Initialized empty Git repository in /server/tools/hello-world/.git/
[root@ci-node2 hello-world]# git remote add origin http://10.0.0.11/root/hello_world.git
[root@ci-node2 hello-world]# git add .
[root@ci-node2 hello-world]# git commit -m "Initial commit"
[master (root-commit) 322526c] Initial commit
3 files changed, 84 insertions(+)
create mode 100644 pom.xml
create mode 100644 src/main/java/com/juvenxu/mvnbook/helloworld/HelloWorld.java
create mode 100644 src/test/java/com/juvenxu/mvnbook/helloworld/HelloWorldTest.java
[root@ci-node2 hello-world]# git push -u origin master
Username for 'http://10.0.0.11': root
Password for 'http://root@10.0.0.11':
Counting objects: 18, done.
Compressing objects: 100% (6/6), done.
Writing objects: 100% (18/18), 1.77 KiB | 0 bytes/s, done.
Total 18 (delta 0), reused 0 (delta 0)
To http://10.0.0.11/root/hello_world.git
* [new branch] master -> master
Branch master set up to track remote branch master from origin.
2、在 jenkins 配置 maven,打开系统管理—>全局工具配置页面,下拉新增一个 maven 配置
3、回到 Jenkins 主页面,点击“新建 Item”进入创建 Job 页面
4、通用部分配置“丢弃旧的构建”
5、源码管理配置从 git 仓库获取我们 helloword 仓库的代码
6、配置要执行的 maven 命令,保存配置,返回 job 主页面,执行构建。
7、在“工作空间”我们可以看到构建后的产物
4.1 Jenkins创建Pipline项目
4.1.1 Jenkins Pipline简介
Jenkins pipeline 是 Jenkins 2.0 的精髓,是帮助 Jenkins 实现 CI 到 CD 转变的重要角色。简单来说,就是一套运行于 Jenkins 上的工作流框架,将原本独立运行于单个或者多个节点的任务连接起来,实现单个任务难以完成的复杂发布流程。Pipeline 的实现方式是一套 Groovy DSL,任何发布流程都可以表述为一段 Groovy 脚本,并且 Jenkins 支持从代码库直接读取脚本,从而实现了 Pipeline as Code 的理念
4.1.2 Pipline基本概念
Node:一个 Node 就是一个 Jenkins 节点,可以是 Master,也可以是 Slave,是 Pipeline
中具体 Step 的运行环境。
Stage:一个 Pipeline 有多个 Stage 组成,每个 Stage 包含一组 Step。注意一个 Stage
可以跨多个 Node 执行,即 Stage 实际上是 Step 的逻辑分组。
Step:是基本的运行单元,可以是创建一个目录、从代码库中 checkout 代码、执行一个 shell 命令、构建 Docker 镜像、将服务发布到 Kubernetes 集群中。Step 由 Jenkins 老男孩IT教育和 Jenkins 各种插件提供
4.1.3 Jenkinsfile语法
Jenkins Pipeline 支持两种语法,一种 Declarative Pipeline(声明式),一种 Scripted Pipeline(脚本式)。 声明式的 Pipeline 限制用户使用严格的预选定义的结构,是一种声明式的编程模型,对比脚本式的 Pipeline 学习起来更加简单;脚本式的 Pipeline 限制比较少,结构和语法的限制由 Groovy 本身决定,是一种命令式的编程模型。所以我们学习使用声明式的方式编写jenkinsfile。一般来说 jenkinsfile 会被放在代码库的根目录下。当然也可以在 Web 页面定义
Jenkinsfile (声明式)
pipeline{
agent any
stages{
stage("get code"){
steps{
echo "get code from scm"
}
}
stage("package"){
steps{
echo "packge code"
}
}
stage("deploy"){
steps{
echo "deploy packge to node1"
}
}
}
}
声明式的Pipeline有严格的预定义格式结构,外层必须是pipeline{},紧接着是 agent 指示 Jenkins 分配一个执行器和工作空间来执行下面的 Pipeline,stages和steps是申明式Jenkinsfile必须的,所有的stage必须要定义在stages里,每一个stage下的 step 要定义在一个 steps 里
Jenkinsfile( 脚本式 )
node {
stage('Build') {
//
}
stage('Test') {
//
}
stage('Deploy') {
//
}
}
在脚本式 jenkinsfile 里,你可以定义一个 node 或者多个 node 块,然后在 node 块里定义你的 stage,在 stage 里定义你的 step 即可
4.1.4 Popeline Job 示例
1、登录到 jenkins 主页面,点击左侧菜单栏的 New Item,进入到新建 Job 页面,输入 job 名称,在下面选择 Pipeline 类型,然后点击 OK
2、打开 Pipeline 配置页面,点 Pipeline 选项卡,下拉到 pipeline 部分,选择 pipeline script,在页面定义 jenkinsfile 的方式,在脚本框输入下面的内容
pipeline{
agent any
stages{
stage("get code"){
steps{
echo "get code from scm"
}
}
stage("package"){
steps{
echo "packge code"
}
}
stage("deploy"){
steps{
echo "deploy packge to node1"
}
}
}
}
3、保存后回到 Job 主页面,点击“立即构建”,构建执行完成后,在页面的右侧以图形的形式显示pipeline 的结构,点击对应的位置可以查看构建执行的情况
4、在构建历史处,点击#1 查看这次构建的运行情况,点击“console output”可以看到 Pipeline 的详细运行情况。
4.1.5 通过 scm 获取 Jenkinsfile
1、在 gitlab 上的 monitor 仓库的根目录下创建一个 Jenkins 文件,文件的内容为:
pipeline{
agent any
stages{
stage("get code"){
steps{
echo "get code from scm"
}
}
stage("package"){
steps{
echo "packge code"
}
}
stage("deploy"){
steps{
echo "deploy packge to node1"
}
}
}
}
3、Jenkins 新建一个 pipeline job,命名为 My-pipeline01,在 My-pipeline-job01 的配置页面,点击 Pipeline 选项卡,下拉到pipeline 部分,选择从 scm 获取 pipeline script,如图下示
4、保存配置后,回到 Job 主页面,执行“立即构件”,在”console output”中,我们可以看到,首先从 gitlab 仓库获取了所有的代码文件,然后识别到 Jenkins 文件,执行文件中定义的构建任务
4.1.6 Pipeline 语法生成器
随着 Pipeline 一起发布的内建的文档,使得创建复杂的 Pipelines 更加容易。内建的文档可以根据安装在 Jenkins 实例中的插件,被自动生成和更新。内建的文档可以通过链接被找到: localhost:8080/pipeline-syntax/。假设你已经有了一个正运行在本地 8080 端口上的实例。同样的文档可以连接到这里,通过任何项目的左边菜单”Pipeline Syntax“
4.1.7 使用 pipeline 实现 monitor 仓库代码的发布
1、在 Gitlab 在 monitor 仓库的根目录上添加 Jenkinsfile 文件,文件内容如下:
pipeline{
agent any
stages{
stage("get code"){
steps{
checkout([$class: 'GitSCM', branches: [[name: '*/master']], doGenerateSubmoduleConfigurations: false, extensions: [], submoduleCfg: [], userRemoteConfigs: [[url: 'git@10.0.0.11:oldboy/monitor.git']]])
}
}
stage("package"){
steps{
sh 'cd /var/lib/jenkins/workspace/My-pipeline01 && tar czf /opt/web-$(date +%F).tar.gz ./* --exclude=./git --exclude=Jenkinsfile'
sh 'ssh 172.16.1.11 "cd /var/www && mkdir web-$(date +%F)"'
sh 'scp /opt/web-$(date +%F).tar.gz 172.16.1.11:/var/www/web-$(date +%F)'
}
}
stage("deploy"){
steps{
sh 'ssh 172.16.1.11 "cd /var/www/web-$(date +%F) && tar xf web-$(date +%F).tar.gz && rm -rf web-$(date+%F).tar.gz"'
sh 'ssh 172.16.1.11 "cd /var/www && rm -rf html && ln -s /var/www/web-$(date +%F) /var/www/html"'
}
}
}
}
2、新建job项目,选择pipeline类型,进入配置界面,如下图
3.保存后选择立即构建,查看输出,代码已成功部署
5.1 Jenkins 权限管理
Jenkins 本身自带安全管理的功能,但是一般情况下很少去使用,更多是使用插件的方式进行更加灵活的处理。
Jenkins 的权限管理需要依赖 Jenkins 的权限管理插件。通过配置插件 role-base,可以很方便给不同用户不同 job 的管理和执行权限。
5.1.1 插件的安装与配置
在系统管理、插件管理中搜索 role-base 插件,可以进行安装,插件安装完成之后
全局安全”中启用插件,打开“系统管理->全局安全配置”页面,选择授权策略为“Role Based Strategy”
保存退出后,在系统管理页面出现一个角色管理工具,点击进入之后,就可以对我们的用户进行权限配置。
5.1.2 创建用户与权限分配
1、,在“系统管理”中,选择“管理用户”
2.新建用户
3、进行权限分配,在“系统管理”,选择“Manage and Assign Roles”进入角色管理页
4、点击“Manage Role”,创建一个全局的 dev 角色,授权只读的权限
5、在“角色管理页面”,选择“Assign Roles”,将 dev 用户赋予 dev 角色
6、使用 dev 用户登录,发现没有任何 job,因为还没有为 dev 用户配置查看的 job 的权限(ps:之前 admin 或 root 的权限选项不要移除,否则这些用户可能无法登录)
7、回到角色管理页面,添加一个 dev 的 job 角色,使用正则表达式匹配 dev 角色可以管理的 job 的名称
8、在“Assign Roles”页面,将刚才创建的 job 角色配置给 dev 用户
9、再次使用 dev 用户登录 jenkins,即可以看到匹配到的 job,而且可以执行配置的操作
6.1 Jenkins 备份、升级、迁移
6.1.1 升级
下载新版 Jenkins.war 文件,替换旧版本 war 文件,重启即可。Jenkins.war 文件的位置一般为/usr/lib/jenkins/Jenkins.war
6.1.2 迁移、备份
Jenkins 的所有的数据都是以文件的形式存放在JENKINS_HOME 目录中。所以不管是迁移还是备份,只需要操作 JENKINS_HOME 就行。建议将JENKINS_HOME 打包后在拷贝,windows上可以用 zip,rar 等,Linux 上有 zip,tar 等。然后将打包的文件解压到新的 JENKINS_HOME目录就行了
6.1.3 使用 thinbackup 插件备份
1、安装thinbackup插件,按照之前的插件流程安装即可
2、配置插件
3、手动备份
4、查看备份的目录
6.1.4 恢复备份
1、我们删除/var/lib/jenkins/jobs目录下的所有文件
2、选择Restore
3、选择最后一次备份,进行恢复
4、再查看var/lib/jenkins/jobs目录