Android Gradle脚本解决美团多渠道打包再加固渠道信息丢失问题

一、关于美团多渠道打包

在Android开发中,肯定少不了要打多渠道包。Umeng有提供一些多渠道打包的方式,但是太慢了,每个渠道都要重复的去打,如果有50多个渠道,就需要编译50乘以1个包编译的时间。So,肯定是不可能这样干的,这个方案只适合一些渠道比较少的。所以我的项目里采用的美团的多渠道打包的方式。

具体的可以移动至我的另一篇文章:Android美团多渠道打包Walle集成

二、为什么又新写了这一篇文章?

就如标题所示,本来万事大吉了,可以一键生成多渠道包。可是等到发布的时候测试和我说,渠道信息没有了,What???然后网上各种翻资料,去Walle项目看看有没有类似的问题。不出所料,Walle官网也给出了原因和具体的解决方案。

360加固导致渠道信息丢失问题解决方案

可是这个方案,太蛋疼了哥。我每次都要手动的打Release包,然后上传360加固,下载加固包。然后本地跑一次Phtyon脚本生成渠道包。请告诉我这个操作蛋疼不?

有没有啥办法可以在Android Studio里也一键生成多渠道包并且渠道信息也不会丢失呢?当然是有的,自己动手丰衣足食。

把上述这些步骤全部写在一个Gradle脚本里,主模块Gradle apply自己的写的脚本。

三、自定义360加固+Walle打包脚本

1、首先在工程主模块新建reinforce.gradle脚本
reinforce.gradle.png
2、复制加固文件夹到项目根目录

(1)配置加固文件夹
把从360加固官网下载的window下载(MAC环境就MAC下载)里的内容有个jiagu文件夹,复制到工程目录,并且改名为reinforce,这里随意我是这样命名的。然后把美团的walle-cli-all.jar复制到reinforce文件夹里lib文件夹下。


加固文件夹.png

(2)配置渠道信息
在reinforce文件夹下新增channel.txt文件。录入你想要的渠道的信息

baidu #百度
xiaomi # 小米
anzhi # 安智
meizu # 魅族
vivo # vivo
oppo # oppo
huawei # 华为
sougou # 搜狗
samsung # 三星
lianxiang # 联想
jinli # 金立
taobao #淘宝
yingyongbao #应用宝
360 #360
anzhi #安智
guanwang #官网

或者直接下我弄好的:(Window)
链接: https://pan.baidu.com/s/1jw_0Wya4pf6HVjwFGWUJwg 提取码: igx9

3、reinforce.gradle脚本内容如下,ext写入项目相关的一些信息。其他的应该都不用动。

(1) Window下的脚本

ext {
    //加固插件路径
    reinforce_plugin_path = '../reinforce'
   //360加固账号密码
    reinforce_plugin_name = 'XXXXX'
    reinforce_plugin_passward = 'XXXXXX'
    //签名信息
    key_store_path = './xyz.keystore'
    key_store_passward = 'XXXXX'
    alias = 'XXXXXX'
    alias_passward = 'XXXXX'
    //加固ApK输出路径
    reinforce_apk_path = 'build/outputs/apk/release/reinforce/'
    //加固包名称
    reinforce_apk_name = 'build/outputs/apk/release/reinforce/release_encrypted_aligned_signed.apk'
    //渠道配置文件
    chanel_config_path = reinforce_plugin_path + '/channel.txt'
    //渠道Apk输出路径
    channel_apks_path = 'build/outputs/apk/release/channels/'
}

/**
 * 注释:编译加固渠道包
 * 时间:2019/1/2 0002 14:01
 * 作者:郭翰林
 */
task buildReinforceRelease() {
    group '360reinforce'
    dependsOn('assembleRelease')
    doLast {
        //第一步:清空缓存
        cleanFilesPath(reinforce_plugin_path + "/.cache")
        cleanFilesPath(reinforce_plugin_path + "/output")
        cleanFilesPath(reinforce_plugin_path + "/jiagu.db")
        cleanFilesPath(reinforce_apk_path)
        cleanFilesPath(channel_apks_path)
        //第二步:开始加固
        reinforceApk()
        //第三部:重命名加固包
        renameReinforceApk()
        //第四步:打多渠道包
        buildChannelApks()
    }
}

/**
 * 注释:打多渠道包
 * 时间:2019/1/4 0004 13:26
 * 作者:郭翰林
 */
