port notificaiton logs to Tron v2

remove uninteresting people lookup timer logs

Bug: 34705522
Test: mmma -j20 platform_testing/tests/functional/notificationtests && adb install -r -g $OUT/data/app/NotificationFunctionalTests/NotificationFunctionalTests.apk && adb shell am instrument -w -e iterations 1 -e class com.android.notification.functional.NotificationInteractionTests com.android.notification.functional/android.support.test.runner.AndroidJUnitRunner
Change-Id: I27c17deab4372c93b41dd2821f08c8d10b73cfbf
This commit is contained in:
Chris Wren
2017-01-26 13:15:06 -05:00
parent 58047b9451
commit 9eb5e102dc
31 changed files with 58 additions and 2439 deletions

View File

@@ -1,54 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
/**
* Parse the Android counter event logs.
* @hide
*/
public class CounterParser extends TagParser {
private static final String TAG = "CounterParser";
private static final int EVENTLOG_TAG = 524290;
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
if (operands.length >= 2) {
try {
String name = ((String) operands[0]);
int value = (Integer) operands[1];
logCount(logger, name, value);
} catch (ClassCastException e) {
if (debug) {
Log.d(TAG, "unexpected operand type", e);
}
}
} else if (debug) {
Log.d(TAG, "wrong number of operands: " + operands.length);
}
}
protected void logCount(TronLogger logger, String name, int value) {
logger.incrementBy(TronCounters.TRON_AOSP_PREFIX + name, value);
}
}

View File

@@ -45,19 +45,6 @@ public class EventLogCollector {
private EventLogCollector() {
mTagParsers = new ArrayMap<>();
addParser(new SysuiViewVisibilityParser());
addParser(new SysuiActionParser());
addParser(new SysuiQueryParser());
addParser(new NotificationPanelRevealedParser());
addParser(new NotificationPanelHiddenParser());
addParser(new NotificationClickedParser());
addParser(new NotificationActionClickedParser());
addParser(new NotificationCanceledParser());
addParser(new NotificationVisibilityParser());
addParser(new NotificationAlertParser());
addParser(new NotificationExpansionParser());
addParser(new CounterParser());
addParser(new HistogramParser());
addParser(new LockscreenGestureParser());
addParser(new StatusBarStateParser());
addParser(new PowerScreenStateParser());

View File

@@ -1,35 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
/**
* Parse the Android histogram event logs.
* @hide
*/
public class HistogramParser extends CounterParser {
private static final String TAG = "HistogramParser";
private static final int EVENTLOG_TAG = 524291;
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
protected void logCount(TronLogger logger, String name, int value) {
logger.incrementIntHistogram("tron_varz_" + name, value);
}
}

View File

@@ -1,72 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the Android notification action button interaction event logs.
* @hide
*/
public class NotificationActionClickedParser extends TagParser {
private static final String TAG = "NotificationAction";
private static final int EVENTLOG_TAG = 27521;
private final NotificationKey mKey;
public NotificationActionClickedParser() {
mKey = new NotificationKey();
}
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
if (operands.length > 1) {
try {
if (mKey.parse((String) operands[0])) {
int index = (Integer) operands[1];
parseTimes(operands, 2);
LogMaker proto = logger.obtain();
proto.setCategory(MetricsEvent.NOTIFICATION_ITEM_ACTION);
proto.setType(MetricsEvent.TYPE_ACTION);
proto.setSubtype(index);
proto.setTimestamp(eventTimeMs);
proto.setPackageName(mKey.mPackageName);
proto.addTaggedData(MetricsEvent.NOTIFICATION_ID, mKey.mId);
proto.addTaggedData(MetricsEvent.NOTIFICATION_TAG, mKey.mTag);
filltimes(proto);
logger.addEvent(proto);
} else if (debug) {
Log.e(TAG, "unable to parse key.");
}
} catch (ClassCastException e) {
if (debug) {
Log.e(TAG, "unexpected operand type: ", e);
}
}
} else if (debug) {
Log.w(TAG, "wrong number of operands: " + operands.length);
}
}
}

View File

@@ -1,86 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
import android.metrics.LogMaker;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the new Android notification alert event logs.
* @hide
*/
public class NotificationAlertParser extends TagParser {
private static final String TAG = "NotificationAlertParser";
private static final int EVENTLOG_TAG = 27532;
@VisibleForTesting
static final int BUZZ = 0x00000001;
@VisibleForTesting
static final int BEEP = 0x00000002;
@VisibleForTesting
static final int BLINK = 0x00000004;
private final NotificationKey mKey;
public NotificationAlertParser() {
mKey = new NotificationKey();
}
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
if (operands.length > 3) {
try {
final String keyString = (String) operands[0];
final boolean buzz = ((Integer) operands[1]) == 1;
final boolean beep = ((Integer) operands[2]) == 1;
final boolean blink = ((Integer) operands[3]) == 1;
if (mKey.parse(keyString)) {
LogMaker proto = logger.obtain();
proto.setCategory(MetricsEvent.NOTIFICATION_ALERT);
proto.setType(MetricsEvent.TYPE_OPEN);
proto.setSubtype((buzz ? BUZZ : 0) | (beep ? BEEP : 0) | (blink ? BLINK : 0));
proto.setTimestamp(eventTimeMs);
proto.setPackageName(mKey.mPackageName);
proto.addTaggedData(MetricsEvent.NOTIFICATION_ID, mKey.mId);
proto.addTaggedData(MetricsEvent.NOTIFICATION_TAG, mKey.mTag);
filltimes(proto);
logger.addEvent(proto);
} else {
if (debug) {
Log.e(TAG, "unable to parse key: " + keyString);
}
}
} catch (ClassCastException e) {
if (debug) {
Log.e(TAG, "unexpected operand type: ", e);
}
return;
}
} else if (debug) {
Log.w(TAG, "wrong number of operands: " + operands.length);
}
}
}

View File

