Refactored InteractionSessionId.
Rather than use a local and global id, just use a local, unique id.
Such change not only simplifies the code, but makes it consistent with
TextClassificationSessionId.
Test: mmm -j packages/experimental/FillService && \
adb install -r ${OUT}/data/app/FillService/FillService.apk && \
adb shell settings put secure intel_service foo.bar.fill/.AiaiService
Bug: 111276913
Change-Id: I0e610f825aab1d2b32bbafa1bd3d3c7897d889d6
This commit is contained in:
@@ -16,43 +16,85 @@
|
||||
|
||||
package android.service.intelligence;
|
||||
|
||||
import android.annotation.NonNull;
|
||||
import android.annotation.SystemApi;
|
||||
import android.os.Parcel;
|
||||
import android.os.Parcelable;
|
||||
|
||||
import java.io.PrintWriter;
|
||||
import java.util.UUID;
|
||||
|
||||
// TODO(b/111276913): add javadocs / implement equals/hashcode/string
|
||||
/** @hide */
|
||||
@SystemApi
|
||||
public final class InteractionSessionId implements Parcelable {
|
||||
|
||||
private final int mGlobalId;
|
||||
private final @NonNull String mValue;
|
||||
|
||||
// TODO(b/111276913): remove if not needed
|
||||
private final int mLocalId;
|
||||
|
||||
/** @hide */
|
||||
public InteractionSessionId(int globalId, int localId) {
|
||||
mGlobalId = globalId;
|
||||
mLocalId = localId;
|
||||
/**
|
||||
* Creates a new instance.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
public InteractionSessionId() {
|
||||
this(UUID.randomUUID().toString());
|
||||
}
|
||||
|
||||
/** @hide */
|
||||
public int getGlobalId() {
|
||||
return mGlobalId;
|
||||
/**
|
||||
* Creates a new instance.
|
||||
*
|
||||
* @param value The internal value.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
public InteractionSessionId(@NonNull String value) {
|
||||
mValue = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* @hide
|
||||
*/
|
||||
public String getValue() {
|
||||
return mValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + ((mValue == null) ? 0 : mValue.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj) return true;
|
||||
if (obj == null) return false;
|
||||
if (getClass() != obj.getClass()) return false;
|
||||
final InteractionSessionId other = (InteractionSessionId) obj;
|
||||
if (mValue == null) {
|
||||
if (other.mValue != null) return false;
|
||||
} else if (!mValue.equals(other.mValue)) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*
|
||||
* <p><b>NOTE: </b>this method is only useful for debugging purposes and is not guaranteed to
|
||||
* be stable, hence it should not be used to identify the session.
|
||||
*/
|
||||
@Override
|
||||
public String toString() {
|
||||
return mValue;
|
||||
}
|
||||
|
||||
/** @hide */
|
||||
// TODO(b/111276913): dump to proto as well
|
||||
public void dump(PrintWriter pw) {
|
||||
pw.print("globalId="); pw.print(mGlobalId);
|
||||
pw.print("localId="); pw.print(mLocalId);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "SessionId[globalId=" + mGlobalId + ", localId=" + mLocalId + "]";
|
||||
pw.print(mValue);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -62,8 +104,7 @@ public final class InteractionSessionId implements Parcelable {
|
||||
|
||||
@Override
|
||||
public void writeToParcel(Parcel parcel, int flags) {
|
||||
parcel.writeInt(mGlobalId);
|
||||
parcel.writeInt(mLocalId);
|
||||
parcel.writeString(mValue);
|
||||
}
|
||||
|
||||
public static final Parcelable.Creator<InteractionSessionId> CREATOR =
|
||||
@@ -71,9 +112,7 @@ public final class InteractionSessionId implements Parcelable {
|
||||
|
||||
@Override
|
||||
public InteractionSessionId createFromParcel(Parcel parcel) {
|
||||
final int globalId = parcel.readInt();
|
||||
final int localId = parcel.readInt();
|
||||
return new InteractionSessionId(globalId, localId);
|
||||
return new InteractionSessionId(parcel.readString());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -17,9 +17,8 @@
|
||||
package android.view.intelligence;
|
||||
|
||||
import android.content.ComponentName;
|
||||
|
||||
import android.os.IBinder;
|
||||
|
||||
import android.service.intelligence.InteractionSessionId;
|
||||
import android.view.intelligence.ContentCaptureEvent;
|
||||
|
||||
import com.android.internal.os.IResultReceiver;
|
||||
@@ -34,19 +33,16 @@ oneway interface IIntelligenceManager {
|
||||
* Starts a session, sending the "remote" sessionId to the receiver.
|
||||
*/
|
||||
void startSession(int userId, IBinder activityToken, in ComponentName componentName,
|
||||
int localSessionId, int flags, in IResultReceiver result);
|
||||
in InteractionSessionId sessionId, int flags, in IResultReceiver result);
|
||||
|
||||
/**
|
||||
* Finishes a session.
|
||||
*/
|
||||
// TODO(b/111276913): pass just (global) session id
|
||||
void finishSession(int userId, IBinder activityToken, in ComponentName componentName,
|
||||
int localSessionId, int globalSessionId);
|
||||
void finishSession(int userId, in InteractionSessionId sessionId);
|
||||
|
||||
/**
|
||||
* Sends a batch of events
|
||||
*/
|
||||
// TODO(b/111276913): pass just (global) session id
|
||||
void sendEvents(int userId, IBinder activityToken, in ComponentName componentName,
|
||||
int localSessionId, int globalSessionId, in List<ContentCaptureEvent> events);
|
||||
void sendEvents(int userId, in InteractionSessionId sessionId,
|
||||
in List<ContentCaptureEvent> events);
|
||||
}
|
||||
|
||||
@@ -25,6 +25,7 @@ import android.os.Bundle;
|
||||
import android.os.IBinder;
|
||||
import android.os.RemoteException;
|
||||
import android.os.SystemClock;
|
||||
import android.service.intelligence.InteractionSessionId;
|
||||
import android.util.Log;
|
||||
import android.view.intelligence.ContentCaptureEvent.EventType;
|
||||
|
||||
@@ -55,9 +56,6 @@ public final class IntelligenceManager {
|
||||
public static final int FLAG_USER_INPUT = 0x1;
|
||||
|
||||
|
||||
/** @hide */
|
||||
public static final int NO_SESSION = 0;
|
||||
|
||||
/**
|
||||
* Initial state, when there is no session.
|
||||
*
|
||||
@@ -66,11 +64,11 @@ public final class IntelligenceManager {
|
||||
public static final int STATE_UNKNOWN = 0;
|
||||
|
||||
/**
|
||||
* Service's startSession() was called, but remote session id was not returned yet.
|
||||
* Service's startSession() was called, but server didn't confirm it was created yet.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
public static final int STATE_WAITING_FOR_SESSION_ID = 1;
|
||||
public static final int STATE_WAITING_FOR_SERVER = 1;
|
||||
|
||||
/**
|
||||
* Session is active.
|
||||
@@ -79,8 +77,6 @@ public final class IntelligenceManager {
|
||||
*/
|
||||
public static final int STATE_ACTIVE = 2;
|
||||
|
||||
private static int sNextSessionId;
|
||||
|
||||
private final Context mContext;
|
||||
|
||||
@Nullable
|
||||
@@ -88,14 +84,9 @@ public final class IntelligenceManager {
|
||||
|
||||
private final Object mLock = new Object();
|
||||
|
||||
// TODO(b/111276913): localSessionId might be an overkill, perhaps just the global id is enough.
|
||||
// Let's keep both for now, and revisit once we decide whether the session id will be persisted
|
||||
// when the activity's process is killed
|
||||
@Nullable
|
||||
@GuardedBy("mLock")
|
||||
private int mLocalSessionId = NO_SESSION;
|
||||
|
||||
@GuardedBy("mLock")
|
||||
private int mRemoteSessionId = NO_SESSION;
|
||||
private InteractionSessionId mId;
|
||||
|
||||
@GuardedBy("mLock")
|
||||
private int mState = STATE_UNKNOWN;
|
||||
@@ -124,27 +115,25 @@ public final class IntelligenceManager {
|
||||
+ getStateAsStringLocked());
|
||||
return;
|
||||
}
|
||||
mState = STATE_WAITING_FOR_SESSION_ID;
|
||||
mLocalSessionId = ++sNextSessionId;
|
||||
mRemoteSessionId = NO_SESSION;
|
||||
mState = STATE_WAITING_FOR_SERVER;
|
||||
mId = new InteractionSessionId();
|
||||
mApplicationToken = token;
|
||||
mComponentName = componentName;
|
||||
|
||||
if (VERBOSE) {
|
||||
Log.v(TAG, "onActivityStarted(): token=" + token + ", act=" + componentName
|
||||
+ ", localSessionId=" + mLocalSessionId);
|
||||
+ ", id=" + mId);
|
||||
}
|
||||
final int flags = 0; // TODO(b/111276913): get proper flags
|
||||
|
||||
try {
|
||||
mService.startSession(mContext.getUserId(), mApplicationToken, componentName,
|
||||
mLocalSessionId, flags, new IResultReceiver.Stub() {
|
||||
mId, flags, new IResultReceiver.Stub() {
|
||||
@Override
|
||||
public void send(int resultCode, Bundle resultData)
|
||||
throws RemoteException {
|
||||
synchronized (mLock) {
|
||||
if (resultCode > 0) {
|
||||
mRemoteSessionId = resultCode;
|
||||
mState = STATE_ACTIVE;
|
||||
} else {
|
||||
// TODO(b/111276913): handle other cases like disabled by
|
||||
@@ -153,7 +142,7 @@ public final class IntelligenceManager {
|
||||
}
|
||||
if (VERBOSE) {
|
||||
Log.v(TAG, "onActivityStarted() result: code=" + resultCode
|
||||
+ ", remoteSession=" + mRemoteSessionId
|
||||
+ ", id=" + mId
|
||||
+ ", state=" + getStateAsStringLocked());
|
||||
}
|
||||
}
|
||||
@@ -189,8 +178,7 @@ public final class IntelligenceManager {
|
||||
}
|
||||
|
||||
try {
|
||||
mService.sendEvents(mContext.getUserId(), mApplicationToken, mComponentName,
|
||||
mLocalSessionId, mRemoteSessionId, events);
|
||||
mService.sendEvents(mContext.getUserId(), mId, events);
|
||||
} catch (RemoteException e) {
|
||||
throw e.rethrowFromSystemServer();
|
||||
}
|
||||
@@ -207,15 +195,13 @@ public final class IntelligenceManager {
|
||||
|
||||
if (VERBOSE) {
|
||||
Log.v(TAG, "onActivityDestroyed(): state=" + getStateAsStringLocked()
|
||||
+ ", localSessionId=" + mLocalSessionId
|
||||
+ ", mRemoteSessionId=" + mRemoteSessionId);
|
||||
+ ", mId=" + mId);
|
||||
}
|
||||
|
||||
try {
|
||||
mService.finishSession(mContext.getUserId(), mApplicationToken, mComponentName,
|
||||
mLocalSessionId, mRemoteSessionId);
|
||||
mService.finishSession(mContext.getUserId(), mId);
|
||||
mState = STATE_UNKNOWN;
|
||||
mLocalSessionId = mRemoteSessionId = NO_SESSION;
|
||||
mId = null;
|
||||
mApplicationToken = null;
|
||||
mComponentName = null;
|
||||
} catch (RemoteException e) {
|
||||
@@ -334,12 +320,11 @@ public final class IntelligenceManager {
|
||||
pw.print(prefix2); pw.print("mService: "); pw.println(mService);
|
||||
pw.print(prefix2); pw.print("user: "); pw.println(mContext.getUserId());
|
||||
pw.print(prefix2); pw.print("enabled: "); pw.println(isContentCaptureEnabled());
|
||||
pw.print(prefix2); pw.print("mLocalSessionId: "); pw.println(mLocalSessionId);
|
||||
pw.print(prefix2); pw.print("mRemoteSessionId: "); pw.println(mRemoteSessionId);
|
||||
pw.print(prefix2); pw.print("mState: "); pw.print(mState); pw.print(" (");
|
||||
pw.print(prefix2); pw.print("id: "); pw.println(mId);
|
||||
pw.print(prefix2); pw.print("state: "); pw.print(mState); pw.print(" (");
|
||||
pw.print(getStateAsStringLocked()); pw.println(")");
|
||||
pw.print(prefix2); pw.print("mAppToken: "); pw.println(mApplicationToken);
|
||||
pw.print(prefix2); pw.print("mComponentName: "); pw.println(mComponentName);
|
||||
pw.print(prefix2); pw.print("appToken: "); pw.println(mApplicationToken);
|
||||
pw.print(prefix2); pw.print("componentName: "); pw.println(mComponentName);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -353,8 +338,8 @@ public final class IntelligenceManager {
|
||||
switch (state) {
|
||||
case STATE_UNKNOWN:
|
||||
return "UNKNOWN";
|
||||
case STATE_WAITING_FOR_SESSION_ID:
|
||||
return "WAITING_FOR_SESSION_ID";
|
||||
case STATE_WAITING_FOR_SERVER:
|
||||
return "WAITING_FOR_SERVER";
|
||||
case STATE_ACTIVE:
|
||||
return "ACTIVE";
|
||||
default:
|
||||
|
||||
Reference in New Issue
Block a user