def buildChannelApks() {
    println('开始编译多渠道包')
    File reinforceApk = new File(reinforce_apk_name)
    if (!reinforceApk.exists()) {
        return
    }
    //新建渠道包目录
    File channelsPath = new File(channel_apks_path)
    if (!channelsPath.exists()) {
        channelsPath.mkdir()
    }
    exec {
        commandLine "powershell", "java -jar", reinforce_plugin_path + "/lib/walle-cli-all.jar batch -f ", chanel_config_path, reinforce_apk_name, channel_apks_path
    }
    println('编译多渠道包成功,生成的渠道包路径:' + channelsPath.getAbsolutePath())
}

/**
 * 注释:重命名已加固好的APK
 * 时间:2019/1/4 0004 12:48
 * 作者:郭翰林
 */
def renameReinforceApk() {
    File files = new File('build/outputs/apk/release/reinforce')
    if (!files.exists()) {
        return
    }
    if (files.isDirectory()) {
        String[] content = files.list()//取得当前目录下所有文件和文件夹
        for (String name : content) {
            //由于第一步清空缓存,reinforce文件夹内只会有一个已经加固并且签名的包
            File signedApk = new File('build/outputs/apk/release/reinforce', name)
            File renameApk = new File(reinforce_apk_name)
            if (signedApk.exists() && signedApk.isFile()) {
                signedApk.renameTo(renameApk)
            }
        }
    }
}

/**
 * 注释:使用360加固加固Release包
 * 时间:2019/1/2 0002 14:32
 * 作者:郭翰林
 */
def reinforceApk() {
    println('开始进行加固操作')
    File releaseApk = new File('build/outputs/apk/release/app-release.apk')
    if (!releaseApk.exists()) {
        throw new FileNotFoundException('Release包不存在,无法进行加固操作')
    }
    String releasePath = 'build/outputs/apk/release/app-release.apk'
    //创建加固文件夹
    File reinforcePath = new File(reinforce_apk_path)
    if (!reinforcePath.exists()) {
        reinforcePath.mkdir()
    }
    exec {
        commandLine "powershell", "java -jar", reinforce_plugin_path + "/jiagu.jar", "-login", reinforce_plugin_name, reinforce_plugin_passward
    }
    exec {
        commandLine "powershell", "java -jar", reinforce_plugin_path + "/jiagu.jar", "-importsign", key_store_path, key_store_passward, alias, alias_passward
    }
    exec {
        commandLine "powershell", "java -jar", reinforce_plugin_path + "/jiagu.jar", "-jiagu", releasePath, reinforce_apk_path, "-autosign"
    }
    println('加固操作结束,加固包路径' + reinforcePath.getAbsolutePath())
}

/**
 * 注释:清空文件夹
 * 时间:2019/1/2 0002 14:15
 * 作者:郭翰林
 */
def cleanFilesPath(String path) {
    File files = new File(path)
    if (!files.exists()) {
        return
    }
    println('开始执行清除:' + files.getAbsolutePath())
    if (files.isDirectory()) {
        String[] content = files.list()//取得当前目录下所有文件和文件夹
        for (String name : content) {
            File temp = new File(path, name)
            if (temp.isDirectory()) {//判断是否是目录
                cleanFilesPath(temp.getAbsolutePath())//递归调用,删除目录里的内容
                temp.delete()
            } else {
                temp.delete()
            }
        }
    }
    files.delete()
}

(2)MAC环境下脚本

ext {
    //加固插件路径
    reinforce_plugin_path = "${project.rootDir}/reinforce"
    reinforce_plugin_name = 'xxxxxx'
    reinforce_plugin_passward = 'xxxxxxx'
    //签名信息
    key_store_path = "${project.rootDir}/app/xyz.keystore"
    key_store_passward = 'xxxxxxx'
    alias = 'xxxxx'
    alias_passward = 'xxxxxxxx'
    //Release Apk输出路劲
    release_apk_path = "${project.buildDir}/outputs/apk/release/app-release.apk"
    //加固ApK输出路径
    reinforce_apk_path = "${project.buildDir}/outputs/apk/release/reinforce/"
    //加固包名称
    reinforce_apk_name = "${project.buildDir}/outputs/apk/release/reinforce/release_encrypted_aligned_signed.apk"
    //渠道配置文件
    chanel_config_path = "${reinforce_plugin_path}/channel.txt"
    //渠道Apk输出路径
    channel_apks_path = "${project.buildDir}/outputs/apk/release/channels/"
}

/**
 * 注释:编译加固渠道包
 * 时间:2019/1/2 0002 14:01
 * 作者:郭翰林
 */
