【问题标题】:How to check programmatically if an application is installed or not in Android?如何以编程方式检查 Android 中是否安装了应用程序?
【发布时间】:2012-07-08 16:22:21
【问题描述】:

我们以编程方式安装了应用程序。

  1. 如果应用程序已安装在设备中,应用程序会自动打开。
  2. 否则安装特定应用程序。

引导我。我不知道。 谢谢。

【问题讨论】:

标签: android apk


【解决方案1】:

试试这个:

public class MainActivity extends AppCompatActivity {
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        // Add respective layout
        setContentView(R.layout.main_activity);

        // Use package name which we want to check
        boolean isAppInstalled = appInstalledOrNot("com.check.application");  
        
        if(isAppInstalled) {
            //This intent will help you to launch if the package is already installed
            Intent LaunchIntent = getPackageManager()
                .getLaunchIntentForPackage("com.check.application");
            startActivity(LaunchIntent);
                    
            Log.i("SampleLog", "Application is already installed.");          
        } else {
            // Do whatever we want to do if application not installed
            // For example, Redirect to play store

            Log.i("SampleLog", "Application is not currently installed.");
        }
    }

    private boolean appInstalledOrNot(String uri) {
        PackageManager pm = getPackageManager();
        try {
            pm.getPackageInfo(uri, PackageManager.GET_ACTIVITIES);
            return true;
        } catch (PackageManager.NameNotFoundException e) {
        }

        return false;
    }

}

【讨论】:

  • @Sathish:希望对你有所帮助
  • 毫无疑问你的帖子真的很有帮助,但我得到一个异常“java.lang.RuntimeException: 添加窗口失败”和“E/AndroidRuntime(7554): Caused by: android.os.TransactionTooLargeException 05-14 11:37:25.305: E/AndroidRuntime(7554): 在 android.os.BinderProxy.transact(Native Method) 05-14 11:37:25.305: E/AndroidRuntime(7554): 在 android.view.IWindowSession $Stub$Proxy.add(IWindowSession.java:516) 05-14 11:37:25.305: E/AndroidRuntime(7554): 在 android.view.ViewRootImpl.setView(ViewRootImpl.java:494) "
  • @BlueGreen:嗨,希望这个链接可以帮助你,stackoverflow.com/questions/11451393/…,否则如果你正在使用对话框类,请检查它。 :)
  • @Aerrow .. 假设我正在检查我的 .apk 是否已安装?在安装时...我在检查我的包 com.test.installedornot 时遇到同样的异常。我的 .apk 大小超过 9MB 那么在这种情况下我将如何管理这个异常?
  • API 23 Fatal Exception: java.lang.RuntimeException Package manager has died 上崩溃了
【解决方案2】:

比公认的答案更清洁的解决方案(基于this question):

public static boolean isAppInstalled(Context context, String packageName) {
    try {
        context.getPackageManager().getApplicationInfo(packageName, 0);
        return true;
    }
    catch (PackageManager.NameNotFoundException e) {
        return false;
    }
}

我选择将它作为静态实用程序放在帮助类中。使用示例:

boolean whatsappFound = AndroidUtils.isAppInstalled(context, "com.whatsapp");

This answer 展示了如果应用程序丢失,如何从 Play 商店获取应用程序,但需要注意没有 Play 商店的设备。

【讨论】:

  • 这是否需要任何特定的 Android 权限才能工作?
  • @Bootstrapper:不,它不需要任何特殊权限。
  • 谢谢(工作解决方案)
【解决方案3】:

上面的代码对我不起作用。以下方法有效。

使用适当的信息创建一个 Intent 对象,然后使用以下函数检查 Intent 是否可调用:

private boolean isCallable(Intent intent) {  
        List<ResolveInfo> list = getPackageManager().queryIntentActivities(intent,   
        PackageManager.MATCH_DEFAULT_ONLY);  
        return list.size() > 0;  
}

