#android

Today, I faced the challenge to check from within the Android SDK, if the app I was running was installed via Google Play or not.

In the Android SDK, there is a way to get the package name of the app that installed a specific package.

Getting the package name is quite easy provided you have the Context instance:

1String packageName = ctx.getPackageName();

The getPackageName method returns the name of the application's package.

Once we have the package name, getting the package name of the app that was used to install the application depends on which version of Android you are running. The original method was getInstallerPackageName:

1PackageManager pm = ctx.getPackageManager();
2String installerPackageName = pm.getInstallerPackageName(packageName);

However, this method was deprecated in Android API level 30. As of Android API level 30, you're supposed to use InstallSourceInfo.getInstallingPackageName instead:

1PackageManager pm = ctx.getPackageManager();
2InstallSourceInfo info = pm.getInstallSourceInfo(packageName);
3
4String installerPackageName = "";
5if (info != null) {
6    installerPackageName = info.getInstallingPackageName();
7}

Now that we have the package name of the installer app, how do we check if it's Google Play? You need to check if that package name equals com.android.vending:

1"com.android.vending".equals(installerPackageName);

Don't make the mistake of doing it like this:

1installerPackageName.equals("com.android.vending");

This might fail as installerPackageName might be null. If that's the case, the second approach will fail while the first one will work just fine.

So, combining everything together gives us (with some extra options):

YDGooglePlayUtils.java

 1package be.yellowduck.apps.utils;
 2
 3import android.content.Context;
 4import android.content.pm.InstallSourceInfo;
 5import android.content.pm.PackageManager;
 6import android.os.Build;
 7import android.text.TextUtils;
 8
 9public class YDGooglePlayUtils {
10
11    public static String GOOGLE_PLAY = "com.android.vending";
12    public static String AMAZON = "com.amazon.venezia";
13
14    public static boolean isInstalledViaGooglePlay(Context ctx) {
15        return isInstalledVia(ctx, GOOGLE_PLAY);
16    }
17
18    public static boolean isInstalledViaAmazon(Context ctx) {
19        return isInstalledVia(ctx, AMAZON);
20    }
21
22    public static boolean isSideloaded(Context ctx) {
23        String installer = getInstallerPackageName(ctx);
24        return TextUtils.isEmpty(installer);
25    }
26
27    public static boolean isInstalledVia(Context ctx, String required) {
28        String installer = getInstallerPackageName(ctx);
29        return required.equals(installer);
30    }
31
32    private static String getInstallerPackageName(Context ctx) {
33        try {
34            String packageName = ctx.getPackageName();
35            PackageManager pm = ctx.getPackageManager();
36            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
37                InstallSourceInfo info = pm.getInstallSourceInfo(packageName);
38                if (info != null) {
39                    return info.getInstallingPackageName();
40                }
41            }
42            return pm.getInstallerPackageName(packageName);
43        } catch (PackageManager.NameNotFoundException e) {
44        }
45        return "";
46    }
47
48}