Gradle编译打包小结

  • Post author:
  • Post category:其他


以前用Eclipse打包,比较笨,右键导出签名

现在一直是用的Android Studio来开发

用Gradle编译打包非常方便

笔者整理的平时编译打包的配置,记录一下,避免遗忘

1.自动签名

可以直接写在build.gradle里,如:

signingConfigs {
        develop {
            storeFile '/xxxxxx/xxx.jks'
            keyAlias 'xxxxxx'
            keyPassword 'xxxxxx'
            storePassword 'xxxxxx'
        }
    }

笔者习惯写在配置文件里,然后加入ignore方便后续更改

这里写图片描述

/**
 * 读取签名
 * @return
 */
def getSignProperty() {
    def Properties buildProperties = new Properties()
    buildProperties.load(new FileInputStream(file('../config/sign.properties')))
    return buildProperties
}

签名配置sign.properties

STORE_PASSWORD=xxxxxx
KEY_PASSWORD=xxxxxx
KEY_ALIAS=xxxxxx
STORE_FILE=xxxxxx.jks

2.同时打出不同环境的包

正常情况下一个项目可能同时有测试环境和正式环境

如果每次打包都去改配置是非常繁琐的,而且容易出错

建议在配置文件里直接添加配置

productFlavors {
        buildDevelop {
            buildConfigField "boolean", "MODEL_DEV", "true"
            versionName = mVersionName
        }
        buildRelease {
            buildConfigField "boolean", "MODEL_DEV", "false"
            versionName = mVersionName
        }
    }

这里写图片描述

如上所述,打包的时候会同时打出两个不同的包,一个是测试环境一个是正式环境

3.输出日志

记录打包时候的时间,版本号以及Git提交的版本等等,方便日后审查

/**
 * 输出日志
 */
def buildLog(String output,String vName,String vCode) {
    File outputFile = new File(output)
    if(!outputFile.exists())
        outputFile.mkdirs()
    FileWriter fw = new FileWriter(output + File.separator + "log.txt")
    StringBuilder builder = new StringBuilder();
    builder.append("[构建时间]=" + buildTime("yy-MM-dd HH:mm"))
    builder.append("\r\n")
    builder.append("[版本编号]=" + vCode)
    builder.append("\r\n")
    builder.append("[版本名称]=" + vName)
    builder.append("\r\n")
    builder.append("[提交记录]=" + getGitVersion())
    fw.write(builder.toString())
    fw.flush();
    fw.close();
}

相关的函数

/**
 * 读取Git日志
 * @return
 */
def getGitVersion() {
    return 'git rev-parse --short HEAD'.execute().text.trim()
}

/**
 * 构建时间
 * @return
 */
def buildTime(String time) {
    def date = new Date()
    def formattedDate = date.format(time)
    return formattedDate
}

4.编译构建完成之后最好备份一下mapping文件

build {
    doLast {
        //记录日志
        buildLog(mOutputs,mVersionName,mVersionProps['VERSION_CODE'])
        //复制文件
        copy {
            from "$buildDir/outputs/mapping"
            into mOutputs
        }
    }
}

最后的全局配置文件

apply plugin: 'com.android.application'

/**
 * 读取版本配置
 */
def Properties mVersionProps = getVersionProperty();

/**
 * 读取版本名
 */
def mVersionName = buildRelease() ? mVersionProps['VERSION_NAME'] : "build_" + buildTime('yyMMdd')

/**
 * 输出目录
 */
def mOutputs = "$rootDir/outputs/build_" + buildTime('yyMMdd')

