Android 应用单元测试涉及 Telephony 环境初始化问题
Telephony 相关类注入问题
SubscriptionManager
Cannot invoke "android.telephony.SubscriptionManager.getActiveSubscriptionInfoList()" because "this.mSubscriptionManager" is null
java.lang.NullPointerException: Cannot invoke "android.telephony.SubscriptionManager.getActiveSubscriptionInfoList()" because "this.mSubscriptionManager" is null
at com.demo.settings.util.SimHotSwapHandler.<init>(SimHotSwapHandler.java:32)
错误初始化方法,因为when不能传入非mock对象,是因为context没有mock初始化
@Beforepublic void setUp() {// 将mock的SubscriptionManager与测试环境中Context的系统服务绑定when(mockContext.getSystemService(Context.TELEPHONY_SUBSCRIPTION_SERVICE)).thenReturn(mockSubscriptionManager);}
正常setup的方法:
import org.robolectric.RobolectricTestRunner;
import org.robolectric.RuntimeEnvironment;
import org.robolectric.annotation.Config;
import org.robolectric.shadows.ShadowApplication;
import org.robolectric.shadows.ShadowSubscriptionManager;@RunWith(RobolectricTestRunner.class)
@Config(sdk = {33})
public class Test {@Mockprivate Context mockContext;@Mockprivate SubscriptionManager mockSubscriptionManager;@Mockprivate SubscriptionInfo mockSubscriptionInfo1;@Mockprivate SubscriptionInfo mockSubscriptionInfo2;@Beforepublic void setUp() {MockitoAnnotations.openMocks(this);// 初始化使用Mock的ContextmockContext = mock(Context.class);when(mockContext.getSystemService(Context.TELEPHONY_SUBSCRIPTION_SERVICE)).thenReturn(mockSubscriptionManager);}}
PersistableBundle
Cannot invoke "android.os.PersistableBundle.getBoolean(String)" because "b" is null
java.lang.NullPointerException: Cannot invoke "android.os.PersistableBundle.getBoolean(String)" because "b" is null
Android 环境相关
Context 初始化
在单元测试 setup 过程经常会有处理 context 的值,必要吗?也看到了很多不初始化的案例,是Mockit 已经处理了是吗?但是不初始化也会报资源错误,当设置资源的时候。
Cannot invoke "android.content.Context.getResources()" because "this.mContext" is null
java.lang.NullPointerException: Cannot invoke "android.content.Context.getResources()" because "this.mContext" is null
常见的初始化有几种,有什么差异区别?
- RuntimeEnvironment
- ApplicationProvder
- mock()
以下是使用 RobolectricTestRunner 的一些案例。
案例1、RuntimeEnvironment
局部变量,模拟系统服务
@Beforepublic void setUp() {Context context = RuntimeEnvironment.application;}