最近团队内部针对AS本地打包编译时间太长提出要提高效率问题,减少开发人员本地打包的次数,减少等待编译打包的等待时间——经过测试一个打包后70M左右的APK在本地打包需要十几分钟甚至二十多分钟,严重浪费开发时间,时间成本太高。
自然想到了需要其他方式来提高效率,那么自然想到了打包服务器,jenkins自然成了首选。
jenkins在android方面,可以完备的结合gradle编译,通过配置也可以设置角色及权限,团队内开发,测试,产品可以给予不同的权限,自行发起构建,下载测试。测试,产品不用因为需要临时体验专门找开发进行一次为时较长的打包。可以在jenkins上自己发起构建进行打包体验,开发可以持续工作,这样各不干扰,也就节省了时间成本。

在讲述Android具体项目配置之前,先了解下jenkins基本的安装,启动,环境配置等前期准备工作。

环境要求

  1. JDK安装;
  2. Windows OS;
  3. Python;
  4. Gradle;
  5. Android SDK, NDK;
  6. Tomcat;

Jenkins准备

准备工作当然是需要准备jenkins环境,初始化配置,以及最终下载方式的准备工作。

安装

在jenkins官网下载与OS相匹配的jenkins版本(建议LTS版本)。
本文说的OS是Windows系统,由于是公司内部使用,因此不具备外部访问功能。
将下载好的jenkins包减压缩后直接双击即可安装,安装目录建议安装在 不含空格的路径 下——空格路径会在配置过程中需要执行的命令产生影响而导致最终编译失败。

启动

jenkins安装成功后,在其安装根目录下找到名为jenkins.war文件。
然后通过cmd命令窗口中输入如下命令就可以启动jenkins了。

java -jar jenkins.war

jenkins启动的默认端口是8080。如果需要修改启动端口,可以在上述命令后添加–httpPort参数修改端口。

java -jar jenkins.war --httpPort=9090

成功启动后,在浏览器中输入"http://localhost:8080" 或者“http://localhost:9090”来打开jenkins。

初始化

  1. 第一次启动jenkins,需要解锁。

解锁页面

按照提示给出的路径找到initialAdminPassword文件,在页面“管理员密码”编辑框中输入initialAdminPassword文件中的初始密码。点击“继续”。

  1. 下一步要求插件安装选择,这里直接选择“安装推荐的插件”即可

插件安装页

等待插件安装结束。再进入到下一步,根据提示安装。

中间有一步骤创建管理员,可以根据需要进行创建,也可以继续使用admin账户。
一切配置完成后进入到jenkins首页。

jenkins首页

全局配置

进入到jenkins首页后,需要先进行必要的全局配置。
依次选择: Manager Jenkins(系统管理)> Config System(系统配置) 进入到全局配置页面。

  1. 修改全局“执行者数量”——同时进行编译的数量
    这里修改的值可以影响到同时可以进行构建的数量,默认值是2,这里修改成5。

执行数量

  1. 添加"全局属性" > "环境变量"
    这里配置Android编译过程中可能用到的所有的工具及环境,比如:Android SDK,NDK等。

全局属性

  1. 启用 BUILD_TIMESTAMP —— 需要插件“Build Timestamp”
    启用TIMESTAMP需要安装“Build Timestamp”插件,然后进行设置。

TIMESTAMP

  1. Jenkins Location

Jenkins Location

此项设置是必要的。
Jenkins URL 指定Jenkins的Http地址,因为Jenkins自身无法检测自己的URL地址,也用于在邮件中产生jenkins链接。

产生url地址

系统管理员邮件地址 这个配置用以在编译结束后,jenkins给发邮件提示。

  1. 邮件通知
    安装后的jenkins自带有邮件通知功能,但是自带的邮件通知功能只在特定的情况下发送邮件通知,因此可以用以测试邮件配置是否正确,在实际使用邮件提示时,会选择可定制邮件通知内容的插件来完成。

邮件通知

全局工具(Global Tool Configuration)

在全局工具中同样需要配置编译需要用到的基本工具。
进入:Manager Jenkins(系统管理)> Global Tool Configuration,配置JDK,Git,Gradle等编译需要的工具。

全局工具配置

除了以上这些基本配置后,另外一些配置需要在项目配置时使用到的接下来会逐一说明。

凭据

这是很重要的一步,要最终生成的签名apk就需要凭据。

在编译APK时必然会有APK签名的步骤,考虑到信息安全,因此签名文件不建议在个人开发者本地保存,或者上传到版本服务器。签名文件统一在jenkins环境下统一管理。因此需要将实现创建好的JKS文件作为凭据上传到jenkins。

找到左侧的“凭据”,进行添加。

凭据
添加凭据

跳转到添加凭据页面

上传凭据页

这里我们需要在“类型”下拉框中选择“Certificate”,然后可以看到“证书”一栏要求我们上传的是PKCS格式的证书。

Certificate类型

而我们在创建签名文件的时候都是JKS格式的文件,因此我们需要使用java的keytool命令进行转换,再进行上传。
具体的命令格式

keytool -importkeystore -srckeystore {REPLACE_WITH_JKS_FILE} -srcstoretype JKS -deststoretype PKCS12 -destkeystore ConvertedCertificate.p12

转换成功之后将p12文件上传即可,输入对应的密码,id字段可以不填写,jenkins会自动分配,描述字段用于在选择时外显信息。
上传成功后可以看到在凭据列表中添加的Certificate类型的凭据。

添加成功

至此,创建具体项目进行配置的准备工作已经好了,可以下一步创建并配置的过程了。

项目示例

在Jenkins首页,点击“新建Item”

点击新建item

进入到创建页面

创建项目页

点击“确定”后进入到基本模板配置页面。

