Merge "Add action active check for anomaly action." into oc-dr1-dev
am: e7735b8d52
Change-Id: I01b51abb73fdc39597388878a846266c339815e2
This commit is contained in:
@@ -24,11 +24,18 @@ import com.android.settings.fuelgauge.anomaly.Anomaly;
|
||||
public interface AnomalyAction {
|
||||
/**
|
||||
* handle the action when user clicks positive button
|
||||
* @param Anomaly about the app that we need to handle
|
||||
* @param anomaly about the app that we need to handle
|
||||
* @param metricsKey key for the page that invokes the action
|
||||
*
|
||||
* @see com.android.internal.logging.nano.MetricsProto
|
||||
*/
|
||||
void handlePositiveAction(Anomaly Anomaly, int metricsKey);
|
||||
void handlePositiveAction(Anomaly anomaly, int metricsKey);
|
||||
|
||||
/**
|
||||
* Check whether the action is active for {@code anomaly}
|
||||
* @param anomaly about the app that we need to handle
|
||||
* @return {@code true} if action is active, otherwise return {@code false}
|
||||
*/
|
||||
boolean isActionActive(Anomaly anomaly);
|
||||
int getActionType();
|
||||
}
|
||||
|
@@ -45,6 +45,14 @@ public class BackgroundCheckAction implements AnomalyAction {
|
||||
AppOpsManager.MODE_IGNORED);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActionActive(Anomaly anomaly) {
|
||||
final int mode = mAppOpsManager
|
||||
.checkOpNoThrow(AppOpsManager.OP_RUN_IN_BACKGROUND, anomaly.uid,
|
||||
anomaly.packageName);
|
||||
return mode != AppOpsManager.MODE_IGNORED && mode != AppOpsManager.MODE_ERRORED;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getActionType() {
|
||||
return Anomaly.AnomalyActionType.BACKGROUND_CHECK;
|
||||
|
@@ -18,6 +18,9 @@ package com.android.settings.fuelgauge.anomaly.action;
|
||||
|
||||
import android.app.ActivityManager;
|
||||
import android.content.Context;
|
||||
import android.content.pm.ApplicationInfo;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.util.Log;
|
||||
import android.util.Pair;
|
||||
|
||||
import com.android.internal.logging.nano.MetricsProto;
|
||||
@@ -25,20 +28,25 @@ import com.android.settings.core.instrumentation.MetricsFeatureProvider;
|
||||
import com.android.settings.fuelgauge.anomaly.Anomaly;
|
||||
import com.android.settings.overlay.FeatureFactory;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Force stop action for anomaly app, which means to stop the app which causes anomaly
|
||||
*/
|
||||
public class ForceStopAction implements AnomalyAction {
|
||||
private static final String TAG = "ForceStopAction";
|
||||
|
||||
private Context mContext;
|
||||
private MetricsFeatureProvider mMetricsFeatureProvider;
|
||||
private ActivityManager mActivityManager;
|
||||
private PackageManager mPackageManager;
|
||||
|
||||
public ForceStopAction(Context context) {
|
||||
mContext = context;
|
||||
mMetricsFeatureProvider = FeatureFactory.getFactory(context).getMetricsFeatureProvider();
|
||||
mActivityManager = (ActivityManager) context.getSystemService(
|
||||
Context.ACTIVITY_SERVICE);
|
||||
mPackageManager = context.getPackageManager();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -52,6 +60,18 @@ public class ForceStopAction implements AnomalyAction {
|
||||
mActivityManager.forceStopPackage(packageName);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActionActive(Anomaly anomaly) {
|
||||
try {
|
||||
ApplicationInfo info = mPackageManager.getApplicationInfo(anomaly.packageName,
|
||||
PackageManager.GET_META_DATA);
|
||||
return (info.flags & ApplicationInfo.FLAG_STOPPED) == 0;
|
||||
} catch (PackageManager.NameNotFoundException e) {
|
||||
Log.e(TAG, "Cannot find info for app: " + anomaly.packageName);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getActionType() {
|
||||
return Anomaly.AnomalyActionType.FORCE_STOP;
|
||||
|
@@ -17,14 +17,11 @@
|
||||
package com.android.settings.fuelgauge.anomaly.checker;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.pm.ApplicationInfo;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.os.BatteryStats;
|
||||
import android.os.SystemClock;
|
||||
import android.support.annotation.VisibleForTesting;
|
||||
import android.text.format.DateUtils;
|
||||
import android.util.ArrayMap;
|
||||
import android.util.Log;
|
||||
|
||||
import com.android.internal.os.BatterySipper;
|
||||
import com.android.internal.os.BatteryStatsHelper;
|
||||
@@ -32,6 +29,8 @@ import com.android.settings.Utils;
|
||||
import com.android.settings.fuelgauge.BatteryUtils;
|
||||
import com.android.settings.fuelgauge.anomaly.Anomaly;
|
||||
import com.android.settings.fuelgauge.anomaly.AnomalyDetectionPolicy;
|
||||
import com.android.settings.fuelgauge.anomaly.AnomalyUtils;
|
||||
import com.android.settings.fuelgauge.anomaly.action.AnomalyAction;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
@@ -47,6 +46,8 @@ public class WakeLockAnomalyDetector implements AnomalyDetector {
|
||||
BatteryUtils mBatteryUtils;
|
||||
@VisibleForTesting
|
||||
long mWakeLockThresholdMs;
|
||||
@VisibleForTesting
|
||||
AnomalyAction mAnomalyAction;
|
||||
|
||||
public WakeLockAnomalyDetector(Context context) {
|
||||
this(context, new AnomalyDetectionPolicy(context));
|
||||
@@ -57,6 +58,8 @@ public class WakeLockAnomalyDetector implements AnomalyDetector {
|
||||
mContext = context;
|
||||
mPackageManager = context.getPackageManager();
|
||||
mBatteryUtils = BatteryUtils.getInstance(context);
|
||||
mAnomalyAction = AnomalyUtils.getInstance(context).getAnomalyAction(
|
||||
Anomaly.AnomalyType.WAKE_LOCK);
|
||||
|
||||
mWakeLockThresholdMs = policy.wakeLockThreshold;
|
||||
}
|
||||
@@ -111,7 +114,10 @@ public class WakeLockAnomalyDetector implements AnomalyDetector {
|
||||
.setDisplayName(displayName)
|
||||
.setPackageName(packageName)
|
||||
.build();
|
||||
anomalies.add(anomaly);
|
||||
|
||||
if (mAnomalyAction.isActionActive(anomaly)) {
|
||||
anomalies.add(anomaly);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
@@ -17,9 +17,7 @@
|
||||
package com.android.settings.fuelgauge.anomaly.checker;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.os.BatteryStats;
|
||||
import android.os.SystemClock;
|
||||
import android.support.annotation.VisibleForTesting;
|
||||
import android.text.format.DateUtils;
|
||||
import android.util.ArrayMap;
|
||||
@@ -30,6 +28,8 @@ import com.android.settings.Utils;
|
||||
import com.android.settings.fuelgauge.BatteryUtils;
|
||||
import com.android.settings.fuelgauge.anomaly.Anomaly;
|
||||
import com.android.settings.fuelgauge.anomaly.AnomalyDetectionPolicy;
|
||||
import com.android.settings.fuelgauge.anomaly.AnomalyUtils;
|
||||
import com.android.settings.fuelgauge.anomaly.action.AnomalyAction;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
@@ -41,6 +41,8 @@ public class WakeupAlarmAnomalyDetector implements AnomalyDetector {
|
||||
private static final String TAG = "WakeupAlarmAnomalyDetector";
|
||||
@VisibleForTesting
|
||||
BatteryUtils mBatteryUtils;
|
||||
@VisibleForTesting
|
||||
AnomalyAction mAnomalyAction;
|
||||
private long mWakeupAlarmThreshold;
|
||||
private Context mContext;
|
||||
|
||||
@@ -52,6 +54,8 @@ public class WakeupAlarmAnomalyDetector implements AnomalyDetector {
|
||||
WakeupAlarmAnomalyDetector(Context context, AnomalyDetectionPolicy policy) {
|
||||
mContext = context;
|
||||
mBatteryUtils = BatteryUtils.getInstance(context);
|
||||
mAnomalyAction = AnomalyUtils.getInstance(context).getAnomalyAction(
|
||||
Anomaly.AnomalyType.WAKEUP_ALARM);
|
||||
mWakeupAlarmThreshold = policy.wakeupAlarmThreshold;
|
||||
}
|
||||
|
||||
@@ -91,7 +95,10 @@ public class WakeupAlarmAnomalyDetector implements AnomalyDetector {
|
||||
.setDisplayName(displayName)
|
||||
.setPackageName(packageName)
|
||||
.build();
|
||||
anomalies.add(anomaly);
|
||||
|
||||
if (mAnomalyAction.isActionActive(anomaly)) {
|
||||
anomalies.add(anomaly);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -16,6 +16,8 @@
|
||||
|
||||
package com.android.settings.fuelgauge.anomaly.action;
|
||||
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
|
||||
import static org.mockito.Mockito.doReturn;
|
||||
import static org.mockito.Mockito.verify;
|
||||
|
||||
@@ -69,4 +71,20 @@ public class BackgroundCheckActionTest {
|
||||
verify(mAppOpsManagerr).setMode(AppOpsManager.OP_RUN_IN_BACKGROUND, UID, PACKAGE_NAME,
|
||||
AppOpsManager.MODE_IGNORED);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIsActionActive_modeAllowed_returnTrue() {
|
||||
doReturn(AppOpsManager.MODE_ALLOWED).when(mAppOpsManagerr).checkOpNoThrow(
|
||||
AppOpsManager.OP_RUN_IN_BACKGROUND, UID, PACKAGE_NAME);
|
||||
|
||||
assertThat(mBackgroundCheckAction.isActionActive(mAnomaly)).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIsActionActive_modeIgnored_returnFalse() {
|
||||
doReturn(AppOpsManager.MODE_IGNORED).when(mAppOpsManagerr).checkOpNoThrow(
|
||||
AppOpsManager.OP_RUN_IN_BACKGROUND, UID, PACKAGE_NAME);
|
||||
|
||||
assertThat(mBackgroundCheckAction.isActionActive(mAnomaly)).isFalse();
|
||||
}
|
||||
}
|
||||
|
@@ -16,11 +16,15 @@
|
||||
|
||||
package com.android.settings.fuelgauge.anomaly.action;
|
||||
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
|
||||
import static org.mockito.Mockito.doReturn;
|
||||
import static org.mockito.Mockito.verify;
|
||||
|
||||
import android.app.ActivityManager;
|
||||
import android.content.Context;
|
||||
import android.content.pm.ApplicationInfo;
|
||||
import android.content.pm.PackageManager;
|
||||
|
||||
import com.android.settings.testutils.SettingsRobolectricTestRunner;
|
||||
import com.android.settings.TestConfig;
|
||||
@@ -44,15 +48,22 @@ public class ForceStopActionTest {
|
||||
private Context mContext;
|
||||
@Mock
|
||||
private ActivityManager mActivityManager;
|
||||
@Mock
|
||||
private ApplicationInfo mApplicationInfo;
|
||||
@Mock
|
||||
private PackageManager mPackageManager;
|
||||
private Anomaly mAnomaly;
|
||||
private ForceStopAction mForceStopAction;
|
||||
|
||||
@Before
|
||||
public void setUp() {
|
||||
public void setUp() throws Exception {
|
||||
MockitoAnnotations.initMocks(this);
|
||||
|
||||
FakeFeatureFactory.setupForTest(mContext);
|
||||
doReturn(mActivityManager).when(mContext).getSystemService(Context.ACTIVITY_SERVICE);
|
||||
doReturn(mPackageManager).when(mContext).getPackageManager();
|
||||
doReturn(mApplicationInfo).when(mPackageManager).getApplicationInfo(PACKAGE_NAME,
|
||||
PackageManager.GET_META_DATA);
|
||||
|
||||
mAnomaly = new Anomaly.Builder()
|
||||
.setPackageName(PACKAGE_NAME)
|
||||
@@ -66,4 +77,18 @@ public class ForceStopActionTest {
|
||||
|
||||
verify(mActivityManager).forceStopPackage(PACKAGE_NAME);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIsActionActive_appStopped_returnFalse() {
|
||||
mApplicationInfo.flags = ApplicationInfo.FLAG_STOPPED;
|
||||
|
||||
assertThat(mForceStopAction.isActionActive(mAnomaly)).isFalse();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIsActionActive_appRunning_returnTrue() {
|
||||
mApplicationInfo.flags = 0;
|
||||
|
||||
assertThat(mForceStopAction.isActionActive(mAnomaly)).isTrue();
|
||||
}
|
||||
}
|
||||
|
@@ -19,6 +19,7 @@ package com.android.settings.fuelgauge.anomaly.checker;
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
|
||||
import static org.mockito.ArgumentMatchers.nullable;
|
||||
import static org.mockito.Matchers.any;
|
||||
import static org.mockito.Matchers.anyInt;
|
||||
import static org.mockito.Matchers.anyLong;
|
||||
import static org.mockito.Matchers.eq;
|
||||
@@ -39,6 +40,7 @@ import com.android.settings.TestConfig;
|
||||
import com.android.settings.fuelgauge.BatteryUtils;
|
||||
import com.android.settings.fuelgauge.anomaly.Anomaly;
|
||||
import com.android.settings.fuelgauge.anomaly.AnomalyDetectionPolicy;
|
||||
import com.android.settings.fuelgauge.anomaly.action.AnomalyAction;
|
||||
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
@@ -96,6 +98,8 @@ public class WakeLockAnomalyDetectorTest {
|
||||
private ApplicationInfo mApplicationInfo;
|
||||
@Mock
|
||||
private AnomalyDetectionPolicy mPolicy;
|
||||
@Mock
|
||||
private AnomalyAction mAnomalyAction;
|
||||
|
||||
private ArrayMap<String, BatteryStats.Uid.Wakelock> mAnomalyWakelocks;
|
||||
private ArrayMap<String, BatteryStats.Uid.Wakelock> mNormalWakelocks;
|
||||
@@ -115,6 +119,7 @@ public class WakeLockAnomalyDetectorTest {
|
||||
doReturn(mPackageManager).when(mContext).getPackageManager();
|
||||
doReturn(mApplicationInfo).when(mPackageManager)
|
||||
.getApplicationInfo(nullable(String.class), anyInt());
|
||||
doReturn(true).when(mAnomalyAction).isActionActive(any());
|
||||
|
||||
mAnomalySipper.uidObj = mAnomalyUid;
|
||||
mAnomalyWakelocks = new ArrayMap<>();
|
||||
@@ -145,6 +150,7 @@ public class WakeLockAnomalyDetectorTest {
|
||||
|
||||
mWakelockAnomalyDetector = spy(new WakeLockAnomalyDetector(mContext, mPolicy));
|
||||
mWakelockAnomalyDetector.mBatteryUtils = mBatteryUtils;
|
||||
mWakelockAnomalyDetector.mAnomalyAction = mAnomalyAction;
|
||||
doReturn(ANOMALY_WAKELOCK_TIME_MS).when(mWakelockAnomalyDetector).getTotalDurationMs(
|
||||
eq(mAnomalyTimer), anyLong());
|
||||
doReturn(ANOMALY_WAKELOCK_TIME_MS).when(mWakelockAnomalyDetector).getTotalDurationMs(
|
||||
|
@@ -38,6 +38,7 @@ import com.android.settings.TestConfig;
|
||||
import com.android.settings.fuelgauge.BatteryUtils;
|
||||
import com.android.settings.fuelgauge.anomaly.Anomaly;
|
||||
import com.android.settings.fuelgauge.anomaly.AnomalyDetectionPolicy;
|
||||
import com.android.settings.fuelgauge.anomaly.action.AnomalyAction;
|
||||
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
@@ -85,6 +86,8 @@ public class WakeupAlarmAnomalyDetectorTest {
|
||||
private BatteryStats.Counter mCounter;
|
||||
@Mock
|
||||
private AnomalyDetectionPolicy mPolicy;
|
||||
@Mock
|
||||
private AnomalyAction mAnomalyAction;
|
||||
|
||||
private WakeupAlarmAnomalyDetector mWakeupAlarmAnomalyDetector;
|
||||
private Context mContext;
|
||||
@@ -100,6 +103,7 @@ public class WakeupAlarmAnomalyDetectorTest {
|
||||
doReturn(false).when(mBatteryUtils).shouldHideSipper(any());
|
||||
doReturn(RUNNING_TIME_MS).when(mBatteryUtils).calculateRunningTimeBasedOnStatsType(any(),
|
||||
anyInt());
|
||||
doReturn(true).when(mAnomalyAction).isActionActive(any());
|
||||
|
||||
mAnomalySipper.uidObj = mAnomalyUid;
|
||||
doReturn(ANOMALY_UID).when(mAnomalyUid).getUid();
|
||||
@@ -116,6 +120,7 @@ public class WakeupAlarmAnomalyDetectorTest {
|
||||
|
||||
mWakeupAlarmAnomalyDetector = spy(new WakeupAlarmAnomalyDetector(mContext, mPolicy));
|
||||
mWakeupAlarmAnomalyDetector.mBatteryUtils = mBatteryUtils;
|
||||
mWakeupAlarmAnomalyDetector.mAnomalyAction = mAnomalyAction;
|
||||
}
|
||||
|
||||
@Test
|
||||
|
Reference in New Issue
Block a user