Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Shrinking WhatsApp

Shrinking WhatsApp

Billions of people in over 180 countries use WhatsApp to stay in touch with friends and family. At WhatsApp we relentlessly work on shrinking our apk as much as possible given that many of our users live in regions with poor connectivity and we are committed to leave no one behind. In this session we will cover some of the wins, regressions, strategies and technologies that we use to tame WhatApp's apk size.

Conference: https://www.droidcon.sg
Video: coming soon

Evelio Tarazona Cáceres

July 18, 2019
Tweet

More Decks by Evelio Tarazona Cáceres

Other Decks in Technology

Transcript

  1. We focus on building a simple, private and secure messaging

    service that works fast and reliably anywhere in the world.
  2. Simple, Reliable, Secure Messaging WhatsApp is widely used on Android

    devices. 
 As we add new features to the product, 
 we must continue supporting it in older devices.
  3. splits {
 density {
 enable true
 include "ldpi", "mdpi", "hdpi",

    "xhdpi", "xxhdpi", "xxxhdpi"
 }
 
 
 
 } // apk splits by density
  4. splits {
 density {
 enable true
 include "ldpi", "mdpi", "hdpi",

    "xhdpi", "xxhdpi", "xxxhdpi"
 }
 abi { enable true include "armeabi-v7a", "arm64-v8a", "x86", "x86_64" } } // apk splits by density & abi
  5. ➜ apksigner USAGE: apksigner <command> [options] apksigner --version apksigner --help

    EXAMPLE: apksigner sign --ks release.jks app.apk apksigner verify --verbose app.apk apksigner is a tool for signing Android APK files and for checking whether signatures of APK files will verify on Android devices. # built-in tooling
  6. ➜ zipalign Zip alignment utility Copyright (C) 2009 The Android

    Open Source Project Usage: zipalign [-f] [-p] [-v] [-z] <align> infile.zip outfile.zip zipalign -c [-p] [-v] <align> infile.zip <align>: alignment in bytes, e.g. '4' provides 32-bit alig -c: check alignment only (does not modify file) -f: overwrite existing outfile.zip -p: memory page alignment for stored shared object files # built-in tooling
  7. configurations { packagingOptions { exclude 'META-INF/LICENSE.txt' exclude 'META-INF/NOTICE.txt' exclude 'com/google/android/search/verification/client/R.java'

    exclude 'third_party/java_src/error_prone/project/annotations/Annotations.gwt.xml' exclude 'third_party/java_src/error_prone/project/annotations/Google_internal.gwt.xml' exclude 'jsr305_annotations/Jsr305_annotations.gwt.xml' exclude 'error_prone/Annotations.gwt.xml' exclude 'protobuf.meta' exclude 'build-data.properties' exclude 'androidsupportmultidexversion.txt' // ... // This saved us ~300KB // packagingOptions - exclude
  8. res

  9. ➜ optipng ➜ pngcrush ➜ zopflipng ➜ advpng # zopflipng

    reduced png bloat by ~2MB # can't use webp because API level support, use it if you can # do use svg for some assets # vector drawable not used extensively enough # optimize pngs
  10. android {
 defaultConfig {
 resConfigs "en", ”es", "fr”, // …


    }
 } // Removing strings for unsupported languages
 // saved us ~1MB. // remove unused configs
  11. String pool: "My App", "Hello", "Exit", "Settings", "Feature" Default config:

    string/myapp 0x00000001 string/hello 0x00000002 string/exit 0x00000003 string/settings 0x00000004 string/feature 0x00000005 ========== Config size: 20 bytes resources.arsc https://medium.com/androiddevelopers/smallerapk-part-3-removing-unused-resources-1511f9e3f761
  12. String pool: "My App", "Hello", "Exit", "Settings", "Feature", "New feature"

    Default config: -v21 config: string/myapp 0x00000001 string/hello 0x00000002 string/exit 0x00000003 string/settings 0x00000004 string/feature 0x00000005 ========== Config size: 20 bytes resources.arsc https://medium.com/androiddevelopers/smallerapk-part-3-removing-unused-resources-1511f9e3f761
  13. String pool: "My App", "Hello", "Exit", "Settings", "Feature", "New feature"

    Default config: -v21 config: string/myapp 0x00000001 NO_ENTRY string/hello 0x00000002 NO_ENTRY string/exit 0x00000003 NO_ENTRY string/settings 0x00000004 NO_ENTRY string/feature 0x00000005 0x00000006 ========== ========== Config size: 20 bytes 20 bytes! resources.arsc https://medium.com/androiddevelopers/smallerapk-part-3-removing-unused-resources-1511f9e3f761
  14. 4 bytes * 3500 null entries * 50 languages =

    700 kilobytes resources.arsc https://medium.com/androiddevelopers/smallerapk-part-3-removing-unused-resources-1511f9e3f761
  15. android {
 buildTypes {
 release { // ... shrinkResources true


    minifyEnabled true
 } 
 }
 } // built-in optimizations
  16. android {
 buildTypes {
 release { // ... shrinkResources true


    minifyEnabled true
 proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'config/proguard-rules-release.pro' } 
 }
 } // built-in optimizations
  17. android {
 buildTypes {
 release { // ... shrinkResources true


    minifyEnabled true
 proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'config/proguard-rules-release.pro' } 
 }
 } // built-in optimizations
  18. android {
 buildTypes {
 release { // ... shrinkResources true


    minifyEnabled true
 proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'config/proguard-rules-release.pro' } 
 }
 } // built-in optimizations
  19. android.enableR8=true // we observed an increase of ~168KB // but

    a reduction on method reference count // and an improvement on cold start // some people on the community observed regressions R8
  20. Method references count for consumer beta (pre-redex) 55000 81200 107400

    133600 159800 186000 Debug Release/Proguard Release/R8 71,296 90,725 185,674 64K
  21. { "redex" : { "passes" : [ "ReBindRefsPass", "BridgePass", "SynthPass",

    "FinalInlinePass", "DelSuperPass", "SingleImplPass", "MethodInlinePass", "StaticReloPass", "RemoveEmptyClassesPass", "ShortenSrcStringsPass" ] } } sample redex config
  22. Method references count for consumer beta release 55000 81200 107400

    133600 159800 186000 Unoptimized Proguard Proguard + Redex R8 R8 + Redex 61,640 71,296 66,778 90,725 185,674 64K
  23. • Better Proguard/R8 configuration • Additional redex passes • Downloadable

    assets: emoji, stringpacks, other res. • Dynamic Features • Keyframes/VectorDrawables/WebP/basis universal • Work on install and download size • Native library optimizations: 
 noCompress vs. xz compress Future Work