android {

    signingConfigs {
        develop {
            def Properties buildSignProps = getSignProperty()
            storeFile file(buildSignProps['STORE_FILE'])
            keyAlias buildSignProps['KEY_ALIAS']
            keyPassword buildSignProps['KEY_PASSWORD']
            storePassword buildSignProps['STORE_PASSWORD']
        }
    }

    buildTypes {
        debug {
            applicationIdSuffix ".debug"
            buildConfigField "boolean", "MODEL_DEV", "true"
        }
        release {
            minifyEnabled true
            buildConfigField "boolean", "MODEL_DEV", "false"
            signingConfig signingConfigs.develop

            zipAlignEnabled true
            //去掉无用资源
            shrinkResources true
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }

    //读取版本配置
    compileSdkVersion 23
    buildToolsVersion "23.0.2"
    defaultConfig {
        applicationId "cn.byhook.main"
        minSdkVersion 9
        targetSdkVersion 23
        versionCode Integer.valueOf(mVersionProps['VERSION_CODE'])
        versionName = mVersionName
    }

    dexOptions {
        javaMaxHeapSize "4g"
    }

    lintOptions {
        checkReleaseBuilds false
        abortOnError false
    }

    compileOptions {
        sourceCompatibility JavaVersion.VERSION_1_7
        targetCompatibility JavaVersion.VERSION_1_7
    }

    productFlavors {
        /*_$ { variant.productFlavors.get(0).name }
        $ { variant.buildType.name }*/
        buildDebug {
            buildConfigField "boolean", "MODEL_DEV", "true"
            versionName = "Local Version"
        }
        buildDevelop {
            buildConfigField "boolean", "MODEL_DEV", "true"
            versionName = mVersionName
        }
        buildRelease {
            buildConfigField "boolean", "MODEL_DEV", "false"
            versionName = mVersionName
        }
    }


    if (buildRelease()) {
        android.variantFilter { variant ->
            if (variant.buildType.name.equals('release')) {
                variant.getFlavors().each() { flavor ->
                    if (flavor.name.equals('buildDebug')) {
                        variant.setIgnore(true);
                    }
                }
            }
        }
    }

    //输出文件配置
    applicationVariants.all { variant ->
        variant.outputs.each { output ->
            def outputFile = output.outputFile
            if (outputFile != null && outputFile.name.endsWith('.apk')) {
                if ("release".equals(variant.buildType.name)) {
                    if ("buildDevelop".equals(variant.productFlavors.get(0).name)) {
                        output.outputFile = new File(
                                mOutputs,
                                "Main_${buildTime("yyMMddHHmm")}_dev.apk")
                    } else if ("buildRelease".equals(variant.productFlavors.get(0).name)) {
                        output.outputFile = new File(
                                mOutputs,
                                "Main_${buildTime("yyMMddHHmm")}.apk")
                    }
                } else {
                    output.outputFile = new File(
                            outputFile.parent,
                            "app-debug.apk")
                }
            }
        }
    }
}

dependencies {
    compile fileTree(dir: 'libs', include: ['*.jar'])
    testCompile 'junit:junit:4.12'
    testCompile 'org.robolectric:robolectric:3.1'
    compile project(':Exlibrary')
}

/********************************************************************
 * 打包脚本
 ********************************************************************/

/**
 * 构建版本
 * @return
 */
def getVersionProperty() {
    def Properties buildProps = new Properties()
    buildProps.load(new FileInputStream(file('../config/version.properties')))
    return buildProps;
}

/**
 * 读取签名
 * @return
 */
def getSignProperty() {
    def Properties buildProperties = new Properties()
    buildProperties.load(new FileInputStream(file('../config/sign.properties')))
    return buildProperties
}

/**
 * 构建时间
 * @return
 */
def buildTime(String time) {
    def date = new Date()
    def formattedDate = date.format(time)
    return formattedDate
}

/**
 * 是否发布
 * 发布为真
 * 版本号自增
 * @return
 */
def buildRelease() {
    return false
}

/**
 * 读取Git日志
 * @return
 */
def getGitVersion() {
    return 'git rev-parse --short HEAD'.execute().text.trim()
}

/**
 * 输出日志
 */
def buildLog(String output,String vName,String vCode) {
    File outputFile = new File(output)
    if(!outputFile.exists())
        outputFile.mkdirs()
    FileWriter fw = new FileWriter(output + File.separator + "log.txt")
    StringBuilder builder = new StringBuilder();
    builder.append("[构建时间]=" + buildTime("yy-MM-dd HH:mm"))
    builder.append("\r\n")
    builder.append("[版本编号]=" + vCode)
    builder.append("\r\n")
    builder.append("[版本名称]=" + vName)
    builder.append("\r\n")
    builder.append("[提交记录]=" + getGitVersion())
    fw.write(builder.toString())
    fw.flush();
    fw.close();
}

build {
    doLast {
        buildLog(mOutputs,mVersionName,mVersionProps['VERSION_CODE'])
        copy {
            from "$buildDir/outputs/mapping"
            into mOutputs
        }
    }
}

task mak{
    buildLog(mOutputs,mVersionName,mVersionProps['VERSION_CODE'])
}

打包只需终端输入

//--info或者--debug输出详细信息,方便出错时候定位错误
gradle clean
gradle build --info

这里写图片描述

输出

这里写图片描述

小结一下,方便以后打包处理更为方便,当然Gradle的强大之处远不止如此



版权声明:本文为byhook原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。