Android Oreo:我应该怎么做才能将我的应用程序发布为自动填充服务提供商? [英] Android Oreo: what should I do to publish my app as an Autofill service provider?

查看:21
本文介绍了Android Oreo:我应该怎么做才能将我的应用程序发布为自动填充服务提供商?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我是密码管理器应用的独立开发者.我应该做什么,或者我应该实现什么(接口/API/服务),以使我的应用成为自动填充服务提供者(在 Android Oreo API >= 26 的设备中)?

I'm an independent developer of a password manager app. What should I do, or what should I implement (interface/API/Service), to make my app an Autofill service provider (in a device with Android Oreo API >= 26)?

我已经阅读了各种相关文档,但我不明白如何做到这一点.我错过了什么吗?

I have read all kinds of related documentation, but I can't understand how to do this. Am I missing something?

目前我看到只有知名密码管理器支持此功能:

At the moment I see that only well-known password managers support this feature:

欢迎任何提示.

推荐答案

像往常一样,谷歌自己的 示例存储库为学习自动填充框架的 API 提供了一个很好的起点,并且涵盖的材料比我能回答的要多得多.以下是关键概念的概述.根据文档中的描述,我们想要创建一个自动填充service 将处理来自其他应用程序(客户端)的请求以存储和检索自动填充字段数据.

As usual, Google's own examples repository provides a good starting point for learning the Autofill Framework's API, and covers much more material than I can fit into an answer. Here's an overview of the key concepts. From the description in the documentation, we want to create an Autofill service that will handle requests from other apps (the clients) to store and retrieve Autofill field data.

首先,我们需要创建一个服务提供者类来履行这个契约.我们可以扩展基础 AutofillService:

First, we need to create a service provider class that fulfills this contract. We can extend the base AutofillService class:

import android.service.autofill.AutofillService;
...
public class MyAutofillService extends AutofillService {
    ...
    @Override
    public void onFillRequest(FillRequest request, CancellationSignal cancellationSignal,
        FillCallback callback) { ... }

    @Override
    public void onSaveRequest(SaveRequest request, SaveCallback callback) { ... }
}

服务的onFillRequest()onSaveRequest() 方法是对我们的理解最重要.Android 系统调用 onFillRequest() 来确定我们的服务是否可以为特定活动自动填充字段,并为该方法提供 FillRequest 包含我们的服务将检查可填充字段的上下文和视图信息.当服务完成时,它使用适当的自动填充数据调用提供的 callback.

The service's onFillRequest() and onSaveRequest() methods are the most significant for our understanding. The Android system calls onFillRequest() to determine if our service can autofill fields for a particular activity, and gives the method a FillRequest which contains the context and view information that our service will examine for fillable fields. When the service finishes, it invokes the provided callback with the appropriate autofill data.

这里是戏剧性地简化了为 FillRequest 提供自动填充建议所需的基本步骤的概述:

Here's a dramatically simplified overview of the basic steps needed to provide autofill suggestions for a FillRequest:

@Override
public void onFillRequest(FillRequest request, CancellationSignal signal, FillCallback callback) {
    List<FillContext> contexts = request.getFillContexts();
    AssistStructure structure = contexts.get(contexts.size() - 1);
    WindowNode windowNode = structure.getWindowNodeAt(0);
    ViewNode viewNode = windowNode.getRootViewNode(); // pretend this is an EditText

    String suggestionText = "This will appear in the autofill list for 'viewNode'.";
    RemoteViews suggestion = new RemoteViews(getPackageName(), R.layout.autofill_suggestion);
    suggestion.setTextViewText(R.id.autofill_suggestion, suggestionText);

    Dataset suggestionDataset = new Dataset.Builder(suggestion) 
        .setValue(viewNode.getAutoFillId(), AutofillValue.forText(suggestionText))
        .build();

    FillResponse response = new FillResponse.Builder() 
        .addDataset(suggestionDataset)
        .build();

    callback.onSuccess(response);
}