task buildReinforceRelease() {
    group '360reinforce'
    dependsOn('assembleRelease')
    doLast {
        //第一步:清空缓存
        cleanFilesPath(reinforce_plugin_path + "/.cache")
        cleanFilesPath(reinforce_plugin_path + "/output")
        cleanFilesPath(reinforce_plugin_path + "/jiagu.db")
        cleanFilesPath(reinforce_apk_path)
        cleanFilesPath(channel_apks_path)
        //第二步:开始加固
        reinforceApk()
        //第三部:重命名加固包
        renameReinforceApk()
        //第四步:打多渠道包
        buildChannelApks()
        //清除无用缓存
        cleanFilesPath(reinforce_plugin_path + "/.cache")
        cleanFilesPath(reinforce_plugin_path + "/output")
        cleanFilesPath(reinforce_plugin_path + "/jiagu.db")
    }
}

/**
 * 注释:打多渠道包
 * 时间:2019/1/4 0004 13:26
 * 作者:郭翰林
 */
def buildChannelApks() {
    println('开始编译多渠道包')
    File reinforceApk = new File(reinforce_apk_name)
    if (!reinforceApk.exists()) {
        return
    }
    //新建渠道包目录
    File channelsPath = new File(channel_apks_path)
    if (!channelsPath.exists()) {
        channelsPath.mkdir()
    }
    exec {
        commandLine "bash", "-c", "java -jar ${reinforce_plugin_path}/lib/walle-cli-all.jar batch -f ${chanel_config_path} ${reinforce_apk_name} ${channel_apks_path}"
    }
    println('编译多渠道包成功,生成的渠道包路径:' + channelsPath.getAbsolutePath())
}

/**
 * 注释:重命名已加固好的APK
 * 时间:2019/1/4 0004 12:48
 * 作者:郭翰林
 */
def renameReinforceApk() {
    File files = new File(reinforce_apk_path)
    if (!files.exists()) {
        return
    }
    if (files.isDirectory()) {
        String[] content = files.list()//取得当前目录下所有文件和文件夹
        for (String name : content) {
            //由于第一步清空缓存,reinforce文件夹内只会有一个已经加固并且签名的包
            File signedApk = new File(reinforce_apk_path, name)
            File renameApk = new File(reinforce_apk_name)
            if (signedApk.exists() && signedApk.isFile()) {
                signedApk.renameTo(renameApk)
            }
        }
    }
}

/**
 * 注释:使用360加固加固Release包
 * 时间:2019/1/2 0002 14:32
 * 作者:郭翰林
 */
def reinforceApk() {
    println('开始进行加固操作')
    File releaseApk = new File(release_apk_path)
    if (!releaseApk.exists()) {
        throw new FileNotFoundException("Release包不存在,无法进行加固操作,文件路径:${releaseApk.getAbsolutePath()}")
    }
    //创建加固文件夹
    File reinforcePath = new File(reinforce_apk_path)
    if (!reinforcePath.exists()) {
        reinforcePath.mkdir()
    }
    exec {
        commandLine "bash", "-c", "chmod +x ${reinforce_plugin_path}/java/bin/*"
    }
    exec {
        commandLine "bash", "-c", "java -jar ${reinforce_plugin_path}/jiagu.jar -login ${reinforce_plugin_name} ${reinforce_plugin_passward}"
    }
    exec {
        commandLine "bash", "-c", "java -jar ${reinforce_plugin_path}/jiagu.jar -importsign ${key_store_path} ${key_store_passward} ${alias} ${alias_passward}"
    }
    exec {
        commandLine "bash", "-c", "java -jar ${reinforce_plugin_path}/jiagu.jar -jiagu ${release_apk_path} ${reinforce_apk_path} -autosign"
    }
    println('加固操作结束,加固包路径' + reinforcePath.getAbsolutePath())
}

/**
 * 注释:清空文件夹
 * 时间:2019/1/2 0002 14:15
 * 作者:郭翰林
 */
def cleanFilesPath(String path) {
    File files = new File(path)
    if (!files.exists()) {
        return
    }
    println('开始执行清除:' + files.getAbsolutePath())
    if (files.isDirectory()) {
        String[] content = files.list()//取得当前目录下所有文件和文件夹
        for (String name : content) {
            File temp = new File(path, name)
            if (temp.isDirectory()) {//判断是否是目录
                cleanFilesPath(temp.getAbsolutePath())//递归调用,删除目录里的内容
                temp.delete()
            } else {
                temp.delete()
            }
        }
    }
    files.delete()
}

四、集成完毕之后,如何使用

1、查找名为buildReinforceRelease的Task任务
2、待生成完毕之后,渠道包在主模块下的build/outputs/apk/release/channels/文件夹下

命令使用方法.png
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 218,451评论 6 506
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,172评论 3 394
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 164,782评论 0 354
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,709评论 1 294
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,733评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,578评论 1 305
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,320评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,241评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,686评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,878评论 3 336
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,992评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,715评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,336评论 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,912评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,040评论 1 270
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,173评论 3 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,947评论 2 355