现在的项目是纯代码依赖的,Library需提供给其他团队使用,当前采用的是打aar的方式,在打生产包的时候,Jenkins会去打aar包,并存储下来,提供给其他团队使用。
项目的依赖情况如下图所示
通过aar
的方式提供给外部团队,既麻烦又不够优雅,所以想对此做出修改。
希望达到如下的效果
Commit
之后,都会去打一个开发包,此时,会先将library编译上传到Maven快照仓库 (Snapshot) 上,然后在编译app的时候,会从Maven快照仓库
里拉去最新的library库
,然后进行打包config.gradle
中的versionCode
和versionName
+1,然后将构建环境的标志位build_flag
改为生产环境
Maven正式仓库
里拉去最新的library库
,然后进行打正式包。build_flag
修改为开发环境
config.gradle是一个自己新建的gradle,用来全局存放项目的版本号,编译环境等
这部分只是实现了将Android的Library上传到了Maven仓库
具体详见我的另一篇博客 Android Module上传到Maven仓库 及 实现同时上传到多个Maven仓库,新版 Gradle7.0 / 老版 Gradle6.5 Maven仓库上传配置
build_flag
标志来判断编译环境新建一个config.gradle
,用来全局存放项目的版本号,编译环境等
ext.config = [
"versionCode":1,
"versionName":"1.0.0",
"build_flag":"dev"
]
maven_upload.gradle
apply plugin: 'maven'
def RELEASE_REPOSITORY_URL = "http://xxxxxxxx/release/" //TODO <------- 这个修改为正式的Maven仓库地址
def SNAPSHOT_REPOSITORY_URL = "http://xxxxxxxx/snapshot/" //TODO <------- 这个修改为快照的Maven仓库地址
def REPOSITORY_URL = VERSION_NAME.endsWith("-SNAPSHOT") ? SNAPSHOT_REPOSITORY_URL : RELEASE_REPOSITORY_URL
def NEXUS_USERNAME = "maven账号" //TODO <------- 这个修改为Maven仓库的账号
def NEXUS_PASSWORD = "maven密码" //TODO <------- 这个修改为Maven仓库的密码
logger.info("groupId = %s\t\nartifactId = %s\t\nversion = %s\t\nrepository = %s\t\n", GROUP, POM_ARTIFACT_ID, VERSION_NAME, REPOSITORY_URL)
afterEvaluate { project ->
uploadArchives {
repositories.mavenDeployer {
pom.groupId = GROUP
pom.artifactId = POM_ARTIFACT_ID
pom.version = VERSION_NAME
repository(url: REPOSITORY_URL) {
authentication(userName: NEXUS_USERNAME, password: NEXUS_PASSWORD)
}
}
}
task androidSourcesJar(type: Jar) {
classifier = 'sources'
from android.sourceSets.main.java.sourceFiles
}
artifacts {
archives androidSourcesJar
}
}
repositories {
maven {
url "http://xxxxxxxx/release/" //TODO <------- 这个修改为正式的Maven仓库地址
}
maven {
url "http://xxxxxxxx/snapshot/" //TODO <------- 这个修改为快照的Maven仓库地址
}
}
lib1的build.gradle
中
ext.GROUP = "com.heiko.test"
ext.POM_ARTIFACT_ID = "lib1"
String versionName = android.defaultConfig.versionName
if ("release" != buildConfig.build_flag) {
versionName += "-SNAPSHOT"
}
ext.VERSION_NAME = versionName
//引用gradle_upload.gradle
apply from: "${project.rootDir}/maven_upload.gradle"
lib2的build.gradle
中
ext.GROUP = "com.heiko.test"
ext.POM_ARTIFACT_ID = "lib2"
String versionName = android.defaultConfig.versionName
if ("release" != buildConfig.build_flag) {
versionName += "-SNAPSHOT"
}
ext.VERSION_NAME = versionName
//引用gradle_upload.gradle
apply from: "${project.rootDir}/maven_upload.gradle"
添加上面的代码之后,我们点击sync,同步下代码
可以发现多了一个uploadArchives
的Gradle Task
我们双击运行,一段时间后,出现如下成功的提示,说明就上传到maven仓库成功了
app模块的build.gradle
中
dependencies{
configurations.all {
resolutionStrategy.cacheDynamicVersionsFor 1,'days'
resolutionStrategy.cacheChangingModulesFor 0,'seconds'
}
String lib1 = 'com.heiko.test:lib1:' + buildConfig.version_number
if ("release" != buildConfig.build_flag) {
lib1 += "-SNAPSHOT"
}
implementation (lib1) {
changing = true
}
String lib2 = 'com.heiko.test:lib2:' + buildConfig.version_number
if ("release" != buildConfig.build_flag) {
lib2 += "-SNAPSHOT"
}
implementation (lib2) {
changing = true
}
}
这里需要注意的是cacheDynamicVersionsFor
、cacheChangingModulesFor
、changing = true
cacheDynamicVersionsFor
: 动态版本,你见过的像 3.+ 这种就是动态版本,它会取检查到的最高的版本号。又比如 latest.integration ,它也是动态版本cacheChangingModulesFor
: 变化模块,像 0.2-SNAPSHOT 这种后面带 SNAPSHOT 的版本changing = true
: 加了changing=true 就和添加标记SNAPSHOT后缀功能是一样的我们直接依赖源代码,方便实时编译调试,此时,IS_DEV
标志位为true
IS_DEV
这个标志位只在本地做修改,不上传到gitlab
上,也就是说gitlab上这个值永远是false
if(IS_DEV.toBoolean()){
//使用源码的依赖
implementation project(path: ':lib1')
implementation project(path: ':lib2')
} else {
//使用maven的依赖
String lib1 = 'com.heiko.test:lib1:' + buildConfig.version_number
if ("release" != buildConfig.build_flag) {
lib1 += "-SNAPSHOT"
}
implementation (lib1) {
changing = true
}
String lib2 = 'com.heiko.test:lib2:' + buildConfig.version_number
if ("release" != buildConfig.build_flag) {
lib2 += "-SNAPSHOT"
}
implementation (lib2) {
changing = true
}
}
当将代码上传到gitlab
上,并合并到develop
分支后,Jenkins会自动执行脚本打包
此时,IS_DEV
标志位为false,buildConfig
的build_flag
为develop
打包流程为
1.执行 git pull
更新代码到最新
2.执行uploadArchives
脚本上传Library到Maven仓库
3.执行assemble
脚本进行打包,这时候因为build_flag
为develop
,所以依赖的是快照的maven,会拉取到最新的快照依赖
4.复制文件到指定目录,修改文件名之类的操作
当代码被合并到master
分支,Jenkins会自动执行脚本打包
此时,IS_DEV
标志位为false,buildConfig
的build_flag
会被Jenkins自动修改为release
这个打包完成后,Maven依赖可以直接对外部团队提供了
打包流程为
1.执行 git pull
更新代码到最新
2.buildConfig的versionCode
和versionName
自动增加1
3.buildConfig的build_flag
修改为release
4.执行uploadArchives
脚本上传Library到Maven仓库
5.执行assemble
脚本进行打包,这时候因为build_flag
为release
,所以依赖的是正式的maven,会拉取到对应版本号的maven依赖,而对应版本号我们已经在前面步骤中自动+1了,所以不会冲突
6.buildConfig的build_flag
修改回develop
7.执行git push
上传代码
8.复制文件到指定目录,修改文件名之类的操作
至此,自动化打包maven的搭建我们就配置完毕了
感谢
Android Studio处理SNAPSHOT依赖项
深踩Android Studio 缓存的坑及解决方法