单元测试RxJava组成和功能

时间:2017-03-10 22:32:53

标签: unit-testing rx-java

在我的架构中,我使用一个名为UseCase的类来组成一个observable并订阅它。 UseCase在构造函数中接受一个或多个存储库,并且有一个“execute”方法,负责创建observable并订阅它。

这是一个简单的例子;

public class MyUseCase {
    IRepoA mRepoA;
    IRepoB mRepoB;
    Scheduler mScheduleOn;
    Scheduler mObserveOn;
    CompositeSubscription mCompositeSubscription;

    public MyUseCase(IRepoA repoA, IRepoB repoB, Scheduler subscribeOn, Scheduler observeOn, CompositeSubscription compositeSubscription) {
    mRepoA = repoA;
    mRepoB = repoB;
    mSubscribeOn = subscribeOn;
    mObserveOn = observeOn;
    mCompositeSubscription = compositeSubscription;
}

public Observable execute(Observable observable, Subscriber subscriber) {
    if (observable == null) {
                     observable = mRepoA
                    .fetchLoginPreference()
                    .map(new Func1<LoginPreference, String>() {
                        @Override
                        public String call(LoginPreference loginPreference) {
                            return loginPreference.getActivationCode();
                        }
                    })
                    .flatMap(new Func1<String, Observable<List<RegistrationField>>>() {
                        @Override
                        public Observable<List<RegistrationField>> call(String s) {
                            return mRepoB.fetchRegistrationFields(s);
                        }
                    })
    }
    mCompositeSubscription.add(observable.subscribeOn(mSubscribeOn).observeOn(mObserveOn).subscribe(observable));
    return observable;
}
}

在我看来,这里有几件事要测试,我想知道最好的方法是什么。

1)我想测试observable是否正确组合。也就是说,我想确保调用.map(),. flattMap()和.cache()。之前我这样做的方法是使用模拟并验证这些方法是在模拟上调用的。因此,例如,repoA.fetchLoginPreference()将返回一个模拟observable,然后我可以验证模拟是否有.map()调用它等等。

2)我想测试observable在我订阅时实际上是否正常运行。为了测试这一点,我所做的就是使用真实的Observable而不是模拟。所以当repoA.fetchLoginPreference()被调用时,我会让它返回Observable.just(mockLoginPreference)。然后我使用TestSubscriber订阅生成的observable并验证是否在Func1回调中正确调用了模拟。

这看起来像是一种理智的做事方式吗?我最终能够测试组合是否正确,并验证当observable订阅它时它实际上做了它应该做的但是我很好奇是否有更好的方法。

1 个答案:

答案 0 :(得分:1)

当您学习RxJava的行为时,您的第一种方法会很有用,特别是对于switchMap()等更具异国情调的运算符。但是,您并不特别需要测试rxjava库本身的正确性。

第二种方法很有意义。拥有一个单元测试工具,它是模拟和可观察/测试用户的组合,是反应式编程的一个非常强大的功能。

话虽如此,在处理CompositeSubscription()时你可能需要两种方法,因为我认为它不会像你认为的那样做。将需要一些低级调试探针来确保在线程上完成操作