如何测试需要授权的屏幕?浓缩咖啡 + MockWebServer
How to test screens which requires authorization? Espresso + MockWebServer
我正在创建 UI 测试。为了不和真正的服务器交互,我使用了MockWebServer。我的目标是模拟各种服务器响应并查看整个程序将如何响应它们。目前,我不明白如何打开需要授权的屏幕。当然,我可以写一个代码,登录到授权屏幕,然后去想要的window。但这需要额外的时间来完成测试,我想避免这种情况。我不想模拟 classes,因为我需要检查应用程序的生产版本。我该怎么做?
对于 DI,我使用 Dagger-2。这是组件代码:
@Singleton
@Component(modules = {
AvatarsModule.class,
EncryptionModule.class,
ApiModule.class,
WalletsModule.class,
GeneralModule.class,
InteractorsModule.class,
PushNotificationsModule.class,
AppModule.class
})
public interface AppComponent {
@Component.Builder
interface Builder {
@BindsInstance
Builder context(Context context);
AppComponent build();
}
void inject(App app);
}
这是存储授权状态的 class 代码:
public class ApiWrapper {
private Api api;
private KeyPair keyPair;
private Account account;
...
public Flowable<Authorization> authorize(KeyPair tempKeyPair) {
return api
.authorize(tempKeyPair.getPublicKeyString().toLowerCase())
.subscribeOn(Schedulers.io())
.doOnNext((authorization -> {
this.account = authorization.getAccount();
this.keyPair = tempKeyPair;
}));
}
...
}
如果还有人感兴趣。我写了一个 InstrumentationTestFacade class,其中我使用 Dagger 放置了一个 ApiWrapper 对象。接下来,将 InstrumentationTestFacade 注入到 Application 对象中。由于应用程序对象不是单例,因此主要代码中没有责任泄漏,但是从测试代码中您可以使用以下代码访问此外观:
Application application = (Application) InstrumentationRegistry.getInstrumentation().getTargetContext().getApplicationContext();
InstrumentationTestFacade facade = application.getInstrumentationTestFacade();
下面是一个例子:
public class InstrumentationTestFacade {
private LogoutInteractor logoutInteractor;
private SecurityInteractor securityInteractor;
private ApiWrapper apiWrapper;
public InstrumentationTestFacade(
LogoutInteractor logoutInteractor,
SecurityInteractor securityInteractor,
ApiWrapper apiWrapper
) {
this.logoutInteractor = logoutInteractor;
this.securityInteractor = securityInteractor;
this.apiWrapper = apiWrapper;
}
public void logout() {
logoutInteractor.logout();
}
public ApiWrapper getApiWrapper() {
return apiWrapper;
}
public SecurityInteractor getSecurityInteractor() {
return this.securityInteractor;
}
}
public class Application extends MultiDexApplication implements HasActivityInjector, HasServiceInjector {
...
@Inject
InstrumentationTestFacade instrumentationTestFacade;
@Override
public void onCreate() {
super.onCreate();
DaggerAppComponent
.builder()
.context(this)
.build()
.inject(this);
}
...
public InstrumentationTestFacade getInstrumentationTestFacade() {
return instrumentationTestFacade;
}
}
我正在创建 UI 测试。为了不和真正的服务器交互,我使用了MockWebServer。我的目标是模拟各种服务器响应并查看整个程序将如何响应它们。目前,我不明白如何打开需要授权的屏幕。当然,我可以写一个代码,登录到授权屏幕,然后去想要的window。但这需要额外的时间来完成测试,我想避免这种情况。我不想模拟 classes,因为我需要检查应用程序的生产版本。我该怎么做?
对于 DI,我使用 Dagger-2。这是组件代码:
@Singleton
@Component(modules = {
AvatarsModule.class,
EncryptionModule.class,
ApiModule.class,
WalletsModule.class,
GeneralModule.class,
InteractorsModule.class,
PushNotificationsModule.class,
AppModule.class
})
public interface AppComponent {
@Component.Builder
interface Builder {
@BindsInstance
Builder context(Context context);
AppComponent build();
}
void inject(App app);
}
这是存储授权状态的 class 代码:
public class ApiWrapper {
private Api api;
private KeyPair keyPair;
private Account account;
...
public Flowable<Authorization> authorize(KeyPair tempKeyPair) {
return api
.authorize(tempKeyPair.getPublicKeyString().toLowerCase())
.subscribeOn(Schedulers.io())
.doOnNext((authorization -> {
this.account = authorization.getAccount();
this.keyPair = tempKeyPair;
}));
}
...
}
如果还有人感兴趣。我写了一个 InstrumentationTestFacade class,其中我使用 Dagger 放置了一个 ApiWrapper 对象。接下来,将 InstrumentationTestFacade 注入到 Application 对象中。由于应用程序对象不是单例,因此主要代码中没有责任泄漏,但是从测试代码中您可以使用以下代码访问此外观:
Application application = (Application) InstrumentationRegistry.getInstrumentation().getTargetContext().getApplicationContext();
InstrumentationTestFacade facade = application.getInstrumentationTestFacade();
下面是一个例子:
public class InstrumentationTestFacade {
private LogoutInteractor logoutInteractor;
private SecurityInteractor securityInteractor;
private ApiWrapper apiWrapper;
public InstrumentationTestFacade(
LogoutInteractor logoutInteractor,
SecurityInteractor securityInteractor,
ApiWrapper apiWrapper
) {
this.logoutInteractor = logoutInteractor;
this.securityInteractor = securityInteractor;
this.apiWrapper = apiWrapper;
}
public void logout() {
logoutInteractor.logout();
}
public ApiWrapper getApiWrapper() {
return apiWrapper;
}
public SecurityInteractor getSecurityInteractor() {
return this.securityInteractor;
}
}
public class Application extends MultiDexApplication implements HasActivityInjector, HasServiceInjector {
...
@Inject
InstrumentationTestFacade instrumentationTestFacade;
@Override
public void onCreate() {
super.onCreate();
DaggerAppComponent
.builder()
.context(this)
.build()
.inject(this);
}
...
public InstrumentationTestFacade getInstrumentationTestFacade() {
return instrumentationTestFacade;
}
}