@@ -1,102 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the Android notification cancellation event logs.
* @hide
*/
public class NotificationCanceledParser extends TagParser {
private static final String TAG = "NotificationCanceled";
private static final int EVENTLOG_TAG = 27530;
// from com.android.server.notification.NotificationManagerService
static final int REASON_DELEGATE_CLICK = 1;
static final int REASON_DELEGATE_CANCEL = 2;
static final int REASON_DELEGATE_CANCEL_ALL = 3;
static final int REASON_PACKAGE_BANNED = 7;
static final int REASON_LISTENER_CANCEL = 10;
static final int REASON_LISTENER_CANCEL_ALL = 11;
private final NotificationKey mKey;
public NotificationCanceledParser() {
mKey = new NotificationKey();
}
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
if (operands.length > 1) {
try {
final String keyString = (String) operands[0];
final int reason = (Integer) operands[1];
parseTimes(operands, 2);
// handle old style log
// TODO: delete once M is launched
if (operands.length < 5) {
mSinceVisibleMillis = mSinceUpdateMillis;
mSinceUpdateMillis = 0;
}
boolean intentional = true;
switch (reason) {
case REASON_DELEGATE_CANCEL:
case REASON_DELEGATE_CANCEL_ALL:
case REASON_LISTENER_CANCEL:
case REASON_LISTENER_CANCEL_ALL:
case REASON_DELEGATE_CLICK:
case REASON_PACKAGE_BANNED:
break;
default:
intentional = false;
}
if (mKey.parse(keyString)) {
if (intentional) {
LogMaker proto = logger.obtain();
proto.setCategory(MetricsEvent.NOTIFICATION_ITEM);
proto.setType(MetricsEvent.TYPE_DISMISS);
proto.setSubtype(reason);
proto.setTimestamp(eventTimeMs);
proto.setPackageName(mKey.mPackageName);
proto.addTaggedData(MetricsEvent.NOTIFICATION_ID, mKey.mId);
proto.addTaggedData(MetricsEvent.NOTIFICATION_TAG, mKey.mTag);
filltimes(proto);
logger.addEvent(proto);
}
} else if (debug) {
Log.e(TAG, "unable to parse key: " + keyString);
}
} catch (ClassCastException e) {
if (debug) {
Log.e(TAG, "unexpected operand type: ", e);
}
}
}
}
}

View File

@@ -1,70 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the Android notification interaction event logs.
* @hide
*/
public class NotificationClickedParser extends TagParser {
private static final String TAG = "NotificationClicked";
private static final int EVENTLOG_TAG = 27520;
private final NotificationKey mKey;
public NotificationClickedParser() {
mKey = new NotificationKey();
}
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
if (operands.length > 0) {
try {
if (mKey.parse((String) operands[0])) {
parseTimes(operands, 1);
LogMaker proto = logger.obtain();
proto.setCategory(MetricsEvent.NOTIFICATION_ITEM);
proto.setType(MetricsEvent.TYPE_ACTION);
proto.setTimestamp(eventTimeMs);
proto.setPackageName(mKey.mPackageName);
proto.addTaggedData(MetricsEvent.NOTIFICATION_ID, mKey.mId);
proto.addTaggedData(MetricsEvent.NOTIFICATION_TAG, mKey.mTag);
filltimes(proto);
logger.addEvent(proto);
} else if (debug) {
Log.e(TAG, "unable to parse key.");
}
} catch (ClassCastException e) {
if (debug) {
Log.e(TAG, "unexpected operand type: ", e);
}
}
} else if (debug) {
Log.w(TAG, "wrong number of operands: " + operands.length);
}
}
}

View File

@@ -1,76 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the Android notification expansion event logs.
* @hide
*/
public class NotificationExpansionParser extends TagParser {
private static final String TAG = "NotificationExpansion";
private static final int EVENTLOG_TAG = 27511;
private final NotificationKey mKey;
public NotificationExpansionParser() {
mKey = new NotificationKey();
}
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
if (operands.length > 2) {
try {
if (mKey.parse((String) operands[0])) {
boolean byUser = ((Integer) operands[1]) == 1;
boolean expanded = ((Integer) operands[2]) == 1;
parseTimes(operands, 3);
if (!byUser || !expanded) {
return;
}
LogMaker proto = logger.obtain();
proto.setCategory(MetricsEvent.NOTIFICATION_ITEM);
proto.setType(MetricsEvent.TYPE_DETAIL);
proto.setTimestamp(eventTimeMs);
proto.setPackageName(mKey.mPackageName);
proto.addTaggedData(MetricsEvent.NOTIFICATION_ID, mKey.mId);
proto.addTaggedData(MetricsEvent.NOTIFICATION_TAG, mKey.mTag);
filltimes(proto);
logger.addEvent(proto);
} else if (debug) {
Log.e(TAG, "unable to parse key.");
}
} catch (ClassCastException e) {
if (debug) {
Log.e(TAG, "unexpected operand type: ", e);
}
}
} else if (debug) {
Log.w(TAG, "wrong number of operands: " + operands.length);
}
}
}

View File

@@ -1,60 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
/**
* Parse Android notification keys
* @hide
*/
public class NotificationKey {
private static final String TAG = "NotificationKey";
public int mUser;
public String mPackageName;
public int mId;
public String mTag;
public int mUid;
public boolean parse(String key) {
if (key == null) {
return false;
}
boolean debug = Util.debug();
String[] parts = key.split("\\|");
if (parts.length == 5) {
try {
mUser = Integer.valueOf(parts[0]);
mPackageName = parts[1];
mId = Integer.valueOf(parts[2]);
mTag = parts[3].equals("null") ? "" : parts[3];
mUid = Integer.valueOf(parts[4]);
return true;
} catch (NumberFormatException e) {
if (debug) {
Log.w(TAG, "could not parse notification key.", e);
}
return false;
}
}
if (debug) {
Log.w(TAG, "wrong number of parts in notification key: " + key);
}
return false;
}
}

View File

@@ -1,42 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the Android notification panel visibility event logs.
* @hide
*/
public class NotificationPanelHiddenParser extends TagParser {
private static final String TAG = "NotificationPanelHidden";
private static final int EVENTLOG_TAG = 27501;
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
LogMaker proto = logger.obtain();
proto.setCategory(MetricsEvent.NOTIFICATION_PANEL);
proto.setType(MetricsEvent.TYPE_CLOSE);
proto.setTimestamp(eventTimeMs);
logger.addEvent(proto);
}
}

View File

@@ -1,56 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the Android notification panel visibility event logs.
* @hide
*/
public class NotificationPanelRevealedParser extends TagParser {
private static final String TAG = "NotificationPanelRevea";
private static final int EVENTLOG_TAG = 27500;
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
if (operands.length >= 1) {
try {
int load = ((Integer) operands[0]).intValue();
//logger.incrementBy(TronCounters.TRON_NOTIFICATION_LOAD, load);
} catch (ClassCastException e) {
if (debug) {
Log.e(TAG, "unexpected operand type: ", e);
}
}
}
LogMaker proto = logger.obtain();
proto.setCategory(MetricsEvent.NOTIFICATION_PANEL);
proto.setType(MetricsEvent.TYPE_OPEN);
proto.setTimestamp(eventTimeMs);
logger.addEvent(proto);
}
}

View File

