gradle配置技巧

gradle配置全局變量

1.gradle的ext屬性

ext屬性是ExtensionAware類型的一個(gè)特殊的屬性,本質(zhì)是一個(gè)Map類型的變量。
ext屬性可以伴隨對(duì)應(yīng)的ExtensionAware對(duì)象在構(gòu)建的過程中被其他對(duì)象訪問,例如你在rootProject中聲明的ext中添加的內(nèi)容,就可以在任何能獲取到rootProject的地方訪問這些屬性。

在android的rootProject的build.gradle中,定義如下代碼塊

ext.commonConfig = [
        minSdkVersion    : 21,
        targetSdkVersion : 26,
        compileSdkVersion: 29,
        versionName      : "1.0.0",
        versionCode      : 1,
]

然后在模塊下使用該數(shù)據(jù),這里首先用def定義一個(gè)變量ext = rootProject.ext.commonConfig

def ext = rootProject.ext.commonConfig
android {
    compileSdkVersion ext.compileSdkVersion

    defaultConfig {
        applicationId "com.example.mvvmframe"
        minSdkVersion ext.minSdkVersion
        targetSdkVersion ext.targetSdkVersion
        versionCode ext.versionCode
        versionName ext.versionName
    }
}
2.配置請(qǐng)求環(huán)境變量

在項(xiàng)目的build.gradle文件中,配置出開發(fā),測(cè)試,正式環(huán)境的變量。

buildscript {

    //配置3種環(huán)境
    ext.isDev = 0
    ext.isBeta = 1
    ext.isRelease = 2

    //當(dāng)前打包環(huán)境
    ext.curEnv = isRelease
}

在app模塊下的build.gradle文件的android->defaultConfig代碼塊中,添加如下代碼。

    defaultConfig {

        if (curEnv == isDev) {
            manifestPlaceholders.put('APP_NAME', "開眼-開發(fā)")
        } else if (curEnv == isBeta) {
            manifestPlaceholders.put('APP_NAME', "開眼-測(cè)試")
        } else if (curEnv == isRelease){
            manifestPlaceholders.put('APP_NAME', "開眼-正式")
        }

    }

curEnv、isDev、isBeta、isRelease變量都是之前定義過的,能直接引用到。通過manifestPlaceholders注入APP_NAME的屬性到manifest文件中,在menifest中設(shè)置application的名字為當(dāng)前環(huán)境對(duì)應(yīng)的名字,從而實(shí)現(xiàn)app名字為對(duì)應(yīng)環(huán)境的名字,manifestPlaceholders 可以替換androidmanifest文件中的標(biāo)簽。這里添加:

android:label="${APP_NAME}"

在網(wǎng)絡(luò)請(qǐng)求所屬模塊下的android->defaultConfig代碼塊中,像BuildConfig文件注入如下四個(gè)屬性:

    defaultConfig {

        //將環(huán)境變量注入到buildConfig中
        buildConfigField 'int', 'CUR_ENV', "$curEnv"
        buildConfigField 'int', 'IS_DEV', "0"
        buildConfigField 'int', 'IS_BETA', "1"
        buildConfigField 'int', 'IS_RELEASE', "2"
    }

經(jīng)過編譯之后就自動(dòng)生成了該四個(gè)屬性和值:


最后一步,根據(jù)配置的環(huán)境變量配置域名:

/** 開發(fā)服務(wù)器地址  */
        private const val SERVER_ADDRESS_DEV = ""

        /** 測(cè)試服務(wù)器地址  */
        private const val SERVER_ADDRESS_BETA = ""

        /** 正式服務(wù)器地址  */
        private const val SERVER_ADDRESS_RELEASE = ""

        /**
         * 獲取服務(wù)器域名
         */
        fun getBaseUrl(): String? {
            return when (BuildConfig.CUR_ENV) {
                BuildConfig.IS_DEV -> {
                    ToastUtil.show("開發(fā)環(huán)境")
                    SERVER_ADDRESS_DEV
                }
                BuildConfig.IS_BETA -> {
                    ToastUtil.show("測(cè)試環(huán)境")
                    SERVER_ADDRESS_BETA
                }
                BuildConfig.IS_RELEASE -> {
                    ToastUtil.show("正式環(huán)境")
                    SERVER_ADDRESS_RELEASE
                }
                else -> ""
            }
        }
  • 引入gradle插件

apply plugin: 插件名 引入插件以后相當(dāng)于包含了該插件所有的任務(wù)類型、任務(wù)、屬性等。

  • 在gradle文件中引入獨(dú)立gradle文件:
apply from: '../xxx.gradle'
  • 讀取gradle.properties文件中數(shù)據(jù)

示例:讀取gradle.properties中一個(gè)屬性值NET_TYPE=dev,用來(lái)對(duì)應(yīng)當(dāng)前安裝包的環(huán)境類型。

//使用文件流讀取properties數(shù)據(jù)
def getServer() {
    def netType
    Properties properties = new Properties()  //使用Properties讀取流文件
    def file = file("../gradle.properties")  // file() 創(chuàng)建一個(gè)Java中的File對(duì)象
    if (file.canRead()) {
        //可以讀取到文件
        properties.load(file.newInputStream())
        if (properties != null) {
            //文件讀取成功
            netType = properties.getProperty('NET_TYPE')  //getProperty讀取屬性值
        }
    }
    return netType
}
  • 往該模塊的BuildConfig文件注入屬性和值
        //需要三個(gè)參數(shù)  1.屬性類型(String/int)   2.屬性名  3.屬性值
        //String類型,需要加入轉(zhuǎn)義的雙引號(hào)才表示字符串,不然生成的變量沒有雙引號(hào)
        buildConfigField 'String', 'IS_DEV', "\"dev\""
        buildConfigField 'String', 'IS_BETA', "\"beta\""
        buildConfigField 'String', 'IS_RELEASE', "\"release\""
        buildConfigField 'String', 'NET_TYPE', "\""+getServer()+"\""  //net_type讀取properties中NET_TYPE值

