1 /* 2 * Copyright (C) 2023 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 package com.android.adservices.common; 17 18 import static org.mockito.Mockito.mock; 19 20 import android.Manifest; 21 import android.annotation.CallSuper; 22 import android.content.Context; 23 24 import androidx.test.platform.app.InstrumentationRegistry; 25 26 import com.android.adservices.flags.AdServicesFakeDebugFlagsSetterRule; 27 import com.android.adservices.flags.AdServicesFakeFlagsSetterRule; 28 import com.android.adservices.flags.AdServicesFlagsSetterRuleForUnitTests; 29 import com.android.adservices.service.DebugFlags; 30 import com.android.adservices.service.Flags; 31 import com.android.adservices.shared.testing.common.ApplicationContextSingletonRule; 32 import com.android.compatibility.common.util.AdoptShellPermissionsRule; 33 34 import org.junit.Rule; 35 36 /** 37 * Base class for all unit tests. 38 * 39 * <p>Contains only the bare minimum functionality required by them, like custom JUnit rules. 40 * 41 * <p>In fact, this class "reserves" the first 11 rules (as defined by order 0-10), so subclasses 42 * should start defining rules with {@code order = 11}. 43 */ 44 public abstract class AdServicesUnitTestCase extends AdServicesTestCase { 45 46 // NOTE: must be defined here (instead of on AdServicesMockerLessExtendedMockitoTestCase), 47 // otherwise it would be null when flags call newFlagsRule() below (and tests override that 48 // method to return AdServicesMockFlagsSetterRule) 49 /** 50 * @deprecated tests should use {@link AdServicesFakeFlagsSetterRule} instead. 51 */ 52 @Deprecated protected final Flags mMockFlags = mock(Flags.class); 53 54 private static final String APP_CONTEXT_MSG = "should use existing mAppContext instead"; 55 56 protected static final String FAKE_FLAGS_MSG = "should use mFakeFlags and flags rule insteads"; 57 58 @Rule(order = 5) 59 public final ApplicationContextSingletonRule appContext = 60 new ApplicationContextSingletonRule(/* restoreAfter= */ false); 61 62 @Rule(order = 6) 63 public final AdServicesFlagsSetterRuleForUnitTests<?, ? extends Flags> flags = newFlagsRule(); 64 65 @Rule(order = 7) 66 public final AdServicesFakeDebugFlagsSetterRule debugFlags = 67 new AdServicesFakeDebugFlagsSetterRule(); 68 69 @Rule(order = 8) 70 public final AdoptShellPermissionsRule mAdoptShellPermissionsRule = 71 new AdoptShellPermissionsRule( 72 InstrumentationRegistry.getInstrumentation().getUiAutomation(), 73 Manifest.permission.READ_DEVICE_CONFIG); 74 75 /** 76 * Reference to the application context of this test's instrumentation package (as defined by 77 * {@link android.app.Instrumentation#getContext()}. 78 * 79 * <p>In other words, it's the same as {@code mContext.getApplicationContext()}. 80 */ 81 protected final Context mAppContext = mContext.getApplicationContext(); 82 83 /** Stubbed {@link Flags} implementation that can be set by {@code flags}. */ 84 protected final Flags mFakeFlags = flags.getFlags(); 85 86 /** Stubbed {@link DebugFlags} implementation that can be set by {@code debugFlags}. */ 87 protected final DebugFlags mFakeDebugFlags = debugFlags.getDebugFlags(); 88 89 /** 90 * Creates the rule that will be referenced as {@code flags}. 91 * 92 * <p>Returns a new {@link AdServicesFakeFlagsSetterRule} by default, should be overridden by 93 * tests that want to use {@code AdServicesMockFlagsSetterRule} instead. 94 */ newFlagsRule()95 protected AdServicesFlagsSetterRuleForUnitTests<?, ? extends Flags> newFlagsRule() { 96 return new AdServicesFakeFlagsSetterRule(); 97 } 98 99 @CallSuper 100 @Override assertValidTestCaseFixtures()101 protected void assertValidTestCaseFixtures() throws Exception { 102 super.assertValidTestCaseFixtures(); 103 104 // TODO(b/388097793): add mLegacyFakeFlags once tests are refactored to not used it 105 assertTestClassHasNoFieldsFromSuperclass( 106 AdServicesUnitTestCase.class, 107 "mAppContext", 108 "appContext", 109 "flags", 110 "mMockFlags", 111 "mFakeFlags", 112 "debugFlags", 113 "mFakeDebugFlags"); 114 assertTestClassHasNoSuchField("APPLICATION_CONTEXT", APP_CONTEXT_MSG); 115 assertTestClassHasNoSuchField("mApplicationContext", APP_CONTEXT_MSG); 116 assertTestClassHasNoSuchField("FLAGS", FAKE_FLAGS_MSG); 117 // TODO(b/384798806): add a check prohibiting realFlags, which is currently using on some 118 // unit tests that "really" change the Flags using DeviceConfig - these tests should instead 119 // use AdServicesFakeFlagsSetterRule (which will eventually be provided by a superclass). 120 // We'll need to fix these test first (for example, some of them also set DebugFlags, which 121 // is not supported by AdServicesFakeFlagsSetterRule and won't be, as we should have a 122 // separate rule for DebugFlags / SystemProperties) 123 assertTestClassHasNoSuchField("mDebugFlags", REASON_USE_FAKE_DEBUG_FLAGS_INSTEAD); 124 } 125 } 126