@@ -1,81 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the new Android notification visibility event logs.
* @hide
*/
public class NotificationVisibilityParser extends TagParser {
private static final String TAG = "NotificationVisibility";
private static final int EVENTLOG_TAG = 27531;
private final NotificationKey mKey;
public NotificationVisibilityParser() {
mKey = new NotificationKey();
}
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
if (operands.length > 1) {
try {
final String keyString = (String) operands[0];
final boolean visible = ((Integer) operands[1]) == 1;
parseTimes(operands, 2);
int index = 0;
if (operands.length > 5 && operands[5] instanceof Integer) {
index = (Integer) operands[5];
}
if (mKey.parse(keyString)) {
LogMaker proto = logger.obtain();
proto.setCategory(MetricsEvent.NOTIFICATION_ITEM);
proto.setType(visible ? MetricsEvent.TYPE_OPEN : MetricsEvent.TYPE_CLOSE);
proto.setTimestamp(eventTimeMs);
proto.setPackageName(mKey.mPackageName);
proto.addTaggedData(MetricsEvent.NOTIFICATION_ID, mKey.mId);
proto.addTaggedData(MetricsEvent.NOTIFICATION_TAG, mKey.mTag);
proto.addTaggedData(MetricsEvent.NOTIFICATION_SHADE_INDEX, index);
filltimes(proto);
logger.addEvent(proto);
} else {
if (debug) {
Log.e(TAG, "unable to parse key: " + keyString);
}
}
} catch (ClassCastException e) {
if (debug) {
Log.e(TAG, "unexpected operand type: ", e);
}
return;
}
} else if (debug) {
Log.w(TAG, "wrong number of operands: " + operands.length);
}
}
}

View File

@@ -1,81 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the Android framework sysui action logs.
* @hide
*/
public class SysuiActionParser extends TagParser {
private static final String TAG = "SysuiActionParser";
private static final int EVENTLOG_TAG = 524288;
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
try {
String packageName = null;
int subType = -1;
boolean hasSubType = false;
if (operands.length > 1) {
String arg = (String) operands[1];
if (arg.equals("true")) {
hasSubType = true;
subType = 1;
} else if (arg.equals("false")) {
hasSubType = true;
subType = 0;
} else if (arg.matches("^-?\\d+$")) {
try {
subType = Integer.valueOf(arg);
hasSubType = true;
} catch (NumberFormatException e) {
}
} else {
packageName = arg;
}
}
if (operands.length > 0) {
int category = ((Integer) operands[0]).intValue();
LogMaker proto = logger.obtain();
proto.setCategory(category);
proto.setType(MetricsEvent.TYPE_ACTION);
proto.setTimestamp(eventTimeMs);
if (packageName != null) {
proto.setPackageName(packageName);
}
if (hasSubType) {
proto.setSubtype(subType);
}
logger.addEvent(proto);
}
} catch (ClassCastException e) {
if (debug) {
Log.e(TAG, "unexpected operand type: ", e);
}
}
}
}

View File

@@ -1,32 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
/**
* Parse the Android framework sysui search query logs.
* For now just treat them like actions.
* @hide
*/
public class SysuiQueryParser extends SysuiActionParser {
private static final String TAG = "SysuiQueryParser";
private static final int EVENTLOG_TAG = 524289;
@Override
public int getTag() {
return EVENTLOG_TAG;
}
}

View File

@@ -1,58 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.util.Log;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
/**
* Parse the Android framework sysui view visibility logs.
* @hide
*/
public class SysuiViewVisibilityParser extends TagParser {
private static final String TAG = "SysuiViewVisibility";
private static final int EVENTLOG_TAG = 524287;
@Override
public int getTag() {
return EVENTLOG_TAG;
}
@Override
public void parseEvent(TronLogger logger, long eventTimeMs, Object[] operands) {
final boolean debug = Util.debug();
if (operands.length >= 2) {
try {
int category = ((Integer) operands[0]).intValue();
boolean visibility = ((Integer) operands[1]).intValue() != 0;
LogMaker proto = logger.obtain();
proto.setCategory(category);
proto.setType(visibility ? MetricsEvent.TYPE_OPEN : MetricsEvent.TYPE_CLOSE);
proto.setTimestamp(eventTimeMs);
logger.addEvent(proto);
} catch (ClassCastException e) {
if (debug) {
Log.e(TAG, "unexpected operand type: ", e);
}
}
} else if (debug) {
Log.w(TAG, "wrong number of operands: " + operands.length);
}
}
}

View File