配置模板页

General

General 选项卡可以配置项目描述,以及基本的配置。这里需要着重注意的checkbox项是"This project is parameterzed"。

选中后可以定义变量,这些变量在编译过程中,jenkins会将这些变量值侵入到项目的gradle中,作为项目的全局属性被访问——需要注意的是要在项目的gradle.properties中定义对应的变量——将变量的值替换gradle.properties中相应变量的默认值。

项目描述

参数定义

在参数配置中定义了BUILD_TYPE,APK_NAME,VERSION_NAME,BUILD_TIME,IS_JENKINS。
在项目发起编译时,可以看到这些定义的变量及其描述。

配置后效果

发起编译前,还需要确保在项目的gradle.properties中同样定义了对应需要使用的变量,这样在jenkins进行编译时,这些定义的变量值才能起作用。

IS_JENKINS = false
BUILD_TIME = ''
APK_NAME = ''
VERSION_NAME = 1.0.0

这里定义了项目中需要使用的变量,在jenkins编译时,这些变量值会被jenkins中定义的同名变量值替换。gradle.properties中定 义的变量也会在项目的gradle文件中被引用。

// 定义的versionName
versionName VERSION_NAME

// 定义编译生成的apk名格式
applicationVariants.all { variant ->
    variant.outputs.each { output ->
        def newName

        if ('true' == IS_JENKINS) {
            println("jenkins build ==> $BUILD_TIME")
            newName = "$APK_NAME-v$VERSION_NAME-$BUILD_TIME-${variant.buildType.name}-unsigned.apk"
        } else {
            if ('debug' == variant.buildType.name) {
                newName = "$APK_NAME-v${rootProject.android.versionName}-${rootProject.android.versionCode}-debug.apk"
            } else {
                newName  = "$APK_NAME-v${rootProject.android.versionName}-${rootProject.android.versionCode}-${variant.buildType.name}.apk"
            }
        }

        output.outputFileName newName
    }

}

这样在发起编译后,最终jenkins编译生成的apk文件名即是IS_JENKINS分支的输出名。

源码管理

源码管理 项选择源码配置工具。
因为我们的源码管理工具是git,因此选择git,并且在对应的配置填写源码url等信息。

选择Git方式后,填写“Repository URL”gitlab上project的http地址,“Credentials”初始需要点击有责“添加”增加凭据。在“Branch to build”中填写需要编译的分支。

构建触发器

构建触发器 中可以设置触发编译的条件。

这里设置了每隔30分钟拉取一次代码并且编译。也可以根据需要,根据对应的格式填写需要触发的条件。

构建环境

构建环境 项中配置编译条件。

  • "Add timestamp to the console Output"可以在编译时的控制台输出中看到时间戳。
    -“Set Build Name”设置编译发起人等信息,有助于查看编译发起者信息。
    -“Set jenkins user build variables”用于获取user数据。

构建环境
构建历史

构建

构建 配置需要执行的操作等。在构建配置中,主要选择编译使用的gradle版本及执行的任务命令,选择签名,已经可能需要签名后执行的命令(配置块的顺序不可更改,一定是gradle编译,后签名,再针对签名后的文件进行操作,否则会造成奇怪的问题。)

  • Invoke Gradle script 块中选择编译的Gradle版本,以及在tasks填写执行的任务。

在选择编译gradle版本中,有一点特别需要注意,点击“高级”,在展开的配置项中,勾选 ”
Pass all job parameters as Project properties”项
,让在 “General”项中配置的参数可以在编译时准确将值替换到项目gradle.properties文件中的对应变量的值。否则在编译时你会发现,即使编译成功了,但是产生的APK文件名不是想要的输出。

  • Sign Android APKs 块设置签名文件等,需要“Android Signning Plugin”插件支持,在块中选择"Key Store",“Key Alias”,“Apks to Sign”,最后的“Archive Signed APKs”,Archive Unsigned APKs”项用于设置最终显示的是签名apk,或者是未签名apk。

APK签名

  • “Execute Windows batch command”中可以使用windows cmd命令针对签名操作后的apk文件进行操作或者其他操作。

  • “Send files to a windows share" 块配置将打包签名的apk文件upload到一台共享服务器——提前安装好CIFS插件后,需要在全局设置针对共享服务器的基本信息进行配置。

成功编译后,可以在项目构建首页看到编译输出结果。

构建后操作

构建后操作 配置在打包签名完成后的操作。

  • “Set build description” 设置编译成功后再在项目首页编译历史中查看描述信息——此处设置了一张二维码图片,大小为120x120——前提:在全局安全设置“标记格式器”将原来的text格式修改为html。


  • “Editable Email Notification”设置邮件通知。这个邮件通知jenkins自带的邮件通知不同,是内容格式定制后的邮件。首先需要安装“Email Extension”插件。在全局配置中配置邮件格式。

最后邮件样式:


这样一个项目基本的配置也就完成了。

需要的插件

插件名说明
Date Parameter Plugin日期格式,主要用于在参数化编译时格式化输出日期时间,例如:yyyyMMdd_HHmmss
user build vars plugin用户变量,可以获取jenkins用户名及id,引用:${BUILD_USER}
Build Timestamp在Jenkins环境变量及系统属性中添加BUILD_TIMESTAMP
Build Name and Description Setter在“构建环境”块中添加“set build name”设置在编译时"build history"中显示构建信息
Publish Over CIFS将生成的apk上传到共享服务器
Android Signing Pluginapk签名,选择key store,填写alias
Email Extension定制发送内容
Role-based Authorization Strategy为jenkins内操作进行角色,权限分配
Logo

权威|前沿|技术|干货|国内首个API全生命周期开发者社区

更多推荐