zoukankan      html  css  js  c++  java
  • Bamboo自动化部署

    问题

    现有的状态:需要部署最新代码时,手动在Bamboo上trigger build,然后手动到Nexus目录下下载tar包,然后手动用Filezila上传到Server对应目录下,解压后运行。

    期望达成的状态:需要部署最新代码时,直接在Server上跑一个脚本,然后它会自动下载并解压。

    分析

    对于存在的问题,将其细化拆分,逐个分析解决方案。

    问题1:需要每次手动trigger build。
    解决1:在Bamboo上设置自动化的build schedule。

    问题2:需要手动下载并解压build好的tar包。
    解决2:写一个download package的脚本。

    至此,上述的问题已经得到解决。

    解决

    Fix 1: Configure build schedule -> Bamboo

    Bamboo -> Action/Configure Branch -> Plan Configuration -> Triggers -> Add trigger

    Bamboo上的trigger build strategy(笔者认为)可以分为两大类:一是poll build,去poll repo,有change的话就build。二是fix build,受到trigger后一定会做一个build,不管有没有change。
    而这两大类有有各种细分:比如按频率来算,每小时一次。比如按时间来算,早晚8点一次。比如设置一个规则,满足条件的话trigger。具体的可以看这里:Triggering builds - Bamboo Support

    bamboo-build

    总的来说,Bamboo的设置还是比较容易上手的。

    Fix 2: Add download script -> shell

    shell script可以分为三个部分,第一部分,读取输入参数。这里主要用到了getopts这个命令。

    ## get input params
    while getopts hxp:b: arg; do
    case $arg in
    	h)
    	echo "downloadsnap [-x (extract after download)] [-p <package-name>] [-b <branch>]"
    	exit
    	;;
    	p)
    	package=$OPTARG
    	;;
    	x)
    	extract=1
    	;;
    	b)
    	branch=/$OPTARG
    	;;
    esac
    done
    

    第二部分,实现核心逻辑,即下载。这里主要用到了wget命令。

    ## search on nexus and download latest snapshots
    mkdir snaptemp
    rm ./download_info.txt 2> /dev/null
    date +%x_%H:%M:%S:%N >>download_info.txt
    pkglst=$(wget -r -A package.tarxxx -P snaptemp --no-parent http://path/to/repo/${branch}/path/to/project/ 
    	|& grep some_key_word | awk '{print $NF}' | sort -V | awk -F '/' '{ map[$(NF-2)]=$0;} END{for( key in map) print map[key];}' | grep -i "$package")
    echo "$pkglst" | while read line; do
    	echo $line
    	wget -r -A package.tar -P snaptemp --no-parent $line 
    done
    

    第三部分,后续一些清理工作。这里主要是清理文件(mv,rm),解压缩(tar)。

    ## move from temp folder to base folder and extract
    for f in $(find snaptemp -name *package.tar); do
    	rm ./$(basename $f) &>/dev/null||:
    	mv $f $(basename $f)
    	if [[ $extract -eq 1 ]]
    	then
    		tar xvf $(basename $f)
    		rm ./$(basename $f) &>/dev/null||:
    	fi
    done
    rm -rf ./snaptemp
    

    注:一些具体的路径名和其它细节已经隐去,不过大体实现的思路和逻辑都描述出来了。写任何的script,大都可以分为以上三块:读取输入,处理,清理环境。

    优化

    在实现的过程中,又发现一个问题,即所有build好的snapshot文件上传的路径都是一样的。如下在pom.xml中的定义:

    <distributionManagement>
    	<repository>
    		<id>my-releases</id>
    		<name>My Releases</name>
    		<url>http://path/to/my/releases</url>
    	</repository>
    	<snapshotRepository>
    		<id>my-snapshots</id>
    		<name>My Snapshots</name>
    		<url>http://path/to/my/snapshots</url>
    	</snapshotRepository>
    </distributionManagement>
    

    当大家都用的是一个git branch的时候,完全没有问题,但是如果有多个branch同时开发并需要联动Bamboo自动化部署时,就有问题了。

    这里的问题是:难以快速区分不同branch代码的build版本。举例,开发A用branch_a build出来的一个包是repo_1.5.5,开发B用branch_b build出来的一个包是repo_1.5.6,两者在同一目录下。
    虽然两者的version不一样,但是很难快速区分,需要分别去看自己的build log,然后根据里面打出的version版本来做出判断。但是,以上的自动化方案没有办法做出这种判断。

    解决的方案有很多,列举两个:

    • 1.在build好的包中加入一些metadata信息,包含git branch,download script读取metadata,只抓去对应的branch的包。
    • 2.根据路径区分不同branch,比如branch_a的包会上传到/branch_a/repo,以此类推。download script就只需要到对应的路径下抓取。

    方案一的pom部分改动如下,主要是用了buildnumber-maven-pluginmaven-jar-plugin,前者生成一些git info,后者将这些信息写入jar。

    <!-- generate build timestamp, version, branch related info -->
    <plugin>
    	<groupId>org.codehaus.mojo</groupId>
    	<artifactId>buildnumber-maven-plugin</artifactId>
    	<version>1.4</version>
    	<executions>
    		<execution>
    			<id>generate-timestamp</id>
    			<phase>validate</phase>
    			<goals>
    				<goal>create</goal>
    			</goals>
    			<configuration>
    				<format>{0,date,MMM-dd HH:mm:ss z}</format>
    				<items>
    					<item>timestamp</item>
    				</items>
    				<buildNumberPropertyName>buildDateTime</buildNumberPropertyName>
    				<getRevisionOnlyOnce>true</getRevisionOnlyOnce>
    			</configuration>
    		</execution>
    		<execution>
    			<id>generate-buildnumber</id>
    			<phase>validate</phase>
    			<goals>
    				<goal>create</goal>
    			</goals>
    			<configuration>
    				<revisionOnScmFailure>0</revisionOnScmFailure>
    				<useLastCommittedRevision>true</useLastCommittedRevision>
    				<buildNumberPropertyName>buildRevision</buildNumberPropertyName>
    				<scmBranchPropertyName>buildBranch</scmBranchPropertyName>
    			</configuration>
    		</execution>
    		<execution>
    			<id>create-metadata</id>
    			<phase>generate-resources</phase>
    			<goals>
    				<goal>create-metadata</goal>
    			</goals>
    			<configuration>
    				<attach>true</attach>
    				<properties>
    					<buildBranch>${buildBranch}</buildBranch>
    				</properties>
    				<addOutputDirectoryToResources>true</addOutputDirectoryToResources>
    			</configuration>
    		</execution>
    	</executions>
    </plugin>
    
    <!-- add git branch info to metadata when building jar -->
    <plugin>
    	<groupId>org.apache.maven.plugins</groupId>
    	<artifactId>maven-jar-plugin</artifactId>
    	<version>3.1.1</version>
    	<configuration>
    		<archive>
    			<index>true</index>
    			<manifestEntries>
    				<Git-Revision>${buildRevision}</Git-Revision>
    				<Build-Time>${buildDateTime}</Build-Time>
    				<Git-Branch>${buildBranch}</Git-Branch>
    			</manifestEntries>
    		</archive>
    	</configuration>
    </plugin>
    

    方案二的pom部分改动如下:主要是用了maven-deploy-plugin来override snapshot location。

    <!-- set up overridden snapshot deploy location -->
    <plugin>
    	<groupId>org.apache.maven.plugins</groupId>
    	<artifactId>maven-deploy-plugin</artifactId>
    	<version>3.0.0-M1</version>
    	<configuration>
    		<altSnapshotDeploymentRepository>
    			my-snapshots::some/path${buildBranch}
    		</altSnapshotDeploymentRepository>
    	</configuration>
    </plugin>
    

    总结

    针对开发中的问题,本文从三个层次实现了自动化部署,提高了开发测试的效率。

    • Configure build schedule -> Bamboo
    • Add download script -> shell
    • Change snapshot deploy location -> pom.xml
  • 相关阅读:
    (64)通信协议之一xml
    (63)通信协议之一json
    (61)C语言预处理命令详解
    (60) 结构体指针、结构体变量嵌套、结构体指针嵌套、函数指针、数组指针、指针数组、typedef 综合运用
    (59)Linux操作系统深入应用
    (58)PHP开发
    (57)Linux驱动开发之三Linux字符设备驱动
    (56)Linux驱动开发之二
    (55)Linux驱动开发之一驱动概述
    (54)LINUX应用编程和网络编程之九Linux网络通信实践
  • 原文地址:https://www.cnblogs.com/maxstack/p/10654128.html
Copyright © 2011-2022 走看看