@@ -1,91 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Matchers.anyInt;
import static org.mockito.Matchers.anyString;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
public class CounterParserTest extends ParserTest {
public CounterParserTest() {
mParser = new CounterParser();
}
public void testGoodData() throws Throwable {
String name = "foo";
int value = 5;
Object[] objects = new Object[2];
objects[0] = name;
objects[1] = value;
validateGoodData(name, value, objects);
}
private void validateGoodData(String name, int value, Object[] objects) {
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, times(1)).incrementBy(mNameCaptor.capture(), mCountCaptor.capture());
assertEquals(TronCounters.TRON_AOSP_PREFIX + name, mNameCaptor.getValue());
assertEquals(value, mCountCaptor.getValue().intValue());
}
public void testMissingName() throws Throwable {
Object[] objects = new Object[1];
objects[0] = 5;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testWrongTypes() throws Throwable {
String name = "foo";
int value = 5;
Object[] objects = new Object[2];
objects[0] = value;
objects[1] = name;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreMissingInput() throws Throwable {
Object[] objects = new Object[0];
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreUnexpectedData() throws Throwable {
String name = "foo";
int value = 5;
Object[] objects = new Object[3];
objects[0] = name;
objects[1] = value;
objects[2] = "foo";
validateGoodData(name, value, objects);
}
}

View File

@@ -1,90 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Matchers.anyInt;
import static org.mockito.Matchers.anyString;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
public class HistogramParserTest extends ParserTest {
public HistogramParserTest() {
mParser = new HistogramParser();
}
public void testGoodData() throws Throwable {
String name = "foo";
int bucket = 5;
Object[] objects = new Object[2];
objects[0] = name;
objects[1] = bucket;
validateGoodData(name, bucket, objects);
}
private void validateGoodData(String name, int bucket, Object[] objects) {
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, times(1))
.incrementIntHistogram(mNameCaptor.capture(), mCountCaptor.capture());
assertEquals(TronCounters.TRON_AOSP_PREFIX + name, mNameCaptor.getValue());
assertEquals(bucket, mCountCaptor.getValue().intValue());
}
public void testMissingName() throws Throwable {
Object[] objects = new Object[1];
objects[0] = 5;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testWrongTypes() throws Throwable {
String name = "foo";
int value = 5;
Object[] objects = new Object[2];
objects[0] = value;
objects[1] = name;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreMissingInput() throws Throwable {
Object[] objects = new Object[0];
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreUnexpectedData() throws Throwable {
String name = "foo";
int bucket = 5;
Object[] objects = new Object[3];
objects[0] = name;
objects[1] = bucket;
objects[2] = "foo";
validateGoodData(name, bucket, objects);
}
}

View File

@@ -1,123 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Matchers.anyObject;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
public class NotificationActionClickedParserTest extends ParserTest {
public NotificationActionClickedParserTest() {
mParser = new NotificationActionClickedParser();
}
public void testGoodData() throws Throwable {
int t = 1000;
int index = 1;
Object[] objects = new Object[2];
objects[0] = mKey;
objects[1] = index;
validateGoodData(t, "", index, objects);
}
public void testTagged() throws Throwable {
int t = 1000;
int index = 1;
Object[] objects = new Object[2];
objects[0] = mTaggedKey;
objects[1] = index;
validateGoodData(t, mTag, index, objects);
}
private LogMaker validateGoodData(int t, String tag, int index, Object[] objects) {
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(MetricsEvent.NOTIFICATION_ITEM_ACTION, proto.getCategory());
assertEquals(mKeyPackage, proto.getPackageName());
validateNotificationIdAndTag(proto, mId, tag);
assertEquals(MetricsEvent.TYPE_ACTION, proto.getType());
assertEquals(index, proto.getSubtype());
return proto;
}
public void testMissingData() throws Throwable {
Object[] objects = new Object[0];
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testWrongType() throws Throwable {
Object[] objects = new Object[2];
objects[0] = 2;
objects[1] = 5;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testBadKey() throws Throwable {
Object[] objects = new Object[2];
objects[0] = "foo";
objects[1] = 5;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testMncTimestamps() throws Throwable {
int t = 1000;
int index = 1;
Object[] objects = new Object[5];
objects[0] = mKey;
objects[1] = index;
objects[2] = mSinceCreationMillis;
objects[3] = mSinceUpdateMillis;
objects[4] = mSinceVisibleMillis;
LogMaker proto = validateGoodData(t, "", index, objects);
validateNotificationTimes(proto, mSinceCreationMillis, mSinceUpdateMillis,
mSinceVisibleMillis);
}
public void testIgnoreUnexpectedData() throws Throwable {
int t = 1000;
int index = 1;
Object[] objects = new Object[6];
objects[0] = mKey;
objects[1] = index;
objects[2] = mSinceCreationMillis;
objects[3] = mSinceUpdateMillis;
objects[4] = mSinceVisibleMillis;
objects[5] = "foo";
validateGoodData(t, "", index, objects);
}
}

View File

@@ -1,135 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Matchers.anyString;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import org.mockito.ArgumentCaptor;
public class NotificationAlertParserTest extends ParserTest {
protected ArgumentCaptor<Boolean> mConfigCaptor;
private final int mTime = 1000;
public NotificationAlertParserTest() {
mParser = new NotificationAlertParser();
}
@Override
protected void setUp() throws Exception {
super.setUp();
mConfigCaptor = ArgumentCaptor.forClass(Boolean.class);
when(mLogger.getConfig(anyString())).thenReturn(false);
}
public void testBuzzOnly() throws Throwable {
Object[] objects = new Object[4];
objects[0] = mTaggedKey;
objects[1] = 1;
objects[2] = 0;
objects[3] = 0;
validateInteraction(true, false, false, objects);
}
public void testBeepOnly() throws Throwable {
Object[] objects = new Object[4];
objects[0] = mTaggedKey;
objects[1] = 0;
objects[2] = 1;
objects[3] = 0;
validateInteraction(false, true, false, objects);
}
public void testBlinkOnly() throws Throwable {
Object[] objects = new Object[4];
objects[0] = mTaggedKey;
objects[1] = 0;
objects[2] = 0;
objects[3] = 1;
validateInteraction(false, false, true, objects);
}
public void testBuzzBlink() throws Throwable {
Object[] objects = new Object[4];
objects[0] = mTaggedKey;
objects[1] = 1;
objects[2] = 0;
objects[3] = 1;
validateInteraction(true, false, true, objects);
}
public void testBeepBlink() throws Throwable {
Object[] objects = new Object[4];
objects[0] = mTaggedKey;
objects[1] = 0;
objects[2] = 1;
objects[3] = 1;
validateInteraction(false, true, true, objects);
}
public void testIgnoreExtraArgs() throws Throwable {
Object[] objects = new Object[5];
objects[0] = mTaggedKey;
objects[1] = 0;
objects[2] = 1;
objects[3] = 1;
objects[4] = "foo";
validateInteraction(false, true, true, objects);
}
private void validateInteraction(boolean buzz, boolean beep, boolean blink, Object[] objects) {
int flags = 0;
int counts = 0;
if (buzz) {
counts++;
flags |= NotificationAlertParser.BUZZ;
}
if (beep) {
counts++;
flags |= NotificationAlertParser.BEEP;
}
if (blink) {
counts++;
flags |= NotificationAlertParser.BLINK;
}
mParser.parseEvent(mLogger, mTime, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(mTime, proto.getTimestamp());
assertEquals(MetricsEvent.NOTIFICATION_ALERT, proto.getCategory());
assertEquals(mKeyPackage, proto.getPackageName());
validateNotificationIdAndTag(proto, mId, mTag);
assertEquals(flags, proto.getSubtype());
assertEquals(MetricsEvent.TYPE_OPEN, proto.getType());
}
}

View File

@@ -1,198 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Mockito.anyObject;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
public class NotificationCanceledParserTest extends ParserTest {
public NotificationCanceledParserTest() {
mParser = new NotificationCanceledParser();
}
public void testGoodProto() throws Throwable {
int t = 1000;
int reason = NotificationCanceledParser.REASON_DELEGATE_CANCEL;
Object[] objects = new Object[2];
objects[0] = mKey;
objects[1] = reason;
validateGoodData(t, "", reason, objects);
}
public void testTagged() throws Throwable {
int t = 1000;
int reason = NotificationCanceledParser.REASON_DELEGATE_CANCEL;
Object[] objects = new Object[2];
objects[0] = mTaggedKey;
objects[1] = reason;
validateGoodData(t, mTag, reason, objects);
}
private void validateGoodData(int t, String tag, int reason, Object[] objects) {
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(MetricsEvent.NOTIFICATION_ITEM, proto.getCategory());
assertEquals(mKeyPackage, proto.getPackageName());
validateNotificationIdAndTag(proto, mId, tag);
assertEquals(MetricsEvent.TYPE_DISMISS, proto.getType());
assertEquals(reason, proto.getSubtype());
}
public void testLifetime() throws Throwable {
int t = 1000;
int reason = NotificationCanceledParser.REASON_DELEGATE_CANCEL;
Object[] objects = new Object[3];
objects[0] = mKey;
objects[1] = reason;
objects[2] = mSinceCreationMillis;
validateTimers(t, objects, mSinceCreationMillis, 0, 0);
}
public void testExposure() throws Throwable {
int t = 1000;
int reason = NotificationCanceledParser.REASON_DELEGATE_CANCEL;
Object[] objects = new Object[4];
objects[0] = mKey;
objects[1] = reason;
objects[2] = mSinceCreationMillis;
objects[3] = mSinceVisibleMillis;
validateTimers(t, objects, mSinceCreationMillis, 0, mSinceVisibleMillis);
}
public void testFreshness() throws Throwable {
int t = 1000;
int reason = NotificationCanceledParser.REASON_DELEGATE_CANCEL;
Object[] objects = new Object[5];
objects[0] = mKey;
objects[1] = reason;
objects[2] = mSinceCreationMillis;
objects[3] = mSinceUpdateMillis;
objects[4] = mSinceVisibleMillis;
validateTimers(t, objects, mSinceCreationMillis, mSinceUpdateMillis, mSinceVisibleMillis);
}
private void validateTimers(int t, Object[] objects, int life, int freshness, int exposure) {
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
validateNotificationTimes(proto, life, freshness, exposure);
}
public void verifyReason(int reason, boolean intentional, boolean important, String counter)
throws Throwable {
Object[] objects = new Object[2];
objects[0] = mKey;
objects[1] = reason;
mParser.parseEvent(mLogger, 0, objects);
if (intentional) {
verify(mLogger, times(1)).addEvent((LogMaker) anyObject());
}
}
public void testDelegateCancel() throws Throwable {
verifyReason(NotificationCanceledParser.REASON_DELEGATE_CANCEL,
true, true, TronCounters.TRON_NOTE_DISMISS_BY_USER);
}
public void testDelegateCancelAll() throws Throwable {
verifyReason(NotificationCanceledParser.REASON_DELEGATE_CANCEL_ALL,
true, true, TronCounters.TRON_NOTE_DISMISS_BY_USER);
}
public void testListenerCancel() throws Throwable {
verifyReason(NotificationCanceledParser.REASON_LISTENER_CANCEL,
false, true, TronCounters.TRON_NOTE_DISMISS_BY_LISTENER);
}
public void testListenerCancelAll() throws Throwable {
verifyReason(NotificationCanceledParser.REASON_LISTENER_CANCEL_ALL,
false, true, TronCounters.TRON_NOTE_DISMISS_BY_LISTENER);
}
public void testDelegateClick() throws Throwable {
verifyReason(NotificationCanceledParser.REASON_DELEGATE_CLICK,
true, true, TronCounters.TRON_NOTE_DISMISS_BY_CLICK);
}
public void testBanned() throws Throwable {
verifyReason(NotificationCanceledParser.REASON_PACKAGE_BANNED,
false, true, TronCounters.TRON_NOTE_DISMISS_BY_BAN);
}
public void testUnknownReason() throws Throwable {
verifyReason(1001010, false, false, TronCounters.TRON_NOTE_DISMISS_BY_BAN);
}
public void testMissingData() throws Throwable {
Object[] objects = new Object[0];
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testWrongType() throws Throwable {
Object[] objects = new Object[2];
objects[0] = 2;
objects[1] = 5;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testBadKey() throws Throwable {
Object[] objects = new Object[2];
objects[0] = "foo";
objects[1] = 5;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testIgnoreUnexpectedData() throws Throwable {
int t = 1000;
int reason = NotificationCanceledParser.REASON_DELEGATE_CANCEL;
Object[] objects = new Object[3];
objects[0] = mKey;
objects[1] = reason;
objects[2] = "foo";
validateGoodData(t, "", reason, objects);
}
}

View File

@@ -1,114 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Matchers.anyObject;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
public class NotificationClickedParserTest extends ParserTest {
public NotificationClickedParserTest() {
mParser = new NotificationClickedParser();
}
public void testGoodData() throws Throwable {
int t = 1000;
Object[] objects = new Object[1];
objects[0] = mKey;
validateGoodData(t, "", objects);
}
public void testTagged() throws Throwable {
int t = 1000;
Object[] objects = new Object[1];
objects[0] = mTaggedKey;
validateGoodData(t, mTag, objects);
}
private LogMaker validateGoodData(int t, String tag, Object[] objects) {
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(MetricsEvent.NOTIFICATION_ITEM, proto.getCategory());
assertEquals(mKeyPackage, proto.getPackageName());
validateNotificationIdAndTag(proto, mId, tag);
assertEquals(MetricsEvent.TYPE_ACTION, proto.getType());
assertEquals(0, proto.getSubtype());
return proto;
}
public void testMissingKey() throws Throwable {
Object[] objects = new Object[0];
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testWrongType() throws Throwable {
Object[] objects = new Object[1];
objects[0] = 5;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testBadKey() throws Throwable {
Object[] objects = new Object[1];
objects[0] = "foo";
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testMncTimestamps() throws Throwable {
int t = 1000;
Object[] objects = new Object[4];
objects[0] = mKey;
objects[1] = mSinceCreationMillis;
objects[2] = mSinceUpdateMillis;
objects[3] = mSinceVisibleMillis;
LogMaker proto = validateGoodData(t, "", objects);
validateNotificationTimes(proto, mSinceCreationMillis, mSinceUpdateMillis,
mSinceVisibleMillis);
}
public void testIgnoreUnexpectedData() throws Throwable {
int t = 1000;
Object[] objects = new Object[5];
objects[0] = mKey;
objects[1] = mSinceCreationMillis;
objects[2] = mSinceUpdateMillis;
objects[3] = mSinceVisibleMillis;
objects[4] = "foo";
validateGoodData(t, "", objects);
}
}

View File

@@ -1,175 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Matchers.anyObject;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
public class NotificationExpansionParserTest extends ParserTest {
public NotificationExpansionParserTest() {
mParser = new NotificationExpansionParser();
}
public void testExpandedByUser() throws Throwable {
int t = 1000;
int byUser = 1;
int expanded = 1;
Object[] objects = new Object[3];
objects[0] = mKey;
objects[1] = byUser;
objects[2] = expanded;
validateGoodData(t, "", objects);
}
public void testTagged() throws Throwable {
int t = 1000;
int byUser = 1;
int expanded = 1;
Object[] objects = new Object[3];
objects[0] = mTaggedKey;
objects[1] = byUser;
objects[2] = expanded;
validateGoodData(t, mTag, objects);
}
private LogMaker validateGoodData(int t, String tag, Object[] objects) {
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(MetricsEvent.NOTIFICATION_ITEM, proto.getCategory());
assertEquals(mKeyPackage, proto.getPackageName());
validateNotificationIdAndTag(proto, mId, tag);
assertEquals(MetricsEvent.TYPE_DETAIL, proto.getType());
return proto;
}
public void testAutoExpand() throws Throwable {
int t = 1000;
int byUser = 0;
int expanded = 1;
Object[] objects = new Object[3];
objects[0] = mKey;
objects[1] = byUser;
objects[2] = expanded;
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testCollapsedByUser() throws Throwable {
int t = 1000;
int byUser = 1;
int expanded = 0;
Object[] objects = new Object[3];
objects[0] = mKey;
objects[1] = byUser;
objects[2] = expanded;
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testAutoCollapsed() throws Throwable {
int t = 1000;
int byUser = 0;
int expanded = 0;
Object[] objects = new Object[3];
objects[0] = mKey;
objects[1] = byUser;
objects[2] = expanded;
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testMissingData() throws Throwable {
Object[] objects = new Object[0];
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testWrongType() throws Throwable {
Object[] objects = new Object[3];
objects[0] = 2;
objects[1] = 5;
objects[2] = 7;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testBadKey() throws Throwable {
Object[] objects = new Object[3];
objects[0] = "foo";
objects[1] = 5;
objects[2] = 2;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
}
public void testMncTimestamps() throws Throwable {
int t = 1000;
int byUser = 1;
int expanded = 1;
Object[] objects = new Object[6];
objects[0] = mKey;
objects[1] = byUser;
objects[2] = expanded;
objects[3] = mSinceCreationMillis;
objects[4] = mSinceUpdateMillis;
objects[5] = mSinceVisibleMillis;
LogMaker proto = validateGoodData(t, "", objects);
validateNotificationTimes(proto, mSinceCreationMillis, mSinceUpdateMillis,
mSinceVisibleMillis);
}
public void testIgnoreUnexpectedData() throws Throwable {
int t = 1000;
int byUser = 1;
int expanded = 1;
Object[] objects = new Object[7];
objects[0] = mKey;
objects[1] = byUser;
objects[2] = expanded;
objects[3] = mSinceCreationMillis;
objects[4] = mSinceUpdateMillis;
objects[5] = mSinceVisibleMillis;
objects[6] = "foo";
validateGoodData(t, "", objects);
}
}

View File

@@ -1,65 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import android.test.InstrumentationTestCase;
public class NotificationKeyTest extends InstrumentationTestCase {
private final NotificationKey mKey;
public NotificationKeyTest() {
mKey = new NotificationKey();
}
public void testGoodKey() throws Throwable {
assertTrue(mKey.parse("1|com.android.example.notificationshowcase|31338|null|10090"));
assertEquals("com.android.example.notificationshowcase", mKey.mPackageName);
assertEquals("", mKey.mTag);
assertEquals(31338, mKey.mId);
assertEquals(1, mKey.mUser);
assertEquals(10090, mKey.mUid);
}
public void testTaggedKey() throws Throwable {
assertTrue(mKey.parse("1|com.android.example.notificationshowcase|31338|foo|10090"));
assertEquals("com.android.example.notificationshowcase", mKey.mPackageName);
assertEquals("foo", mKey.mTag);
assertEquals(31338, mKey.mId);
assertEquals(1, mKey.mUser);
assertEquals(10090, mKey.mUid);
}
public void testEmptyTag() throws Throwable {
assertTrue(mKey.parse("1|com.android.example.notificationshowcase|31338||10090"));
assertEquals("com.android.example.notificationshowcase", mKey.mPackageName);
assertEquals("", mKey.mTag);
assertEquals(31338, mKey.mId);
assertEquals(1, mKey.mUser);
assertEquals(10090, mKey.mUid);
}
public void testBadKeys() throws Throwable {
assertFalse(mKey.parse(null));
assertFalse(mKey.parse(""));
assertFalse(mKey.parse("foo")); // not a key
assertFalse(mKey.parse("1|com.android.example.notificationshowcase|31338|null"));
assertFalse(mKey.parse("bar|com.android.example.notificationshowcase|31338|null|10090"));
}
}

View File

@@ -1,56 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
public class NotificationPanelHiddenParserTest extends ParserTest {
public NotificationPanelHiddenParserTest() {
mParser = new NotificationPanelHiddenParser();
}
public void testNoInput() throws Throwable {
int t = 1000;
Object[] objects = new Object[0];
validateGoodData(t, objects);
}
public void testIgnoreExtraneousInput() throws Throwable {
Object[] objects = new Object[1];
objects[0] = "nothing to see here";
validateGoodData(0, objects);
}
private void validateGoodData(int t, Object[] objects) {
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(MetricsEvent.NOTIFICATION_PANEL, proto.getCategory());
assertEquals(MetricsEvent.TYPE_CLOSE, proto.getType());
}
}

View File

@@ -1,84 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Matchers.anyObject;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
public class NotificationPanelRevealedParserTest extends ParserTest {
public NotificationPanelRevealedParserTest() {
mParser = new NotificationPanelRevealedParser();
}
public void testLollipopInput() throws Throwable {
int t = 1000;
Object[] objects = new Object[0];
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(MetricsEvent.NOTIFICATION_PANEL, proto.getCategory());
assertEquals(MetricsEvent.TYPE_OPEN, proto.getType());
}
public void testMncData() throws Throwable {
int t = 1000;
int n = 5;
Object[] objects = new Object[1];
objects[0] = Integer.valueOf(n);
validateMncData(t, n, objects);
}
private void validateMncData(int t, int n, Object[] objects) {
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(MetricsEvent.NOTIFICATION_PANEL, proto.getCategory());
assertEquals(MetricsEvent.TYPE_OPEN, proto.getType());
}
public void testBadInput() throws Throwable {
Object[] objects = new Object[1];
objects[0] = "This is not the integer you're looking for.";
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, times(1)).addEvent((LogMaker) anyObject());
}
public void testIgnoreUnexpectedData() throws Throwable {
int t = 1000;
int n = 5;
Object[] objects = new Object[2];
objects[0] = Integer.valueOf(n);
objects[1] = "foo";
validateMncData(t, n, objects);
}
}

View File

@@ -1,92 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static junit.framework.Assert.assertTrue;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
public class NotificationVisibilityParserTest extends ParserTest {
private final int mCreationTime = 23124;
private final int mUpdateTime = 3412;
private final int mTime = 1000;
public NotificationVisibilityParserTest() {
mParser = new NotificationVisibilityParser();
}
public void testReveal() throws Throwable {
Object[] objects = new Object[4];
objects[0] = mTaggedKey;
objects[1] = 1;
objects[2] = mCreationTime;
objects[3] = mUpdateTime;
validateInteraction(true, mUpdateTime, 0, objects);
}
public void testHide() throws Throwable {
Object[] objects = new Object[4];
objects[0] = mTaggedKey;
objects[1] = 0;
objects[2] = mCreationTime;
objects[3] = mUpdateTime;
validateInteraction(false, mUpdateTime, 0, objects);
}
public void testIgnoreUnexpectedData() throws Throwable {
Object[] objects = new Object[5];
objects[0] = mTaggedKey;
objects[1] = 1;
objects[2] = mCreationTime;
objects[3] = mUpdateTime;
objects[4] = "foo";
validateInteraction(true, mUpdateTime, 0, objects);
}
public void testMarshmallowIndexData() throws Throwable {
Object[] objects = new Object[6];
objects[0] = mTaggedKey;
objects[1] = 1;
objects[2] = mCreationTime;
objects[3] = mUpdateTime;
objects[4] = 0;
objects[5] = 3;
validateInteraction(true, mUpdateTime, 3, objects);
}
private void validateInteraction(boolean visible, int freshness, int index, Object[] objects) {
mParser.parseEvent(mLogger, mTime, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(mTime, proto.getTimestamp());
assertEquals(MetricsEvent.NOTIFICATION_ITEM, proto.getCategory());
assertEquals(mKeyPackage, proto.getPackageName());
validateNotificationIdAndTag(proto, mId, mTag);
validateNotificationTimes(proto, mCreationTime, mUpdateTime);
assertEquals(index, proto.getTaggedData(MetricsEvent.NOTIFICATION_SHADE_INDEX));
assertEquals(visible ? MetricsEvent.TYPE_OPEN : MetricsEvent.TYPE_CLOSE, proto.getType());
}
}

View File

@@ -1,167 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Matchers.anyInt;
import static org.mockito.Matchers.anyObject;
import static org.mockito.Matchers.anyString;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
public class SysuiActionParserTest extends ParserTest {
public SysuiActionParserTest() {
mParser = new SysuiActionParser();
}
public void testGoodDatal() throws Throwable {
int t = 1000;
int view = 10;
Object[] objects = new Object[1];
objects[0] = view;
validateGoodData(t, view, objects);
}
private void validateGoodData(int t, int view, Object[] objects) {
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(view, proto.getCategory());
assertEquals(MetricsEvent.TYPE_ACTION, proto.getType());
}
public void testGoodDataWithPackage() throws Throwable {
int t = 1000;
int view = 10;
String packageName = "com.foo";
Object[] objects = new Object[2];
objects[0] = view;
objects[1] = packageName;
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(view, proto.getCategory());
assertEquals(packageName, proto.getPackageName());
assertEquals(MetricsEvent.TYPE_ACTION, proto.getType());
}
public void testGoodDataWithTrue() throws Throwable {
validateSubType(Boolean.toString(true), 1);
}
public void testGoodDataWithFalse() throws Throwable {
validateSubType(Boolean.toString(false), 0);
}
public void testGoodDataWithIntZero() throws Throwable {
validateSubType(Integer.toString(0), 0);
}
public void testGoodDataWithIntONe() throws Throwable {
validateSubType(Integer.toString(1), 1);
}
public void testGoodDataWithIntTwo() throws Throwable {
validateSubType(Integer.toString(2), 2);
}
public void testGoodDataWithNegativeInt() throws Throwable {
validateSubType(Integer.toString(-1), -1);
}
public void testGoodDataWithIntLarge() throws Throwable {
validateSubType(Integer.toString(120312), 120312);
}
public void testGoodDataWithNegativeIntLarge() throws Throwable {
validateSubType(Integer.toString(-120312), -120312);
}
private void validateSubType(String arg, int expectedValue) {
int t = 1000;
int view = 10;
Object[] objects = new Object[2];
objects[0] = view;
objects[1] = arg;
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(view, proto.getCategory());
assertEquals(expectedValue, proto.getSubtype());
assertNull(proto.getPackageName());
assertEquals(MetricsEvent.TYPE_ACTION, proto.getType());
}
public void testIgnoreMissingInput() throws Throwable {
Object[] objects = new Object[0];
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreWrongInputs() throws Throwable {
Object[] objects = new Object[2];
objects[0] = "nothing to see here";
objects[1] = 10;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreStringViewInput() throws Throwable {
Object[] objects = new Object[1];
objects[0] = "this is not the input you are looking for";
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreUnexpectedData() throws Throwable {
int t = 1000;
int view = 10;
Object[] objects = new Object[2];
objects[0] = view;
objects[1] = "foo";
validateGoodData(t, view, objects);
}
}

View File

@@ -1,122 +0,0 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.logging.legacy;
import static org.mockito.Matchers.anyInt;
import static org.mockito.Matchers.anyObject;
import static org.mockito.Matchers.anyString;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import android.metrics.LogMaker;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
public class SysuiViewVisibilityParserTest extends ParserTest {
public SysuiViewVisibilityParserTest() {
mParser = new SysuiViewVisibilityParser();
}
public void testViewReveal() throws Throwable {
int t = 1000;
int view = 10;
Object[] objects = new Object[2];
objects[0] = view;
objects[1] = 100;
validateViewReveal(t, view, objects);
}
private void validateViewReveal(int t, int view, Object[] objects) {
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(t, proto.getTimestamp());
assertEquals(view, proto.getCategory());
assertEquals(MetricsEvent.TYPE_OPEN, proto.getType());
}
public void testViewHidden() throws Throwable {
int t = 1000;
int view = 10;
Object[] objects = new Object[2];
objects[0] = view;
objects[1] = 0;
mParser.parseEvent(mLogger, t, objects);
verify(mLogger, times(1)).addEvent(mProtoCaptor.capture());
LogMaker proto = mProtoCaptor.getValue();
assertEquals(MetricsEvent.TYPE_CLOSE, proto.getType());
}
public void testIgnoreMissingInput() throws Throwable {
Object[] objects = new Object[0];
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreStringInARgOne() throws Throwable {
Object[] objects = new Object[2];
objects[0] = "nothing to see here";
objects[1] = 100;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreStringInArgTwo() throws Throwable {
Object[] objects = new Object[2];
objects[0] = 100;
objects[1] = "nothing to see here";
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testOneInput() throws Throwable {
Object[] objects = new Object[1];
objects[0] = 100;
mParser.parseEvent(mLogger, 0, objects);
verify(mLogger, never()).addEvent((LogMaker) anyObject());
verify(mLogger, never()).incrementBy(anyString(), anyInt());
}
public void testIgnoreUnexpectedData() throws Throwable {
int t = 1000;
int view = 10;
Object[] objects = new Object[3];
objects[0] = view;
objects[1] = 100;
objects[2] = "foo";
validateViewReveal(t, view, objects);
}
}

View File

@@ -86,6 +86,7 @@ import android.database.ContentObserver;
import android.media.AudioManager;
import android.media.AudioManagerInternal;
import android.media.IRingtonePlayer;
import android.metrics.LogMaker;
import android.net.Uri;
import android.os.Binder;
import android.os.Bundle;
@@ -132,6 +133,8 @@ import android.widget.Toast;
import com.android.internal.R;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.logging.MetricsLogger;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.internal.statusbar.NotificationVisibility;
import com.android.internal.util.FastXmlSerializer;
import com.android.internal.util.Preconditions;
@@ -549,6 +552,9 @@ public class NotificationManagerService extends SystemService {
return;
}
final long now = System.currentTimeMillis();
MetricsLogger.action(r.getLogMaker(now)
.setCategory(MetricsEvent.NOTIFICATION_ITEM)
.setType(MetricsEvent.TYPE_ACTION));
EventLogTags.writeNotificationClicked(key,
r.getLifespanMs(now), r.getFreshnessMs(now), r.getExposureMs(now));
@@ -570,6 +576,10 @@ public class NotificationManagerService extends SystemService {
return;
}
final long now = System.currentTimeMillis();
MetricsLogger.action(r.getLogMaker(now)
.setCategory(MetricsEvent.NOTIFICATION_ITEM_ACTION)
.setType(MetricsEvent.TYPE_ACTION)
.setSubtype(actionIndex));
EventLogTags.writeNotificationActionClicked(key, actionIndex,
r.getLifespanMs(now), r.getFreshnessMs(now), r.getExposureMs(now));
// TODO: Log action click via UsageStats.
@@ -586,6 +596,8 @@ public class NotificationManagerService extends SystemService {
@Override
public void onPanelRevealed(boolean clearEffects, int items) {
MetricsLogger.visible(getContext(), MetricsEvent.NOTIFICATION_PANEL);
MetricsLogger.histogram(getContext(), "notification_load", items);
EventLogTags.writeNotificationPanelRevealed(items);
if (clearEffects) {
clearEffects();
@@ -594,6 +606,7 @@ public class NotificationManagerService extends SystemService {
@Override
public void onPanelHidden() {
MetricsLogger.hidden(getContext(), MetricsEvent.NOTIFICATION_PANEL);
EventLogTags.writeNotificationPanelHidden();
}
@@ -655,6 +668,9 @@ public class NotificationManagerService extends SystemService {
if (r != null) {
r.stats.onExpansionChanged(userAction, expanded);
final long now = System.currentTimeMillis();
MetricsLogger.action(r.getLogMaker(now)
.setCategory(MetricsEvent.NOTIFICATION_ITEM)
.setType(MetricsEvent.TYPE_DETAIL));
EventLogTags.writeNotificationExpansion(key,
userAction ? 1 : 0, expanded ? 1 : 0,
r.getLifespanMs(now), r.getFreshnessMs(now), r.getExposureMs(now));
@@ -3426,6 +3442,10 @@ public class NotificationManagerService extends SystemService {
& NotificationListenerService.SUPPRESSED_EFFECT_SCREEN_OFF) != 0)) {
if (DBG) Slog.v(TAG, "Suppressed SystemUI from triggering screen on");
} else {
MetricsLogger.action(record.getLogMaker()
.setCategory(MetricsEvent.NOTIFICATION_ALERT)
.setType(MetricsEvent.TYPE_OPEN)
.setSubtype((buzz ? 1 : 0) | (beep ? 2 : 0) | (blink ? 4 : 0)));
EventLogTags.writeNotificationAlert(key,
buzz ? 1 : 0, beep ? 1 : 0, blink ? 1 : 0);
mHandler.post(mBuzzBeepBlinked);
@@ -3896,6 +3916,10 @@ public class NotificationManagerService extends SystemService {
mArchive.record(r.sbn);
final long now = System.currentTimeMillis();
MetricsLogger.action(r.getLogMaker(now)
.setCategory(MetricsEvent.NOTIFICATION_ITEM)
.setType(MetricsEvent.TYPE_DISMISS)
.setSubtype(reason));
EventLogTags.writeNotificationCanceled(canceledKey, reason,
r.getLifespanMs(now), r.getFreshnessMs(now), r.getExposureMs(now));
}

View File

@@ -31,6 +31,7 @@ import android.graphics.Bitmap;
import android.graphics.drawable.Icon;
import android.media.AudioAttributes;
import android.media.AudioSystem;
import android.metrics.LogMaker;
import android.net.Uri;
import android.os.Build;
import android.os.UserHandle;
@@ -44,6 +45,8 @@ import android.util.Slog;
import android.util.TimeUtils;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.logging.MetricsLogger;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.server.EventLogTags;
import java.io.PrintWriter;
@@ -118,6 +121,7 @@ public final class NotificationRecord {
private ArrayList<String> mPeopleOverride;
private ArrayList<SnoozeCriterion> mSnoozeCriteria;
private boolean mShowBadge;
private LogMaker mLogMaker;
@VisibleForTesting
public NotificationRecord(Context context, StatusBarNotification sbn,
@@ -585,9 +589,16 @@ public final class NotificationRecord {
final long now = System.currentTimeMillis();
mVisibleSinceMs = visible ? now : mVisibleSinceMs;
stats.onVisibilityChanged(visible);
MetricsLogger.action(getLogMaker(now)
.setCategory(MetricsEvent.NOTIFICATION_ITEM)
.setType(visible ? MetricsEvent.TYPE_OPEN : MetricsEvent.TYPE_CLOSE)
.addTaggedData(MetricsEvent.NOTIFICATION_SHADE_INDEX, rank));
if (visible) {
MetricsLogger.histogram(mContext, "note_freshness", getFreshnessMs(now));
}
EventLogTags.writeNotificationVisibility(getKey(), visible ? 1 : 0,
(int) (now - mCreationTimeMs),
(int) (now - mUpdateTimeMs),
getLifespanMs(now),
getFreshnessMs(now),
0, // exposure time
rank);
}
@@ -690,4 +701,25 @@ public final class NotificationRecord {
protected void setSnoozeCriteria(ArrayList<SnoozeCriterion> snoozeCriteria) {
mSnoozeCriteria = snoozeCriteria;
}
public LogMaker getLogMaker(long now) {
if (mLogMaker == null) {
mLogMaker = new LogMaker(MetricsEvent.VIEW_UNKNOWN)
.setPackageName(sbn.getPackageName())
.addTaggedData(MetricsEvent.NOTIFICATION_ID, sbn.getId())
.addTaggedData(MetricsEvent.NOTIFICATION_TAG, sbn.getTag());
}
return mLogMaker
.setCategory(MetricsEvent.VIEW_UNKNOWN)
.setType(MetricsEvent.TYPE_UNKNOWN)
.setSubtype(0)
.clearTaggedData(MetricsEvent.NOTIFICATION_SHADE_INDEX)
.addTaggedData(MetricsEvent.NOTIFICATION_SINCE_CREATE_MILLIS, getLifespanMs(now))
.addTaggedData(MetricsEvent.NOTIFICATION_SINCE_UPDATE_MILLIS, getFreshnessMs(now))
.addTaggedData(MetricsEvent.NOTIFICATION_SINCE_VISIBLE_MILLIS, getExposureMs(now));
}
public LogMaker getLogMaker() {
return getLogMaker(System.currentTimeMillis());
}
}

View File

@@ -46,7 +46,6 @@ import java.util.concurrent.Semaphore;
import java.util.concurrent.TimeUnit;
import android.os.SystemClock;
import com.android.internal.logging.MetricsLogger;
/**
* This {@link NotificationSignalExtractor} attempts to validate
@@ -264,9 +263,6 @@ public class ValidateNotificationPeople implements NotificationSignalExtractor {
// record the best available data, so far:
affinityOut[0] = affinity;
MetricsLogger.histogram(mBaseContext, "validate_people_cache_latency",
(int) (SystemClock.elapsedRealtime() - start));
if (pendingLookups.isEmpty()) {
if (VERBOSE) Slog.i(TAG, "final affinity: " + affinity);
return null;
@@ -485,9 +481,6 @@ public class ValidateNotificationPeople implements NotificationSignalExtractor {
mUsageStats.registerPeopleAffinity(mRecord, mContactAffinity > NONE,
mContactAffinity == STARRED_CONTACT, false /* cached */);
}
MetricsLogger.histogram(mBaseContext, "validate_people_lookup_latency",
(int) (SystemClock.elapsedRealtime() - start));
}
@Override