二、脚本式Script
特点:
1.最外层有node{}包裹
2.可直接使用groovy语句
如何创建最基本的PIpeline
直接在Jenkins Web UI 网页界面中输入脚本
通过创建一个jenkinsfile可以检入项目的源代码管理库
通常推荐在Jenkins中直接从源代码控制(SCM)中载入Jenklinsfile Pipeline
脚本式pipeline案例:
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010102020509.png" alt="image-20211010102020509" style="zoom: 67%;" />
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010102132835.png" alt="image-20211010102132835" style="zoom: 67%;" />
1.引用linux命令
node {
stage('step1'){
sh 'touch /home/qf.txt'
sh 'echo "Jenkins-pipeline\ntest1" >> /home/qf.txt'
}
}
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010102215410.png" alt="image-20211010102215410" style="zoom:80%;" />
[root@jenkins-server1 .jenkins]# cat /home/qf.txt
Jenkins-pipeline
test1
如果有jenkins从节点,想要指定在从节点上面执行,可以这样写
node (node-test1) { //括号中,指定从节点名称;
stage('step1'){
sh 'touch /home/qf.txt'
sh 'echo "Jenkins-pipeline\ntest1" >> /home/qf.txt'
}
}
2.设置变量
//为注释,鼠标多行标记,CTRL+/即可
node {
def username = "飞哥" //def可加可不加
stage ('step1') {
print "${username}"
// sh 'touch /home/qf.txt'
// sh 'echo "Jenkins-pipeline\ntest1" >> /home/qf.txt'
}
}
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010103205293.png" alt="image-20211010103205293" style="zoom: 80%;" />
3.自定义分隔符
node {
def username = "飞哥"
value = "****************************************************"
stage ('step1') {
print "${username}"
}
stage ('step2') {
print "${value}"
sh 'echo "youngfit2021"'
}
}
4.列表
node {
def username = "飞哥"
list dest_servers = ["192.168.153.190", "192.168.153.195"]
value = "****************************************************"
stage ('step1') {
print "${username}"
}
stage ('step2') {
print "${value}"
sh 'echo "youngfit2021"'
}
stage ('ping3') {
print "${value}"
String dest_num1 = dest_servers[0]
sh "ping -c3 ${dest_num1}"
}
}
5.for循环,遍历列表
不使用之前
node {
def username = "飞哥"
host1 = "192.168.153.195" //定义多个变量,比较麻烦
host2 = "192.168.153.196"
value = "****************************************************"
stage ('step1') {
print "${username}"
}
stage ('step2') {
print "${value}"
sh 'echo "youngfit2021"'
}
stage ('ping3') {
print "${value}"
sh "ping -c2 ${host1}"
sh "ping -c2 ${host2}"
}
}
可以使用列表
node {
def username = "飞哥"
list dest_servers = ["192.168.153.190", "192.168.153.195"]
value = "****************************************************"
stage ('step1') {
print "${username}"
}
stage ('step2') {
print "${value}"
sh 'echo "youngfit2021"'
}
stage ('ping3') {
print "${value}"
for (i=0; i<dest_servers.size(); i++) {
String dest_num1 = dest_servers[i]
sh "ping -c2 ${dest_num1}"
}
}
}
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010110407525.png" alt="image-20211010110407525" style="zoom: 80%;" />
6.拉取代码
node {
def githubUrl = "https://github.com/bingyue/easy-springmvc-maven"
value = "****************************************************"
stage ('step1') {
print "${value}"
git branch: "master", url: "${githubUrl}"
}
}
我这里用gitee仓库创建了1个私有仓库
仓库url:[email protected]:youngfit/jenkins.git
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010154821140.png" alt="image-20211010154821140" style="zoom:80%;" />
#jenkins服务器制作密钥对
[root@jenkins-server1 <sub>]# yum -y install git
[root@jenkins-server1 </sub>]# git config --global user.name "feige"
[root@jenkins-server1 <sub>]# git config --global user.email "[email protected]"
[root@jenkins-server1 </sub>]# ssh-keygen
#将公钥配置到gitee中
[root@jenkins-server1 ~]# cat /root/.ssh/id_rsa.pub
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCzBgMIt5DPSY8In23zsTtyXcMdGk4AXtJlGBp177qxOYAscKuCycr3CZkH9fjNw/F6QMUcTcT0A4qjBxJdnHvnLfNOp2EwufBjBbWGGeiKNFmicm6slM+HT+JlhbDubUMD9YGi793dT+ie10Xt5veVvVFfjtQ4O2/Ic6mdmJDVajQL5YEaa72lR4rU8DegbY3t8Ux44Kzf1PANhMq3Swmi6q2E8UGjwU1LE1YzPqXO9otoDVDWSN9gNf/jzV/lY+4YMAriaKU+pkTzv3tVrGA/VY6QWxwMCloJY269Ql5dEXOEFNqHzd40vTD1qBmnNuypYOgC8vFh8TNUpie5tUg/ root@jenkins-server1
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010155104690.png" alt="image-20211010155104690" style="zoom: 80%;" />
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010155127188.png" alt="image-20211010155127188" style="zoom:80%;" />
node {
def githubUrl = "[email protected]:youngfit/jenkins.git"
value = "****************************************************"
stage ('step1') {
print "${value}"
git branch: "master", url: "${githubUrl}", credentialsId: '250'
}
}
来到Jenkins服务器查看,代码拉取成功
7.版本参数化构建
jenkins参数化构建
可以用git的分支、标签、修订/commit的版本来进行使用
这里我用的是标签的概念,也让我们再了解git的标签概念
说明"标签就是tag,是开发人员提交代码之前,可以给将要提交的代码打一个tag,比如v1.0,这样容易分辨代码的历史版本"
也就是说,Jenkins可以识别到仓库里面的分支,历史版本commit、和标签;
可以选择任何分支、任何历史版本、任何标签进行构建;所以,一旦新发布的代码有问题,我们还可以利用Jenkins重新构建一次没有问题的代码,确保应用使用正常;感受到jenkins的强大了嘛!!!
Jenkins安装git参数插件“Git Parameter”
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010155607251.png" alt="image-20211010155607251" style="zoom: 67%;" />
7.1标签式参数
添加git参数
标签/tag、每次提交代码的时候,可以打个tag,类似于版本号;这样可以明确历史版本。
首先用1台机器作为git客户端,拉取代码,修改代码,打tag,上传至远程仓库,这里远程仓库我用的仍是gitee。
这里git客户端机器,可以用新的,我这里仍然使用的jenkins服务器,各位应该都能看懂;
[root@git-client <sub>]# yum -y install git
[root@git-client </sub>]# git config --global user.name "jenkins"
[root@git-client <sub>]# git config --global user.email "[email protected]"
[root@git-client </sub>]# git clone [email protected]:youngfit/jenkins.git
仓库里不是代码,我们这里只是一些文件,看实验效果:
<img src="https://gitee.com/youngfit/typora/raw/master/images/image-20211010165008516.png" alt="image-20211010165008516" />
来到gitee页面查看
那么来到jenkins服务器
node {
def githubUrl = "[email protected]:youngfit/jenkins.git"
value = "****************************************************"
stage ('step1') {
print "${value}"
git branch: "master", url: "${githubUrl}"
print "${Tag}"
}
}
其实不是出了问题,他拉取下来了,但是并不会自动切换tag,也就是位置仍然处于master分支,并没有切换到v1.0tag的位置;
#来到Jenkins的工作目录
[root@jenkins-server1 test-p1]# pwd
/root/.jenkins/workspace/test-p1
如果,你想直接拉取之后,并切换到指定的tag版本中,可以这样写
node {
def githubUrl = "[email protected]:youngfit/jenkins.git"
value = "-------------------------------------------"
stage ('step1') {
print "${value}"
git branch: "master", url: "${githubUrl}"
print "${Tag}" //这里打印,只是在页面上显示一下tag,方便我们查看是否生效
sh "git checkout ${Tag}; git branch"
}
}
如果每次推送前都打一次tag,那我们再进行版本切换的时候,也就方便多了,比如开发更新了代码,再次推送,并且打了tag,如果推送的代码有问题,我们可以随时用jenkins进行重新构建;
模拟开发更新代码
标签:也就是开发推送代码之前,我们要和他们沟通,每次推送前要打个tag,也就是给当前即将推送的代码打个版本号,方便后续我们的管理;各位程序猴应该体会到了~~
这就是标签式参数化了,不过这种方式有个小缺陷,不是什么大问题;如果是第一次构建,也就是没有拉取过代码的时候,它是无法识别到仓库中的标签的,因为它根本没有尝试识别过仓库地址,更别说识别到里面的tag了;不过识别不到,我们就点击构建即可,让他拉取一次,第二次就可以识别到了
演示一下:
1.将刚才的pipline任务删除,或者新建1个pipeline任务都可以
我这里删除吧
然后,选择之前的配置,以及标签构建,配置之前的pipline代码
7.2commit/修订式参数
标签式参数搞明白,这个也就容易了;简单说一下就行
node {
def githubUrl = "[email protected]:youngfit/jenkins.git"
value = "-------------------------------------------"
stage ('step1') {
print "${value}"
git branch: "master", url: "${githubUrl}"
print "${Commit}" //这里打印,只是在页面上显示一下commit历史id,方便我们查看是否生效
sh 'git checkout ${Commmit}; git branch'
}
}
所以,Jenkins是可以直接进行版本的切换构建,发布的,只不过我们这里没有设置后续的动作;各位要理解到位;
7.3分支式参数
后续哥再整理!!个人感觉有上面2个,已经够用;
8.脚本式中引用Credentials
其实,私有仓库,上面拉取代码应该是要凭证的,指定拉取代码的用户的公钥,要配置到私有仓库中,私钥要配置Jenkins中。上面gitee,并没有使用,也能正常拉取有点奇怪,应该是gitee没有这个要求,github和gitlab都是有要求的不过我们先不纠结这个;记得都配置就可以了;
我们现在用的是root用户,公钥已经配置到了gitee的配置中,私钥已经配置到了id为1的Credentials中;
下面再pipeline的代码中引用对应的Credentials即可
node {
def githubUrl = "[email protected]:youngfit/jenkins.git"
value = "-------------------------------------------"
stage ('pull code') {
print "${value}"
git branch: "master", url: "${githubUrl}", credentialsId: "1"
}
}
9.定义多版本构建工具
虽然我们的Jenkins服务器上,暂时只有1个版本的jdk、和1个版本的maven工具;但是在公司的Jenkins服务器上,可能会有多个版本的Jdk或者maven工具,因为在构建一些项目代码时,可能需要用到jdk11的新特性,那么Jenkins服务器上就要有jdk11的版本;
#上传不同版本的jdk工具和maven工具包,到Jenkins服务器,解压,进行配置
[root@jenkins-server1 <sub>]# tar -xvzf openjdk-11+28_linux-x64_bin.tar.gz -C /usr/local/
[root@jenkins-server1 </sub>]# tar -xvzf apache-maven-3.5.4-bin.tar.gz -C /usr/local/jdk-11/
node {
value = "-------------------------------------------"
mavenHome = tool "maven-jdk11" //这里tool指的是工具,工具名称和jenkins定义的要对应好
env.MAVEN_HOME = "${mavenHome}"
env.PATH = "${mavenHome}/bin:${env.PATH}"
stage ('test1') {
print "${env.PATH}"
sh "mvn -version"
}
}
#换成maven-jdk8,试试看效果
node {
value = "-------------------------------------------"
mavenHome = tool "maven-jdk8" //这里tool指的是工具,工具名称和jenkins定义的要对应好
env.MAVEN_HOME = "${mavenHome}"
env.PATH = "${mavenHome}/bin:${env.PATH}"
stage ('test1') {
print "${env.PATH}"
sh "mvn -version"
}
}
10.调用Docker容器
调用工具的时候,麻烦点在于,Jenkins服务器上安装对应工具,而且Jenkins服务也要添加上,后续pipeline的代码中,路径也要配置正确;
如果Jenkins服务器不想安装工具,可以使用docker容器的方式,比如拉取jdk的docker镜像,镜像中自然会有jdk工具,然后进行调用;那么Jenkins服务器要安装docker服务,Jenkins也要安装调用docker的插件
[root@jenkins-server1 yum.repos.d]# pwd
/etc/yum.repos.d
[root@jenkins-server1 yum.repos.d]# wget https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
[root@jenkins-server1 yum.repos.d]# yum -y install docker-ce
[root@jenkins-server1 yum.repos.d]# systemctl start docker && systemctl enable docker
10.1安装调用docker的插件
10.2调用node容器
node {
value = "-------------------------------------------"
stage ("test-node") {
print "${value}"
docker.image("node:14-alpine").inside{
sh "node -v"
}
}
}
10.2调用jdk容器
[root@jenkins-server1 ~]# docker pull daocloud.io/ld00000/jdk-8:latest #提前拉取镜像也可以
node {
value = "-------------------------------------------"
stage ('test-jdk8') {
docker.image ("daocloud.io/ld00000/jdk-8:latest").inside("-v /path:/path"){
sh "java -version"
}
}
}
10.2调用maven容器
[root@jenkins-server1 ~]# docker pull maven:latest #提前拉取镜像也可以
node {
value = "-------------------------------------------"
stage ('test-maven') {
print "${value}"
docker.image ("maven:latest").inside("-v /path:/path"){
sh "mvn -v"
}
}
}
总之:想要调用什么工具的命令,就拉取对应的docker镜像,要比安装工具方便的多;注意我们现在调用之后,容器会自动关闭和删除;我们这里没有用工具做具体的运行服务的命令,先感受一下;
10.3withDockerContainer语法风格
node {
withDockerContainer (args: '-e "http_proxy=xxxx" -e "https_proxy=yyyyy" -v "/home:/home"',
image: "maven:latest") {
sh "cd /home && touch qf.txt"
sh "mvn -v"
}
}
// args:添加的参数,可以-v挂载目录,-e设置变量,-p映射端口等
可以看到,jenkins本机保留了文件,成功了
11.发送邮件
前提:Jenkins已安装邮箱插件,Jenkins已配置过关于邮箱的配置
node {
stage ('email-test') {
emailext (
subject: 'test-jenkins',
body: '''云计算,YYds!!!
千锋郑州云计算
享受学习,低调挣钱!!!''',
to: '[email protected]'
)
}
}
邮箱变量
node {
stage ('email-test') {
emailext (
subject: 'test-jenkins',
body: '构建通知:${PROJECT_NAME} - Build # ${BUILD_NUMBER} - ${BUILD_STATUS}!',
to: '[email protected]'
)
}
}