summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Tim Yu <yunicorn@google.com> 2024-11-15 00:33:21 +0000
committer Tim Yu <yunicorn@google.com> 2024-11-27 18:27:25 +0000
commit7726696e11b133ad7677a8d860468130f27f3b9f (patch)
tree36a8763cf5b7f8249a4d83967088da8ca1f93cfb
parent27764c0d29f09e1dd757f72e7a3233dace3cec1e (diff)
[Autofill] Add new API for getting FillEventHistory
Introduce a new callback in AutofillService that is called when the session is finished. Bug: 370059095 Test: android.autofillservice.cts.commontests.FillEventHistoryCommonTestCase.test_onSessionDestroyed Flag: android.service.autofill.autofill_session_destroyed Change-Id: I2fcb7d7a1a5c55e4afec73acd37a4bf148f3040b
-rw-r--r--core/api/current.txt3
-rw-r--r--core/java/android/service/autofill/AutofillService.java47
-rw-r--r--core/java/android/service/autofill/IAutoFillService.aidl3
-rw-r--r--services/autofill/features.aconfig7
-rw-r--r--services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java18
-rw-r--r--services/autofill/java/com/android/server/autofill/RemoteFillService.java9
6 files changed, 76 insertions, 11 deletions
diff --git a/core/api/current.txt b/core/api/current.txt
index 38a0144cf6d5..d797336af549 100644
--- a/core/api/current.txt
+++ b/core/api/current.txt
@@ -40889,13 +40889,14 @@ package android.service.autofill {
public abstract class AutofillService extends android.app.Service {
ctor public AutofillService();
- method @Nullable public final android.service.autofill.FillEventHistory getFillEventHistory();
+ method @Deprecated @FlaggedApi("android.service.autofill.autofill_session_destroyed") @Nullable public final android.service.autofill.FillEventHistory getFillEventHistory();
method public final android.os.IBinder onBind(android.content.Intent);
method public void onConnected();
method public void onDisconnected();
method public abstract void onFillRequest(@NonNull android.service.autofill.FillRequest, @NonNull android.os.CancellationSignal, @NonNull android.service.autofill.FillCallback);
method public abstract void onSaveRequest(@NonNull android.service.autofill.SaveRequest, @NonNull android.service.autofill.SaveCallback);
method public void onSavedDatasetsInfoRequest(@NonNull android.service.autofill.SavedDatasetsInfoCallback);
+ method @FlaggedApi("android.service.autofill.autofill_session_destroyed") public void onSessionDestroyed(@Nullable android.service.autofill.FillEventHistory);
field public static final String EXTRA_FILL_RESPONSE = "android.service.autofill.extra.FILL_RESPONSE";
field public static final String SERVICE_INTERFACE = "android.service.autofill.AutofillService";
field public static final String SERVICE_META_DATA = "android.autofill";
diff --git a/core/java/android/service/autofill/AutofillService.java b/core/java/android/service/autofill/AutofillService.java
index 269839b61bef..2d922b4c09ee 100644
--- a/core/java/android/service/autofill/AutofillService.java
+++ b/core/java/android/service/autofill/AutofillService.java
@@ -15,9 +15,12 @@
*/
package android.service.autofill;
+import static android.service.autofill.Flags.FLAG_AUTOFILL_SESSION_DESTROYED;
+
import static com.android.internal.util.function.pooled.PooledLambda.obtainMessage;
import android.annotation.CallSuper;
+import android.annotation.FlaggedApi;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.annotation.SdkConstant;
@@ -669,6 +672,14 @@ public abstract class AutofillService extends Service {
AutofillService.this,
new SavedDatasetsInfoCallbackImpl(receiver, SavedDatasetsInfo.TYPE_PASSWORDS)));
}
+
+ @Override
+ public void onSessionDestroyed(@Nullable FillEventHistory history) {
+ mHandler.sendMessage(obtainMessage(
+ AutofillService::onSessionDestroyed,
+ AutofillService.this,
+ history));
+ }
};
private Handler mHandler;
@@ -783,26 +794,42 @@ public abstract class AutofillService extends Service {
}
/**
- * Gets the events that happened after the last
- * {@link AutofillService#onFillRequest(FillRequest, android.os.CancellationSignal, FillCallback)}
+ * Called when an Autofill context has ended and the Autofill session is finished. This will be
+ * called as the last step of the Autofill lifecycle described in {@link AutofillManager}.
+ *
+ * <p>This will also contain the finished Session's FillEventHistory, so providers do not need
+ * to explicitly call {@link #getFillEventHistory()}
+ *
+ * <p>This will usually happens whenever {@link AutofillManager#commit()} or {@link
+ * AutofillManager#cancel()} is called.
+ */
+ @FlaggedApi(FLAG_AUTOFILL_SESSION_DESTROYED)
+ public void onSessionDestroyed(@Nullable FillEventHistory history) {}
+
+ /**
+ * Gets the events that happened after the last {@link
+ * AutofillService#onFillRequest(FillRequest, android.os.CancellationSignal, FillCallback)}
* call.
*
* <p>This method is typically used to keep track of previous user actions to optimize further
* requests. For example, the service might return email addresses in alphabetical order by
* default, but change that order based on the address the user picked on previous requests.
*
- * <p>The history is not persisted over reboots, and it's cleared every time the service
- * replies to a {@link #onFillRequest(FillRequest, CancellationSignal, FillCallback)} by calling
- * {@link FillCallback#onSuccess(FillResponse)} or {@link FillCallback#onFailure(CharSequence)}
- * (if the service doesn't call any of these methods, the history will clear out after some
- * pre-defined time). Hence, the service should call {@link #getFillEventHistory()} before
- * finishing the {@link FillCallback}.
+ * <p>The history is not persisted over reboots, and it's cleared every time the service replies
+ * to a {@link #onFillRequest(FillRequest, CancellationSignal, FillCallback)} by calling {@link
+ * FillCallback#onSuccess(FillResponse)} or {@link FillCallback#onFailure(CharSequence)} (if the
+ * service doesn't call any of these methods, the history will clear out after some pre-defined
+ * time). Hence, the service should call {@link #getFillEventHistory()} before finishing the
+ * {@link FillCallback}.
*
* @return The history or {@code null} if there are no events.
- *
* @throws RuntimeException if the event history could not be retrieved.
+ * @deprecated Use {@link #onSessionDestroyed(FillEventHistory) instead}
*/
- @Nullable public final FillEventHistory getFillEventHistory() {
+ @FlaggedApi(FLAG_AUTOFILL_SESSION_DESTROYED)
+ @Deprecated
+ @Nullable
+ public final FillEventHistory getFillEventHistory() {
final AutofillManager afm = getSystemService(AutofillManager.class);
if (afm == null) {
diff --git a/core/java/android/service/autofill/IAutoFillService.aidl b/core/java/android/service/autofill/IAutoFillService.aidl
index 3b64b8a0ec5e..71b75e7789c2 100644
--- a/core/java/android/service/autofill/IAutoFillService.aidl
+++ b/core/java/android/service/autofill/IAutoFillService.aidl
@@ -25,6 +25,8 @@ import android.service.autofill.ISaveCallback;
import android.service.autofill.SaveRequest;
import com.android.internal.os.IResultReceiver;
+parcelable FillEventHistory;
+
/**
* Interface from the system to an auto fill service.
*
@@ -38,4 +40,5 @@ oneway interface IAutoFillService {
void onSaveRequest(in SaveRequest request, in ISaveCallback callback);
void onSavedPasswordCountRequest(in IResultReceiver receiver);
void onConvertCredentialRequest(in ConvertCredentialRequest convertCredentialRequest, in IConvertCredentialCallback convertCredentialCallback);
+ void onSessionDestroyed(in FillEventHistory history);
}
diff --git a/services/autofill/features.aconfig b/services/autofill/features.aconfig
index 444844121190..80ccb0365d80 100644
--- a/services/autofill/features.aconfig
+++ b/services/autofill/features.aconfig
@@ -2,6 +2,13 @@ package: "android.service.autofill"
container: "system"
flag {
+ name: "autofill_session_destroyed"
+ namespace: "autofill"
+ description: "Guards against new metrics definitions introduced in W"
+ bug: "342676602"
+}
+
+flag {
name: "autofill_w_metrics"
namespace: "autofill"
description: "Guards against new metrics definitions introduced in W"
diff --git a/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java b/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java
index cd4ace2e3835..5cf96bfb2b8b 100644
--- a/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java
+++ b/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java
@@ -61,6 +61,7 @@ import android.service.autofill.FillEventHistory;
import android.service.autofill.FillEventHistory.Event;
import android.service.autofill.FillEventHistory.Event.NoSaveReason;
import android.service.autofill.FillResponse;
+import android.service.autofill.Flags;
import android.service.autofill.IAutoFillService;
import android.service.autofill.InlineSuggestionRenderService;
import android.service.autofill.SaveInfo;
@@ -100,6 +101,7 @@ import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.Random;
+
/**
* Bridge between the {@code system_server}'s {@link AutofillManagerService} and the
* app's {@link IAutoFillService} implementation.
@@ -748,6 +750,22 @@ final class AutofillManagerServiceImpl
@GuardedBy("mLock")
void removeSessionLocked(int sessionId) {
mSessions.remove(sessionId);
+ if (Flags.autofillSessionDestroyed()) {
+ if (sVerbose) {
+ Slog.v(
+ TAG,
+ "removeSessionLocked(): removed " + sessionId);
+ }
+ RemoteFillService remoteService =
+ new RemoteFillService(
+ getContext(),
+ mInfo.getServiceInfo().getComponentName(),
+ mUserId,
+ /* callbacks= */ null,
+ mMaster.isInstantServiceAllowed(),
+ /* credentialAutofillService= */ null);
+ remoteService.onSessionDestroyed(null);
+ }
}
/**
diff --git a/services/autofill/java/com/android/server/autofill/RemoteFillService.java b/services/autofill/java/com/android/server/autofill/RemoteFillService.java
index 07f5dcc3cb0a..f1e888400d32 100644
--- a/services/autofill/java/com/android/server/autofill/RemoteFillService.java
+++ b/services/autofill/java/com/android/server/autofill/RemoteFillService.java
@@ -34,6 +34,7 @@ import android.os.RemoteException;
import android.service.autofill.AutofillService;
import android.service.autofill.ConvertCredentialRequest;
import android.service.autofill.ConvertCredentialResponse;
+import android.service.autofill.FillEventHistory;
import android.service.autofill.FillRequest;
import android.service.autofill.FillResponse;
import android.service.autofill.IAutoFillService;
@@ -497,6 +498,14 @@ final class RemoteFillService extends ServiceConnector.Impl<IAutoFillService> {
}));
}
+ public void onSessionDestroyed(@Nullable FillEventHistory history) {
+ boolean success = run(service -> {
+ service.onSessionDestroyed(history);
+ });
+
+ if (sVerbose) Slog.v(TAG, "called onSessionDestroyed(): " + success);
+ }
+
void onSavedPasswordCountRequest(IResultReceiver receiver) {
run(service -> service.onSavedPasswordCountRequest(receiver));
}