Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 2468dc6c authored by Yuri Lin's avatar Yuri Lin Committed by Automerger Merge Worker
Browse files

Merge "Add UiEvent logging for...

Merge "Add UiEvent logging for NOTIFICATION_REMOTE_INPUT_(OPEN|CLOSE|SEND|FAILURE)." into sc-dev am: 56daf16e

Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/14341502

Change-Id: I0e86c9335babc4701a879f23d0cddc33dbf0fc7f
parents c5be7a03 56daf16e
Loading
Loading
Loading
Loading
+3 −0
Original line number Diff line number Diff line
@@ -28,6 +28,7 @@ import android.view.IWindowManager;

import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.logging.MetricsLogger;
import com.android.internal.logging.UiEventLogger;
import com.android.internal.statusbar.IStatusBarService;
import com.android.internal.util.Preconditions;
import com.android.keyguard.KeyguardSecurityModel;
@@ -358,6 +359,7 @@ public class Dependency {
    @Inject Lazy<SystemStatusAnimationScheduler> mSystemStatusAnimationSchedulerLazy;
    @Inject Lazy<PrivacyDotViewController> mPrivacyDotViewControllerLazy;
    @Inject Lazy<EdgeBackGestureHandler> mEdgeBackGestureHandler;
    @Inject Lazy<UiEventLogger> mUiEventLogger;

    @Inject
    public Dependency() {
@@ -571,6 +573,7 @@ public class Dependency {
                mSystemStatusAnimationSchedulerLazy::get);
        mProviders.put(PrivacyDotViewController.class, mPrivacyDotViewControllerLazy::get);
        mProviders.put(EdgeBackGestureHandler.class, mEdgeBackGestureHandler::get);
        mProviders.put(UiEventLogger.class, mUiEventLogger::get);

        Dependency.setInstance(this);
    }
+49 −5
Original line number Diff line number Diff line
@@ -76,6 +76,8 @@ import androidx.annotation.NonNull;

import com.android.internal.graphics.ColorUtils;
import com.android.internal.logging.MetricsLogger;
import com.android.internal.logging.UiEvent;
import com.android.internal.logging.UiEventLogger;
import com.android.internal.logging.nano.MetricsProto;
import com.android.internal.statusbar.IStatusBarService;
import com.android.internal.util.ContrastColorUtil;
@@ -111,6 +113,7 @@ public class RemoteInputView extends LinearLayout implements View.OnClickListene
    private final SendButtonTextWatcher mTextWatcher;
    private final TextView.OnEditorActionListener mEditorActionHandler;
    private final NotificationRemoteInputManager mRemoteInputManager;
    private final UiEventLogger mUiEventLogger;
    private final List<OnFocusChangeListener> mEditTextFocusChangeListeners = new ArrayList<>();
    private final List<OnSendRemoteInputListener> mOnSendListeners = new ArrayList<>();
    private RemoteEditText mEditText;
@@ -145,12 +148,35 @@ public class RemoteInputView extends LinearLayout implements View.OnClickListene
    private ImageView mDelete;
    private ImageView mDeleteBg;

    /**
     * Enum for logged notification remote input UiEvents.
     */
    enum NotificationRemoteInputEvent implements UiEventLogger.UiEventEnum {
        @UiEvent(doc = "Notification remote input view was displayed")
        NOTIFICATION_REMOTE_INPUT_OPEN(795),
        @UiEvent(doc = "Notification remote input view was closed")
        NOTIFICATION_REMOTE_INPUT_CLOSE(796),
        @UiEvent(doc = "User sent data through the notification remote input view")
        NOTIFICATION_REMOTE_INPUT_SEND(797),
        @UiEvent(doc = "Failed attempt to send data through the notification remote input view")
        NOTIFICATION_REMOTE_INPUT_FAILURE(798);

        private final int mId;
        NotificationRemoteInputEvent(int id) {
            mId = id;
        }
        @Override public int getId() {
            return mId;
        }
    }

    public RemoteInputView(Context context, AttributeSet attrs) {
        super(context, attrs);
        mTextWatcher = new SendButtonTextWatcher();
        mEditorActionHandler = new EditorActionHandler();
        mRemoteInputQuickSettingsDisabler = Dependency.get(RemoteInputQuickSettingsDisabler.class);
        mRemoteInputManager = Dependency.get(NotificationRemoteInputManager.class);
        mUiEventLogger = Dependency.get(UiEventLogger.class);
        mStatusBarManagerService = IStatusBarService.Stub.asInterface(
                ServiceManager.getService(Context.STATUS_BAR_SERVICE));
        TypedArray ta = getContext().getTheme().obtainStyledAttributes(new int[]{
@@ -389,12 +415,20 @@ public class RemoteInputView extends LinearLayout implements View.OnClickListene

        MetricsLogger.action(mContext, MetricsProto.MetricsEvent.ACTION_REMOTE_INPUT_SEND,
                mEntry.getSbn().getPackageName());
        mUiEventLogger.logWithInstanceId(
                NotificationRemoteInputEvent.NOTIFICATION_REMOTE_INPUT_SEND,
                mEntry.getSbn().getUid(), mEntry.getSbn().getPackageName(),
                mEntry.getSbn().getInstanceId());
        try {
            mPendingIntent.send(mContext, 0, intent);
        } catch (PendingIntent.CanceledException e) {
            Log.i(TAG, "Unable to send remote input result", e);
            MetricsLogger.action(mContext, MetricsProto.MetricsEvent.ACTION_REMOTE_INPUT_FAIL,
                    mEntry.getSbn().getPackageName());
            mUiEventLogger.logWithInstanceId(
                    NotificationRemoteInputEvent.NOTIFICATION_REMOTE_INPUT_FAILURE,
                    mEntry.getSbn().getUid(), mEntry.getSbn().getPackageName(),
                    mEntry.getSbn().getInstanceId());
        }
        setAttachment(null);
    }
@@ -433,7 +467,7 @@ public class RemoteInputView extends LinearLayout implements View.OnClickListene
        return true;
    }

    private void onDefocus(boolean animate) {
    private void onDefocus(boolean animate, boolean logClose) {
        mController.removeRemoteInput(mEntry, mToken);
        mEntry.remoteInputText = mEditText.getText();

@@ -465,8 +499,14 @@ public class RemoteInputView extends LinearLayout implements View.OnClickListene

        mRemoteInputQuickSettingsDisabler.setRemoteInputActive(false);

        if (logClose) {
            MetricsLogger.action(mContext, MetricsProto.MetricsEvent.ACTION_REMOTE_INPUT_CLOSE,
                    mEntry.getSbn().getPackageName());
            mUiEventLogger.logWithInstanceId(
                    NotificationRemoteInputEvent.NOTIFICATION_REMOTE_INPUT_CLOSE,
                    mEntry.getSbn().getUid(), mEntry.getSbn().getPackageName(),
                    mEntry.getSbn().getInstanceId());
        }
    }

    @Override
@@ -544,6 +584,10 @@ public class RemoteInputView extends LinearLayout implements View.OnClickListene
    public void focus() {
        MetricsLogger.action(mContext, MetricsProto.MetricsEvent.ACTION_REMOTE_INPUT_OPEN,
                mEntry.getSbn().getPackageName());
        mUiEventLogger.logWithInstanceId(
                NotificationRemoteInputEvent.NOTIFICATION_REMOTE_INPUT_OPEN,
                mEntry.getSbn().getUid(), mEntry.getSbn().getPackageName(),
                mEntry.getSbn().getInstanceId());

        setVisibility(VISIBLE);
        if (mWrapper != null) {
@@ -584,7 +628,7 @@ public class RemoteInputView extends LinearLayout implements View.OnClickListene
        mProgressBar.setVisibility(INVISIBLE);
        mController.removeSpinning(mEntry.getKey(), mToken);
        updateSendButton();
        onDefocus(false /* animate */);
        onDefocus(false /* animate */, false /* logClose */);

        mResetting = false;
    }
@@ -878,7 +922,7 @@ public class RemoteInputView extends LinearLayout implements View.OnClickListene
            if (isFocusable() && isEnabled()) {
                setInnerFocusable(false);
                if (mRemoteInputView != null) {
                    mRemoteInputView.onDefocus(animate);
                    mRemoteInputView.onDefocus(animate, true /* logClose */);
                }
                mShowImeOnInputConnection = false;
            }
+33 −0
Original line number Diff line number Diff line
@@ -42,6 +42,8 @@ import android.widget.ImageButton;

import androidx.test.filters.SmallTest;

import com.android.internal.logging.UiEventLogger;
import com.android.internal.logging.testing.UiEventLoggerFake;
import com.android.systemui.Dependency;
import com.android.systemui.R;
import com.android.systemui.SysuiTestCase;
@@ -76,6 +78,7 @@ public class RemoteInputViewTest extends SysuiTestCase {
    @Mock private RemoteInputQuickSettingsDisabler mRemoteInputQuickSettingsDisabler;
    @Mock private LightBarController mLightBarController;
    private BlockingQueueIntentReceiver mReceiver;
    private final UiEventLoggerFake mUiEventLoggerFake = new UiEventLoggerFake();
    private RemoteInputView mView;

    @Before
@@ -87,6 +90,7 @@ public class RemoteInputViewTest extends SysuiTestCase {
                mRemoteInputQuickSettingsDisabler);
        mDependency.injectTestDependency(LightBarController.class,
                mLightBarController);
        mDependency.injectTestDependency(UiEventLogger.class, mUiEventLoggerFake);
        mDependency.injectMockDependency(NotificationRemoteInputManager.class);

        mReceiver = new BlockingQueueIntentReceiver();
@@ -205,4 +209,33 @@ public class RemoteInputViewTest extends SysuiTestCase {
        view.setVisibility(View.INVISIBLE);
        view.setVisibility(View.VISIBLE);
    }

    @Test
    public void testUiEventLogging_openAndSend() throws Exception {
        NotificationTestHelper helper = new NotificationTestHelper(
                mContext,
                mDependency,
                TestableLooper.get(this));
        ExpandableNotificationRow row = helper.createRow();
        RemoteInputView view = RemoteInputView.inflate(mContext, null, row.getEntry(), mController);

        setTestPendingIntent(view);

        // Open view, send a reply
        view.focus();
        EditText editText = view.findViewById(R.id.remote_input_text);
        editText.setText(TEST_REPLY);
        ImageButton sendButton = view.findViewById(R.id.remote_input_send);
        sendButton.performClick();

        mReceiver.waitForIntent();

        assertEquals(2, mUiEventLoggerFake.numLogs());
        assertEquals(
                RemoteInputView.NotificationRemoteInputEvent.NOTIFICATION_REMOTE_INPUT_OPEN.getId(),
                mUiEventLoggerFake.eventId(0));
        assertEquals(
                RemoteInputView.NotificationRemoteInputEvent.NOTIFICATION_REMOTE_INPUT_SEND.getId(),
                mUiEventLoggerFake.eventId(1));
    }
}