Multi-channel Packaging of Alliances

Keywords: Android Gradle

Step 1:

1. According to umeng requirements, manifest files need to be

<meta-data
 android:name="UMENG_CHANNEL"
 android:value="${UMENG_CHANNEL_VALUE}" />

This configuration, where value is the channel name of wandoujia, 360, etc., but we will not write the channel name here, write a placeholder, which will be replaced dynamically when gradle compiles.   


2. Add the following to the android {} of build.gradle of module (usually app):

productFlavors{
          wandoujia{
             manifestPlaceholders = [UMENG_CHANNEL_VALUE: "wandoujia"]
          }
          xiaomi{
             manifestPlaceholders=[UMENG_CHANNEL_VALUE: "xiaomi"]
          }
      }

Product Flavors is a self-node of the android node. What channel package do you need to play? Here we assign UMENG_CHANNEL_VALUE with channel name according to umeng's requirement.

3. Optimize 1: There are only two channels above. If there are dozens of channels, they all write like this. There are too many repetitions. It is observed that each channel is the name of flavor, so we revise it as follows:

productFlavors{
  wandoujia{
      //manifestPlaceholders = [UMENG_CHANNEL_VALUE: "wandoujia"]
  }
  xiaomi{
      //manifestPlaceholders=[UMENG_CHANNEL_VALUE: "xiaomi"]
  }
 }
 productFlavors.all { flavor ->
  flavor.manifestPlaceholders = [UMENG_CHANNEL_VALUE: name]
 }

3. Optimize 2: The name of the APK generated after signature packing above has default naming rules, such as: xxx-xiaomi-release.apk, but we want to include version information such as: x xxx-xiaomi-release-1.0.apk, so the final packaging script is as follows:

productFlavors{
    wandoujia{
        //manifestPlaceholders = [UMENG_CHANNEL_VALUE: "wandoujia"]
    }
    xiaomi{
        //manifestPlaceholders=[UMENG_CHANNEL_VALUE: "xiaomi"]
    }
 }
 productFlavors.all { flavor ->
    flavor.manifestPlaceholders = [UMENG_CHANNEL_VALUE: name]
 }
 applicationVariants.all { variant ->
    variant.outputs.each { output ->
        def outputFile = output.outputFile
        if (outputFile != null && outputFile.name.endsWith('.apk')) {
            def fileName = outputFile.name.replace(".apk", "-${defaultConfig.versionName}.apk")
            output.outputFile = new File(outputFile.parent, fileName)
        }
    }
 }

4. Access
In the code, we can get the channel by reading mate-data information, and then add it to the request parameters. The acquisition method is as follows:

private String getChannel() {
   try {
       PackageManager pm = getPackageManager();
       ApplicationInfo appInfo = pm.getApplicationInfo(getPackageName(), PackageManager.GET_META_DATA);
       return appInfo.metaData.getString("UMENG_CHANNEL");
   } catch (PackageManager.NameNotFoundException ignored) {
   }
   return "";
}

5. Perform signature packing:

Then you go to app/build/outputs/apk and you can see the channel packages automatically typed.
 

2. Disadvantages:

This kind of packing method is inefficient. If dozens of packages are available, it takes more than ten seconds to pack a bag fast and several minutes to pack a bag slowly, which is closely related to the performance of the machine.

Posted by H-Fish on Thu, 11 Apr 2019 13:00:32 -0700