【讨论】:

  • 这样更好,因为它不需要使用异常进行流量控制!
  • @QED 使用异常作为if 语句的人数令人震惊!这绝对是正确的答案
  • Intent 的内容是什么?带有 packageName 的字符串不起作用
  • @HenriquedeSousa Intent intent = getPackageManager().getLaunchIntentForPackage("org.package.name");
  • 如果应用被禁用,应该是错误的。
【解决方案4】:

如果您知道包名称,则无需使用 try-catch 块或迭代一堆包即可:

public static boolean isPackageInstalled(Context context, String packageName) {
    final PackageManager packageManager = context.getPackageManager();
    Intent intent = packageManager.getLaunchIntentForPackage(packageName);
    if (intent == null) {
        return false;
    }
    List<ResolveInfo> list = packageManager.queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY);
    return !list.isEmpty();
}

【讨论】:

  • return !list.isEmpty(); 会更适合 java 风格
【解决方案5】:

此代码会检查以确保应用已安装,但也会检查以确保已启用。

private boolean isAppInstalled(String packageName) {
    PackageManager pm = getPackageManager();
    try {
        pm.getPackageInfo(packageName, PackageManager.GET_ACTIVITIES);
        return pm.getApplicationInfo(packageName, 0).enabled;
    }
    catch (PackageManager.NameNotFoundException e) {
        e.printStackTrace();
        return false;
    }
}

【讨论】:

  • 应用的包名。例如,“com.example.apps.myapp”。我已经编辑了答案以显示 packageName 而不是 uri。
【解决方案6】:

使用 kotlin 检查 Android 中是否安装了 App。

创建 kotlin 扩展。

fun PackageManager.isAppInstalled(packageName: String): Boolean = try {
        getApplicationInfo(packageName, PackageManager.GET_META_DATA)
        true
    } catch (e: Exception) {
        false
    }

现在,可以检查应用是否已安装

if (packageManager.isAppInstalled("AppPackageName")) {
    // App is installed
}else{
    // App is not installed
}