正如我们所见,Autofill API 需要大量代码,以便为我们事先知道的 View 提供单个静态自动填充建议——该示例假定 viewNode 是我们要为其提供自动填充建议的文本输入字段.实际上,这个例子太简单了,但我想清楚地展示最小的实现.对于每个 WindowNode,我们需要遍历根 ViewNode 及其每个子项,以查找我们的服务希望为其提供自动填充数据的每个输入字段,然后创建一个 RemoteViewsDataset 包含我们将添加到 FillResponse 使用 FillResponse.Builder.addDataset().此示例不显示用于为 RemoteViews 创建建议显示项的 R.layout.autofill_suggestion TextView 的纯 XML 布局.

As we can see, the Autofill API requires a lot of code just to provide a single, static autofill suggestion for a View that we already know in advance—the example assumes that viewNode is a text input field that we want to provide autofill suggestions for. In reality, this example is too simple, but I wanted to clearly show the minimum implementation. For each WindowNode, we need to walk through the view tree of the root ViewNode and each of its children to find each of the input fields that our service wishes to provide autofill data for, and then create a RemoteViews and Dataset that contains the autofill suggestion for each field that we'll add to the FillResponse using FillResponse.Builder.addDataset(). This example doesn't show the plain XML layout for the R.layout.autofill_suggestion TextView used to create the suggestion display item for a RemoteViews.

同样,当用户想要将数据保存在活动字段中以供将来完成请求时,Android 会调用 onSaveRequest() 并注入 SaveRequest 我们的服务用来查找要记住的自动填充数据.

Similarly, Android calls onSaveRequest() when a user wants to save the data in an activity's fields for future completion requests and injects a SaveRequest that our service uses to find autofill data to remember.

这些方法的具体实现将取决于我们的应用提供的自动填充数据的类型.自动填充服务必须认真检查每个字段的特征并仔细选择一组适当的自动填充建议,以避免将用户数据泄露给恶意客户端活动(请参阅评论).特别是对于密码管理器,我们需要特别注意正确验证服务用户的身份,并在请求和保存自动填充数据时提供一组安全的建议.

The specific implementation of each of these methods will depend on the type of Autofill data that our app provides. Autofill services must conscientiously examine the characteristics of each field and carefully select a set of appropriate autofill suggestions to avoid leaking the user's data to a malicious client activity (see comments). For a password manager in particular, we need to pay special attention to properly authenticating a user of the service and providing a safe set of suggestions when requesting and saving autofill data.

我们现在可以在注册服务><application> 项目的 AndroidManifest.xml 块:

We can now register the service in the <application> block of the project's AndroidManifest.xml:

<service
    android:name=".MyAutofillService"
    android:label="Multi-Dataset Autofill Service"
    android:permission="android.permission.BIND_AUTOFILL_SERVICE">
    <meta-data
        android:name="android.autofill"
        android:resource="@xml/multidataset_service" />

    <intent-filter>
        <action android:name="android.service.autofill.AutofillService" />
    </intent-filter>
</service>

如图所示,这将我们的自动填充服务绑定为一个可用选项,该选项出现在问题中显示的自动填充服务列表中.android:name 属性必须与我们的 AutofillService 类的名称匹配,并且我们的应用必须声明 BIND_AUTOFILL_SERVICE 权限.将 android:label 的值更改为适合服务的名称(例如,使用密码管理器自动填充").或者,将其设置在字符串资源中.另请注意,我们应该提供一个设置"活动,用于配置我们在 <meta-data> 中为 android.autofill 指定的服务:

As shown, this binds our Autofill service as an available option that appears in the Autofill services list show in the question. The android:name attribute must match the name of our AutofillService class, and our app must declare the BIND_AUTOFILL_SERVICE permission. Change the value of android:label to a suitable name for the service (for example, "Autofill with Password Manager"). Alternatively, set this in a string resource. Note also that we should provide a "settings" activity used to configure our service which we specify in the <meta‑data> for android.autofill:

<autofill-service android:settingsActivity="foo.bar.SettingsActivity" />

然后,用户可以从他们的设备设置中启用我们的自动填充服务.我们可以广播 ACTION_REQUEST_SET_AUTOFILL_SERVICE Intent在设置或首次启动期间帮助用户找到此屏幕.

Then, the user can enable our Autofill service from their device Settings. We can broadcast the ACTION_REQUEST_SET_AUTOFILL_SERVICE intent during setup or first launch to assist the user in finding this screen.

这篇关于Android Oreo:我应该怎么做才能将我的应用程序发布为自动填充服务提供商?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