Understanding Android app size

Hi,

I’m testing following two options for bundling data with my Android app:

  1. A pre-populated SQLite database having size 19.8MB, placed in assets folder

  2. 08 .csv files containing data to be populated in SQLite database on first app launch, placed in assets folder and having size 7.1MB

This testing is being conducted with the sole objective of keeping the app size (post install) smaller.

The results, however, are incomprehensible for me: the post install app size is almost the same in both case, actually a tad bit smaller in case of option 1. Below are the screenshots:

Option 1:

Option 2:

While my main focus is on app size, I can’t happen to ignore the inflated cache size in case of Option 1.

So, if these results are accurate and I’m doing everything right, there is apparently no use of dumping a large sized database file in favour of smaller sized .csv files.

Pl help me out of this confusion!

I do not know how the Settings app (or wherever you got those values from) computes those values.

All that I can recommend is that you make a clean comparison, such as using two separate emulator images. Android’s “uninstall” is a bit weird on modern versions, so if these are from the same device/emulator image, it is possible that Option 2 includes some elements of Option 1.

First, I tried 2 images of Nexus 6 API 28 and following are the results:

Option 1:

Option 2:

Then, I tried 2 images of Nexus 5 API 21 and following are the results:

Option 1:

Option 2:

  • Nexus 5 API 21: results are almost the same in both cases. Any idea why?

  • Nexus 6 API 28: size is substantially lower in case of Option 2, as expected, but there is almost no user data in case of Option 1. So, should we assume that database size counts as app size in case of Option 1 and as user data in case of Option 2?

  • Also, why is there such a big difference in total size between both APIs?

Apparently, I buried the lede, so let me quote myself to emphasize the point:

With that in mind…

No, sorry.

Are you sure that you ran the code that copied the database from assets to a file on the filesystem? If you are, then the Settings app is drunk, or possibly just is not real-time.

I do not know, sorry.

Yep I’m sure. Also, the app worked fine after installation.

Do I also need to Invalidate cache of Android Studio before each install?

Then Settings is drunk or not real-time. If you copied 19.8MB to a file, then I cannot explain how anything called “User Data” would not count that.

That should have no effect. That clears out cached libraries, not app data.

Tried Option 1 with a new Emulator image: Pixel XL API 29 but still user data is negligible and most of the size is in cache.

Below is the code in my BondDatabase class:

private static volatile BondDatabase INSTANCE = null;

public synchronized static BondDatabase get(Context context) {
    if (INSTANCE == null) {
        INSTANCE = create(context);
    }
    return INSTANCE;
}

private static BondDatabase create(final Context context) {
    return Room.databaseBuilder(
            context.getApplicationContext(),
            BondDatabase.class, DB_NAME)
            .createFromAsset("database/" + DB_NAME)
            .build();
}

Is there any problem with how the database is being instantiated?

That seems reasonable.

All this boils down to what you are really trying to achieve:

  • If you are trying to do the right thing for the user, measure those things that you can measure objectively, rather than using Settings. You know how big your APK file is, as you built it. You can use adb shell run-as ... "du /data/data/..." (where both ... is your application ID) to see your disk usage in internal storage, at least for some Android devices (I do not know how prevalent du is, but it is in the Pixel 4 that I just tried).

  • If, OTOH, you are trying to “win” that Settings screen… bear in mind that the Settings app frequently gets modified by device manufacturers, on top of OS version differences.

Nexus 6 API 28
Option 1

4       /data/data/com.appicacious.bondwallet/cache/WebView/SafeBrowsing
8       /data/data/com.appicacious.bondwallet/cache/WebView
4       /data/data/com.appicacious.bondwallet/cache/mopub-volley-cache
16      /data/data/com.appicacious.bondwallet/cache
4       /data/data/com.appicacious.bondwallet/code_cache
36      /data/data/com.appicacious.bondwallet/shared_prefs
240     /data/data/com.appicacious.bondwallet/no_backup
20508   /data/data/com.appicacious.bondwallet/databases
8       /data/data/com.appicacious.bondwallet/files
4       /data/data/com.appicacious.bondwallet/app_webview/webrtc_event_logs
4       /data/data/com.appicacious.bondwallet/app_webview/blob_storage/d823c716-1cd5-4934-bf79-07487f0f5ebd
8       /data/data/com.appicacious.bondwallet/app_webview/blob_storage
8       /data/data/com.appicacious.bondwallet/app_webview/GPUCache/index-dir
16      /data/data/com.appicacious.bondwallet/app_webview/GPUCache
88      /data/data/com.appicacious.bondwallet/app_webview
4       /data/data/com.appicacious.bondwallet/app_textures
20912   /data/data/com.appicacious.bondwallet