【讨论】:

    【解决方案7】:

    使用 Kotlin 的更简单的实现

    fun PackageManager.isAppInstalled(packageName: String): Boolean =
            getInstalledApplications(PackageManager.GET_META_DATA)
                    .firstOrNull { it.packageName == packageName } != null
    

    并这样称呼它(寻找 Spotify 应用程序):

    packageManager.isAppInstalled("com.spotify.music")
    

    【讨论】:

      【解决方案8】:

      比接受的答案(基于AndroidRate Library)更清洁的解决方案(没有try-catch):

      public static boolean isPackageExists(@NonNull final Context context, @NonNull final String targetPackage) {
          List<ApplicationInfo> packages = context.getPackageManager().getInstalledApplications(0);
          for (ApplicationInfo packageInfo : packages) {
              if (targetPackage.equals(packageInfo.packageName)) {
                  return true;
              }
          }
          return false;
      }
      

      【讨论】:

        【解决方案9】:

        我认为使用 try/catch 模式对性能来说不是很好。我建议使用这个:

        public static boolean appInstalledOrNot(Context context, String uri) {
            PackageManager pm = context.getPackageManager();
            List<PackageInfo> packageInfoList = pm.getInstalledPackages(PackageManager.GET_ACTIVITIES);
            if (packageInfoList != null) {
                for (PackageInfo packageInfo : packageInfoList) {
                    String packageName = packageInfo.packageName;
                    if (packageName != null && packageName.equals(uri)) {
                        return true;
                    }
                }
            }
            return false;
        }
        

        【讨论】:

        • 以上代码在 kotlin ``` private fun isAppInstalled(context: Context, uri: String): Boolean { val packageInfoList = context.packageManager.getInstalledPackages(PackageManager.GET_ACTIVITIES) return packageInfoList.asSequence() .filter { it?.packageName == uri }.any() } ```
        【解决方案10】:

        试试这个

        此代码用于检查是否安装了带有包名的应用程序或 如果不是,那么它将打开您的应用程序的 Playstore 链接,否则您的 已安装的应用程序

        String your_apppackagename="com.app.testing";
            PackageManager packageManager = getPackageManager();
            ApplicationInfo applicationInfo = null;
            try {
                applicationInfo = packageManager.getApplicationInfo(your_apppackagename, 0);
            } catch (PackageManager.NameNotFoundException e) {
                e.printStackTrace();
            }
            if (applicationInfo == null) {
                // not installed it will open your app directly on playstore
                startActivity(new Intent(Intent.ACTION_VIEW, Uri.parse("https://play.google.com/store/apps/details?id=" + your_apppackagename)));
            } else {
                // Installed
                Intent LaunchIntent = packageManager.getLaunchIntentForPackage(your_apppackagename);
                startActivity( LaunchIntent );
            }
        

        【讨论】:

          【解决方案11】:

          所有答案仅检查是否安装了某些应用程序。但是,众所周知,一个应用程序可以安装但被用户禁用,无法使用。

          因此,此解决方案会同时检查两者。即,已安装并启用的应用

          public static boolean isPackageInstalled(String packageName, PackageManager packageManager) {
               try {
                    return packageManager.getApplicationInfo(packageName, 0).enabled;
               }
               catch (PackageManager.NameNotFoundException e) {
                    return false;
               }
          }
          

          调用方法isPackageInstalled():

          boolean isAppInstalled = isPackageInstalled("com.android.app" , this.getPackageManager());
          

          现在,使用布尔变量isAppInstalled 做任何你想做的事情。

          if(isAppInstalled ) {
              /* do whatever you want */
          }
          

          【讨论】:

            【解决方案12】:

            @Egemen Hamutçu 在 kotlin B-) 中的回答

                private fun isAppInstalled(context: Context, uri: String): Boolean {
                    val packageInfoList = context.packageManager.getInstalledPackages(PackageManager.GET_ACTIVITIES)
                    return packageInfoList.asSequence().filter { it?.packageName == uri }.any()
                }
            

            【讨论】:

              【解决方案13】:

              其他问题的一个很酷的答案。 例如,如果您不想区分“com.myapp.debug”和“com.myapp.release”!

              public static boolean isAppInstalled(final Context context, final String packageName) {
                  final List<ApplicationInfo> appsInfo = context.getPackageManager().getInstalledApplications(0);
                  for (final ApplicationInfo appInfo : appsInfo) {
                      if (appInfo.packageName.contains(packageName)) return true;
                  }
                  return false;
              }
              

              【讨论】:

                【解决方案14】:

                Kotlin suger 效果更好:

                  private fun isSomePackageInstalled(context: Context, packageName: String): Boolean {
                
                    val packageManager = context.packageManager
                
                    return runCatching { packageManager.getPackageInfo(packageName, 0) }.isSuccess
                  }
                

                【讨论】:

                  【解决方案15】:

                  您可以使用 Kotlin 扩展来做到这一点:

                  fun Context.getInstalledPackages(): List<String> {
                      val packagesList = mutableListOf<String>()
                      packageManager.getInstalledPackages(0).forEach {
                          if ( it.applicationInfo.sourceDir.startsWith("/data/app/") && it.versionName != null)
                              packagesList.add(it.packageName)
                      }
                      return packagesList
                  }
                  
                  fun Context.isInDevice(packageName: String): Boolean {
                      return getInstalledPackages().contains(packageName)
                  }
                  

                  【讨论】:

                    【解决方案16】:

                    Android 11 更新
                    您必须在清单中指定要搜索的确切捆绑包 ID。

                    facebook 和 whatsapp 的示例:

                    在“应用程序”上方的清单内(权限所在)

                    <queries>
                        <package android:name="com.whatsapp" />
                        <package android:name="com.facebook.katana" />
                    </queries>  
                    

                    这将允许您检查是否安装了 facebook 和 whatsapp,否则您将始终得到错误的检查。

                    进一步阅读该主题:
                    https://medium.com/androiddevelopers/package-visibility-in-android-11-cc857f221cd9

                    【讨论】:

                      猜你喜欢
                      • 1970-01-01
                      • 1970-01-01
                      • 2022-12-03
                      • 2011-03-31
                      • 2013-09-16
                      • 2017-08-29
                      • 1970-01-01
                      • 1970-01-01
                      相关资源
                      最近更新 更多