项目依赖统一管理方案

一般对项目的依赖管理会有以下需求。

1、项目依赖同意管理,在单独文件中配置。

2、不同的Module种的依赖版本号统一

3、不同项目种的依赖版本号统一

针对这些需求,提出了以下集中方案:

1、使用循环优化Gradle依赖管理

2、使用buildSrc管理Gradle依赖

3、使用includeBuild统一配置依赖版本

4、使用Version Catalog统一配置依赖版本。

使用循环优化Gradle依赖管理

这种方式就是在app的目录下创建一个xxx.gradle文件,然后将我们项目所有需要用到的依赖放到该文件里,并分好类,例如:

ext{
    android = [
            compileSdkVersion       : 29,
            buildToolsVersion       : "29.0.3",
            minSdkVersion           : 21,
            targetSdkVersion        : 29,
            versionCode             : 10101,
            versionName             : "1.01.01"
    ]
    dependencies  = [
            "rxlifecycle"                 : "com.trello.rxlifecycle2:rxlifecycle:2.2.2",
            "rxlifecycle-android"         : "com.trello.rxlifecycle2:rxlifecycle-android:2.2.2",
            "rxlifecycle-components"      : "com.trello.rxlifecycle2:rxlifecycle-components:2.2.2",
            //网络
            "retrofit"                    : "com.squareup.retrofit2:retrofit:2.6.2",
            "retrofit_adapter"            : "com.squareup.retrofit2:adapter-rxjava2:2.6.2",
            "retrofit_gson"               : "com.squareup.retrofit2:converter-gson:2.6.2",
            "rxjava"                      : "io.reactivex.rxjava2:rxjava:2.2.14",
            "rx_android"                  : "io.reactivex.rxjava2:rxandroid:2.1.1",
            //gson
          
            ........

    ]

    annotationProcessor = [
            "butterknife-compiler"         :"com.jakewharton:butterknife-compiler:10.0.0",
            "glide-compiler"              : "com.github.bumptech.glide:compiler:4.9.0",
            "dagger-compiler"             : "com.google.dagger:dagger-compiler:2.24",
    ]
    
    apiFileDependencies = [
            "launchstarter"                                   :"libs/launchstarter-release-1.0.0.aar"
    ]
    
    debugImplementationDependencies = [
            "MethodTraceMan"                                  : "com.github.zhengcx:MethodTraceMan:1.0.7"
    ]
    
    ...
    
    implementationExcludes = [
            "com.android.support.test.espresso:espresso-idling-resource:3.0.2" : [
                    'com.android.support' : 'support-annotations'
            ]
    ]

然后在我们的build.gradle文件中引用该文件

apply from:"config.gradle"

最后在build.gradle的dependencies中添加如下代码:

def implementationDependencies = project.ext.dependencies
def processors = project.ext.annotationProcesso
def implementationExcludes = project.ext.implementationExcludes
dependencies{
    // 处理所有的 xxximplementation 依赖
    implementationDependencies.each { k, v -> implementation v }   
    // 处理 annotationProcessor 依赖
    processors.each { k, v -> annotationProcessor v }
    // 处理所有包含 exclude 的依赖
    implementationExcludes.each { entry ->
        implementation(entry.key) {
            entry.value.each { childEntry ->
                exclude(group: childEntry)
            }
        }
    }

这样做的优点在于
1.后续添加依赖不需要改动build.gradle,直接在config.gradle中添加即可
2.精简了build.gradle的长度

但是还是有一些痛点:

1.不支持代码提示
2.不支持单击跳转
3.多模块开发时,不同模块相同的依赖需要复制粘贴。

使用buildSrc管理Gradle依赖

创建一个名为buildSrc的module.因为运行Gradle时,它会检查项目中是否存在一个名为buildSrc的目录。然后Gradle会自动编译并测试这段代码,并将其放入构建脚本的类路径中。您不需要提供任何进一步的操作提示。 所以也不需要在settings.gradle文件中添加include xxx。

步骤如下:

1.新建文件 build.gradle.kts,并同步 gradle

plugins {
    `kotlin-dsl`
}
repositories {
    jcenter()
}

2.创建 /src/main/java/Version.kt 文件,在 Dependencies.kt 文件中编写依赖管理代码:

object BuildVersion {
    const val compileSdk = 30
    const val buildTools = "30.0.2"
    const val minSdk = 21
    const val targetSdk = 30
    const val versionCode = 1
    const val versionName = "1.0.0"
}

object Versions {
    const val kotlin = "1.4.30"
    const val core_ktx = "1.3.2"
    const val appcompat = "1.2.0"
    const val material = "1.3.0"
    const val retrofit = "2.9.0"
}

object Libs {
    const val kotlin_stdlib = "org.jetbrains.kotlin:kotlin-stdlib:${Versions.kotlin}"
    const val core_ktx = "androidx.core:core-ktx:1.3.2:${Versions.core_ktx}"
    const val appcompat = "androidx.appcompat:appcompat:${Versions.appcompat}"
    const val material = "com.google.android.material:material:${Versions.material}"
    const val retrofit = "com.squareup.retrofit2:retrofit:${Versions.retrofit}"
}

3.在 module 中 build.gradle 应用依赖项,如下

plugins {
    id 'com.android.library'
    id 'kotlin-android'
}

android {
    compileSdkVersion BuildVersion.compileSdk
    buildToolsVersion BuildVersion.buildTools

    defaultConfig {
        minSdkVersion BuildVersion.minSdk
        targetSdkVersion BuildVersion.targetSdk
        versionCode BuildVersion.versionCode
        versionName BuildVersion.versionName
        ...
    }

    ...
}

dependencies {

    implementation Libs.kotlin_stdlib
    implementation Libs.core_ktx
    implementation Libs.appcompat
    implementation Libs.material

    implementation Libs.retrofit
}

缺点:由于 buildSrc 是对全局的所有 module 的配置,因此在构建速度上会慢一些。

使用includeBuild统一配置依赖版本

步骤如下:

1.先创建一个java或kotlin的library.

2.然后在创建好的library的build.gradle文件中添加以下代码,我这里用的kotlin,如果用的Java,则 apply plugin: 'java-library'。

apply plugin: 'kotlin'
apply plugin: 'java-gradle-plugin'

buildscript {
    repositories {
        jcenter()
        google()
    }
    dependencies {
        classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:1.4.10"

    }
}

repositories {
    jcenter()
    google()
}

dependencies {
    implementation gradleApi()
    implementation "org.jetbrains.kotlin:kotlin-gradle-plugin:1.4.10"
}

gradlePlugin{
    plugins{
        version{
            //id 对应package name
            id = "com.example.version"
            //implementationClass 则是对应我们第三步需要创建的一个类,其内容为包名 + 类名
            implementationClass = "com.example.version.DependencyVersionPlugin"
        }
    }
}

3.在com.example.version路径下创建一个类

class DependencyVersionPlugin : Plugin {
    override fun apply(target: Project) {

    }
}

4.在src/main/java的路径下添加文件,文件里就是所有的依赖集合

5.在settings.gradle添加

//括号里对应library名
includeBuild("version")

6.然后在需要的module,添加

plugins{
    id  "com.example.version"
}

sync之后,就可使用了。

dependencies {
    implementation fileTree(dir: 'libs', include: ['*.jar'])
    implementation(AndroidX.coreKtx)
    implementation(AndroidX.appcompat)
    implementation(AndroidX.constraintlayout)
}

这里有一个坑,不能将

android {
    compileSdkVersion ProjectBuildConfigs.compileSdkVersion
    buildToolsVersion ProjectBuildConfigs.buildToolsVersion

    defaultConfig {
        minSdkVersion ProjectBuildConfigs.minSdkVersion
        targetSdkVersion ProjectBuildConfigs.targetSdkVersion
        versionCode ProjectBuildConfigs.versionCode
        versionName ProjectBuildConfigs.versionName

        consumerProguardFiles "consumer-rules.pro"

        ndk {
            // 设置支持的SO库架构
            //abiFilters 'armeabi', 'x86', 'armeabi-v7a', 'x86_64', 'arm64-v8a'
            abiFilters 'armeabi-v7a', 'arm64-v8a', 'x86'
        }
    }
}

这些公共的东西放在一个公共的base_xxx.gradle,然后再在build.gradle里面 apply from "base_xxx.gradle ",这样会一直报compileSdkVersion is not specified.的错误。我在这上面弄了好久,一直怀疑是写的有问题。


b7841a723bad5c2eb56287073db3324.png

使用红色框的方式会一直报错,所以我们需要采用绿色框的方式

还有一个坑就是不能套娃:

object Kotlin {
        const val Kotlin = "org.jetbrains.kotlin:kotlin-stdlib:${Version.Kotlin}"
        const val CoroutinesCore =
            "org.jetbrains.kotlinx:kotlinx-coroutines-core:${Version.Coroutines}"
        const val CoroutinesAndroid =
            "org.jetbrains.kotlinx:kotlinx-coroutines-android:${Version.Coroutines}"
        object GitHub {
                  const val OkHttp = "com.squareup.okhttp3:okhttp:${Version.OkHttp}"
                  const val OkHttpInterceptorLogging =
            "com.squareup.okhttp3:logging-interceptor:${Version.OkHttpInterceptorLogging}"
                  const val Retrofit = "com.squareup.retrofit2:retrofit:${Version.Retrofit}"
            }
    }

这样会编译不过。

使用Version Catalog统一配置依赖版本

Catalog 是Gradle7.0推出了一个新的特性,它支持以下特性:

1.对所有module可见,可统一管理所有module的依赖

2.支持声明依赖bundles,即总是一起使用的依赖可以组合在一起

3.支持版本号与依赖名分离,可以在多个依赖间共享版本号

4.支持在单独的libs.versions.toml文件中配置依赖

5.支持在项目间共享依赖

具体使用请看【Gradle7.0】依赖统一管理的全新方式,了解一下~

参考资料

【Gradle7.0】依赖统一管理的全新方式,了解一下~

git https://github.com/fengyuehan/Test/tree/master/version

你可能感兴趣的:(项目依赖统一管理方案)