SafetyNet 应用验证 API 是由 Google Play 服务提供支持的库,它允许您的应用以编程方式与设备上的应用验证功能进行交互,从而保护设备免受潜在有害应用的侵害。
如果您的应用处理敏感用户数据(例如财务信息),则务必确认用户的设备已受到保护,免受恶意应用的侵害,并且没有任何应用可能冒充您的应用或执行其他恶意操作。如果设备的安全性不符合最低安全要求,您可以在自己的应用中停用某些功能,以降低用户的风险。
作为持续致力于使 Android 生态系统尽可能安全的一部分,Google 会监控 Android 应用的行为并进行分析。如果应用验证功能检测到潜在危险应用,所有安装了该应用的用户都会收到通知,并被鼓励立即卸载该应用。此过程可保护这些用户的安全和隐私。
SafetyNet 应用验证 API 可让您利用此功能来保护您应用的数据。通过使用此 API,您可以确定用户的设备是否受到应用验证功能的保护,鼓励尚未启用该功能的用户选择启用以获取保护,并识别设备上已安装的任何已知潜在有害应用。
附加服务条款
访问或使用 SafetyNet API 即表示您同意 Google API 服务条款以及以下应用验证 API 服务条款。在使用这些 API 之前,请仔细阅读并理解所有适用的条款和政策。
应用验证 API 服务条款
用于识别潜在有害应用的应用分析可能会产生误报和漏报。此 API 套件返回的结果(或缺少结果)是在我们尽最大努力理解的基础上提供的。您承认并理解,SafetyNet API 套件返回的结果不能保证在任何时候都完全准确。添加 SafetyNet API 依赖项
在使用应用验证 API 之前,请将 SafetyNet API 添加到您的项目中。如果您使用的是 Android Studio,请将此依赖项添加到应用级 Gradle 文件中。如需了解详情,请参阅SafetyNet API 设置。
启用应用验证
SafetyNet 应用验证 API 提供了两种用于启用应用验证功能的方法。您可以使用 isVerifyAppsEnabled()
方法确定应用验证是否已启用,并可以使用 enableVerifyApps()
方法请求启用应用验证。
这两种方法之间的区别在于,isVerifyAppsEnabled()
报告应用验证功能的当前状态,而 enableVerifyApps()
明确征求用户同意使用此功能。如果您的应用只想了解该功能的状态以便做出与安全相关的决策,您的应用应调用 isVerifyAppsEnabled()
。但是,如果您想确保您的应用可以列出潜在有害的已安装应用,则应调用 enableVerifyApps()
。
确定应用验证是否已启用
异步 isVerifyAppsEnabled()
方法可让您的应用确定用户是否已加入应用验证功能。此方法返回一个 VerifyAppsUserResponse
对象,其中包含用户与应用验证功能相关的所有操作的信息,包括是否已启用该功能。
以下代码段展示了如何创建与此方法关联的回调
Kotlin
SafetyNet.getClient(this) .isVerifyAppsEnabled .addOnCompleteListener { task -> if (task.isSuccessful) { if (task.result.isVerifyAppsEnabled) { Log.d("MY_APP_TAG", "The Verify Apps feature is enabled.") } else { Log.d("MY_APP_TAG", "The Verify Apps feature is disabled.") } } else { Log.e("MY_APP_TAG", "A general error occurred.") } }
Java
SafetyNet.getClient(this) .isVerifyAppsEnabled() .addOnCompleteListener(new OnCompleteListener<VerifyAppsUserResponse>() { @Override public void onComplete(Task<VerifyAppsUserResponse> task) { if (task.isSuccessful()) { VerifyAppsUserResponse result = task.getResult(); if (result.isVerifyAppsEnabled()) { Log.d("MY_APP_TAG", "The Verify Apps feature is enabled."); } else { Log.d("MY_APP_TAG", "The Verify Apps feature is disabled."); } } else { Log.e("MY_APP_TAG", "A general error occurred."); } } });
请求启用应用验证
异步 enableVerifyApps()
方法可让您的应用调用对话框,请求用户启用应用验证功能。此方法返回一个 VerifyAppsUserResponse
对象,其中包含用户与应用验证功能相关的所有操作的信息,包括他们是否已同意启用该功能。
以下代码段展示了如何创建与此方法关联的回调
Kotlin
SafetyNet.getClient(this) .enableVerifyApps() .addOnCompleteListener { task -> if (task.isSuccessful) { if (task.result.isVerifyAppsEnabled) { Log.d("MY_APP_TAG", "The user gave consent to enable the Verify Apps feature.") } else { Log.d( "MY_APP_TAG", "The user didn't give consent to enable the Verify Apps feature." ) } } else { Log.e("MY_APP_TAG", "A general error occurred.") } }
Java
SafetyNet.getClient(this) .enableVerifyApps() .addOnCompleteListener(new OnCompleteListener<VerifyAppsUserResponse>() { @Override public void onComplete(Task<VerifyAppsUserResponse> task) { if (task.isSuccessful()) { VerifyAppsUserResponse result = task.getResult(); if (result.isVerifyAppsEnabled()) { Log.d("MY_APP_TAG", "The user gave consent " + "to enable the Verify Apps feature."); } else { Log.d("MY_APP_TAG", "The user didn't give consent " + "to enable the Verify Apps feature."); } } else { Log.e("MY_APP_TAG", "A general error occurred."); } } });
使用此方法时,您的应用可能会遇到一个或多个异常情况
- 如果应用验证功能已启用,则不会显示对话框,并且 API 的行为就像用户已同意启用此功能一样。
- 如果用户退出对话框,对话框将被销毁,并且 API 会假定用户未同意启用此功能。
- 如果您的应用与另一个应用同时调用此方法,则只会显示一个对话框,并且所有应用都会从该方法接收相同的返回值。
列出潜在有害的已安装应用
异步 listHarmfulApps()
方法可让您获取用户设备上安装的任何已知潜在有害应用的列表。此列表包含已识别的潜在有害应用的类别,以便您的应用可以采取适当的措施。
以下代码段展示了如何创建与此方法关联的回调
Kotlin
SafetyNet.getClient(this) .listHarmfulApps() .addOnCompleteListener { task -> Log.d(TAG, "Received listHarmfulApps() result") if (task.isSuccessful) { val result = task.result val scanTimeMs = result.lastScanTimeMs val appList = result.harmfulAppsList if (appList?.isNotEmpty() == true) { Log.e("MY_APP_TAG", "Potentially harmful apps are installed!") for (harmfulApp in appList) { Log.e("MY_APP_TAG", "Information about a harmful app:") Log.e("MY_APP_TAG", " APK: ${harmfulApp.apkPackageName}") Log.e("MY_APP_TAG", " SHA-256: ${harmfulApp.apkSha256}") // Categories are defined in VerifyAppsConstants. Log.e("MY_APP_TAG", " Category: ${harmfulApp.apkCategory}") } } else { Log.d("MY_APP_TAG", "There are no known potentially harmful apps installed.") } } else { Log.d( "MY_APP_TAG", "An error occurred. Call isVerifyAppsEnabled() to ensure that the user " + "has consented." ) } }
Java
SafetyNet.getClient(this) .listHarmfulApps() .addOnCompleteListener(new OnCompleteListener<HarmfulAppsResponse>() { @Override public void onComplete(Task<HarmfulAppsResponse> task) { Log.d(TAG, "Received listHarmfulApps() result"); if (task.isSuccessful()) { HarmfulAppsResponse result = task.getResult(); long scanTimeMs = result.getLastScanTimeMs(); List<HarmfulAppsData> appList = result.getHarmfulAppsList(); if (appList.isEmpty()) { Log.d("MY_APP_TAG", "There are no known " + "potentially harmful apps installed."); } else { Log.e("MY_APP_TAG", "Potentially harmful apps are installed!"); for (HarmfulAppsData harmfulApp : appList) { Log.e("MY_APP_TAG", "Information about a harmful app:"); Log.e("MY_APP_TAG", " APK: " + harmfulApp.apkPackageName); Log.e("MY_APP_TAG", " SHA-256: " + harmfulApp.apkSha256); // Categories are defined in VerifyAppsConstants. Log.e("MY_APP_TAG", " Category: " + harmfulApp.apkCategory); } } } else { Log.d("MY_APP_TAG", "An error occurred. " + "Call isVerifyAppsEnabled() to ensure " + "that the user has consented."); } } });