Option 2

4       /data/data/com.appicacious.bondwallet/cache/WebView/SafeBrowsing
8       /data/data/com.appicacious.bondwallet/cache/WebView
4       /data/data/com.appicacious.bondwallet/cache/mopub-volley-cache
8       /data/data/com.appicacious.bondwallet/cache/org.chromium.android_webview/index-dir
104     /data/data/com.appicacious.bondwallet/cache/org.chromium.android_webview
120     /data/data/com.appicacious.bondwallet/cache
4       /data/data/com.appicacious.bondwallet/code_cache
36      /data/data/com.appicacious.bondwallet/shared_prefs
304     /data/data/com.appicacious.bondwallet/no_backup
21076   /data/data/com.appicacious.bondwallet/databases
8       /data/data/com.appicacious.bondwallet/files
4       /data/data/com.appicacious.bondwallet/app_webview/webrtc_event_logs
4       /data/data/com.appicacious.bondwallet/app_webview/blob_storage/c6816067-3769-449e-9ee1-1910a486dccf
8       /data/data/com.appicacious.bondwallet/app_webview/blob_storage
8       /data/data/com.appicacious.bondwallet/app_webview/GPUCache/index-dir
16      /data/data/com.appicacious.bondwallet/app_webview/GPUCache
112     /data/data/com.appicacious.bondwallet/app_webview
4       /data/data/com.appicacious.bondwallet/app_textures
21672   /data/data/com.appicacious.bondwallet

I can’t see how this data can help select one option over the other.

All I want to do is to see which option I should choose in order to keep the app size relatively smaller: whether to package a pre-populated database with the app or the raw data in the form of csv files. Apparently, the size of assets folder is 12MB+ apart in both options but this difference ain’t evident in post-install app sizes.

So kindly point me in the right direction…may it be Settings or any other tool. I just need to get it sorted.

Thanks

Option 1 is using 20912 KB of disk space. Option 2 is using 21672 KB of disk space. Only you can decide if that is a material difference or not.

Bear in mind that APK files are compressed, and the compressibility of the assets may be different.

But, if you are saying that the two APK files are similarly-sized, then unless you are worried about the < 1MB disk space difference reported by du, the two approaches are equivalent.

That’s relevant in case of APK size but I’m concerned about post install size of the app.
So when the files are uncompressed, shouldn’t the install size ideally be larger by 12MB+ in case of Option 1 as compared to Option 2?

In general, they are not uncompressed. While certain items are, most stuff just stays in the APK and gets decompressed on the fly when it is read in.

My app is already on Play store Alpha channel with a pre populated database. So I decided to release a new version with CSV files (Option 2) in order to see the difference between both options in real life.

The new app size is ~54MB which was pretty much what I expected considering the size of ~67MB in earlier version.
These reading are again from Settings app of my physical device.

While the current issue of selecting one option over the other is settled, I happen to have another question.

How can I drilldown this app size of 54MB? I need to know why this is still so big. I may be using some largely sized libraries but I don’t know how to find that out.

I’m summing up the various size related info below:

  • .csv files in assets: ~7MB
  • .aab file: ~16MB
  • Download size (as per Play store): ~11MB
  • App size (Settings app): ~54MB
  • User data (Settings app): ~24MB
  • adb shell du: corresponds to the user data mentioned above

Thanks!

Well, as I have mentioned a few times, I cannot tell you where any given implementation of the Settings app is getting its number.

You can use the APK Analyzer to determine where your 16MB APK/AAB space is going. And, you can use Android Studio’s Device File Explorer (with a debuggable app build) to determine where the 24MB of disk space is going. Those are the only two things that you really control.

So does it mean that I should only be concerned about the APK/AAB size and the size represented by adb shell du?

All I can tell you is: I do not know how you would affect anything else, beyond those two items.

Ok I’ll take this discussion further if anything new comes to my mind.

Thanks for the guidance!