在BuildConfig中生成了新的屬性和值:


然后可以根據(jù)BuildConfig中類型來(lái)獲取對(duì)應(yīng)BaseUrl

        /**
         * 獲取當(dāng)前環(huán)境的域名
         */
        fun getBaseUrl(): String {
            return when (BuildConfig.NET_TYPE) {
                BuildConfig.IS_DEV -> {
                    SERVER_ADDRESS_DEV
                }
                BuildConfig.IS_BETA -> {
                    SERVER_ADDRESS_BETA
                }
                BuildConfig.IS_RELEASE -> {
                    SERVER_ADDRESS_RELEASE
                }
                else -> SERVER_ADDRESS_DEV
            }
        }
  • 自動(dòng)配置簽名信息

在app下的build.gradle文件的android{}中配置簽名所需信息,可直接用gradle命令打包。

    //簽名配置
    signingConfigs {
        release {
            keyAlias 'xxxx'
            keyPassword 'xxx'
            storeFile file('xxxx.jks')
            storePassword 'xxxx'
        }
    }

    buildTypes {
        release {
            signingConfig signingConfigs.release
        }
    }
  • 多渠道配置,并將相關(guān)信息配置進(jìn)apk名字

在app下的build.gradle文件中,配置一鍵化多渠道打包:

    defaultConfig {
        ...
        flavorDimensions "versionCode"  //還需要配置多渠道打包c(diǎn)ode
    }

    productFlavors {
        yingyongbao {}
        qh360 {}
        xiaomi {}
        vivo {}
        oppo {}
        huawei {}
    }

    productFlavors.all { flavor->
        flavor.manifestPlaceholders = [UMENG_CHANNEL_VALUE: name]
        buildConfigField 'String', 'PLAT_FORM', "\"${name}\""
    }

      buildTypes {
        release {

            //通過Gradle生成apk名稱,帶有渠道名稱,時(shí)間戳,版本號(hào),版本名稱等信息
            android.applicationVariants.all { variant ->
                variant.outputs.all {
                    outputFileName = "${new Date().format("yyyy-MM-dd")}_${defaultConfig.versionName}_release.apk"
                }
            }
        }
    }

限制依賴條件為build類型

對(duì)于一些環(huán)境下,我們并不想在線上依賴某些庫(kù)或者 「model」 ,如果是三方庫(kù),一般都會(huì)有 「relase」 下依賴的版本。當(dāng)我們使用默認(rèn)的 debugImplementation 和 releaseImplementation 進(jìn)行依賴時(shí),最終打包時(shí)是否會(huì)依賴其中,取決于我們 「使用的build命令中build類型是不是debug或者relase」。

debugImplementation project(":dev")
releaseImplementation project(":dev_noop")
排除傳遞的依賴項(xiàng)

開發(fā)中,我們經(jīng)常會(huì)遇見依賴沖突,對(duì)于第三方庫(kù)導(dǎo)致的依賴沖突,比較好解決,我們只需要使用 exclude 解決即可,如下所示:

dependencies {
    implementation("androidx.lifecycle:lifecycle-extensions:2.2.0") {
        exclude group: 'androidx.lifecycle', module: 'lifecycle-process'
    }
}
動(dòng)態(tài)調(diào)整組件開關(guān)

對(duì)于一些組件,在 debug 開發(fā)時(shí)如果依賴,對(duì)我們的編譯時(shí)間可能會(huì)有影響,那么此時(shí),如果我們?cè)黾酉鄳?yīng)的開關(guān)控制,就會(huì)比較好:

buildscript {
 ext.enableBooster = flase
 ext.enableBugly = flase

 if (enableBooster)
    classpath "com.didiglobal.booster:booster-gradle-plugin:$booster_version"
 }
代碼配置地址

參考 https://blog.csdn.net/huangxiaoguo1/article/details/103618209
https://www.bilibili.com/video/BV14541137MV?p=5&spm_id_from=pageDriver
https://mp.weixin.qq.com/s/ZbakWNlT_bYbhtfFx0-Lnw

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • Gradle配置最佳實(shí)踐 本文會(huì)不定期更新,推薦watch下項(xiàng)目。如果喜歡請(qǐng)star,如果覺得有紕漏請(qǐng)?zhí)峤籭ssu...
    Solang閱讀 1,763評(píng)論 0 4
  • 為方便在不同module中設(shè)置版本號(hào)等配置信息,可以通過配置全局變量來(lái)統(tǒng)一所有module的公共配置信息。設(shè)置方法...
    CarlWu_S閱讀 6,964評(píng)論 1 2
  • 為方便在不同module中設(shè)置版本號(hào)等配置信息,可以通過配置全局變量來(lái)統(tǒng)一所有module的公共配置信息。設(shè)置方法...
    zheting閱讀 2,949評(píng)論 1 1
  • 上一篇文章中詳細(xì)介紹了module中build.gradle文件的屬性和配置,今天詳細(xì)講解一下我在自己的應(yīng)用中主...
    sakasa閱讀 1,126評(píng)論 0 1
  • 版權(quán)聲明:本文為博主原創(chuàng)文章,未經(jīng)博主允許不得轉(zhuǎn)載。 https://blog.csdn.net/zhaoyanj...
    勤奮的pangdunhu閱讀 2,230評(píng)論 0 1

友情鏈接更多精彩內(nèi)容