【问题标题】:Reactor StepVerifier test fails with blockFirst()Reactor StepVerifier 测试因 blockFirst() 而失败
【发布时间】:2019-01-08 22:11:37
【问题描述】:

这是检查数据库中重复名称的代码

public Mono<Void> validateDuplicateName(String name) throws RuntimeException {
    Flux<Customer> customerFlux = customerRepository.findByNameIgnoreCase(name);

    customerFlux.take(1).flatMap( customer -> {
        return Mono.error( new RuntimeException ("ABC99") );
    }).blockFirst();

    return Mono.empty();
}

下面是测试 validateDuplicateName 方法的测试脚本

when(customerRepositoryMocked.findByNameIgnoreCase(Mockito.anyString())).thenReturn(Flux.just(customerMocked));
StepVerifier.create(customerValidator.validateDuplicateName(Mockito.anyString()))
        .expectErrorMatches( exception -> exception instanceof RuntimeException )
        .verify();

但测试失败并出现以下错误

java.lang.RuntimeException: ABC99
..
..
Suppressed: java.lang.Exception: #block terminated with an error
        at reactor.core.publisher.BlockingSingleSubscriber.blockingGet(BlockingSingleSubscriber.java:93)
        at reactor.core.publisher.Flux.blockFirst(Flux.java:2013)
        ... 34 more

我能得到一些帮助吗?

【问题讨论】:

    标签: project-reactor


    【解决方案1】:

    你的StepVerifier实际上只能测试方法系统返回的Mono.empty()。同时,您使用blockFirst,它将抛出发布者发出的任何异常,从而使整个断言短路。

    记住StepVerifier 让您断言您期望序列异步发出的内容(包括错误,以onError 信号的形式)。如果因为创建它的方法(validateDuplicateName)抛出,甚至无法创建序列,那么StepVerifier是无能为力的。

    但真正的问题是到底为什么要阻塞在一个具有Mono 返回类型并且有一个非常好的Mono 源方便的方法中? 你的返回Mono 必须是源自customerFlux

    您可以使用then() 切换到Mono&lt;Void&gt;:这会忽略源的元素,但会正确传播错误。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-05-27
      • 2019-05-01
      • 2013-07-06
      • 2017-10-08
      相关资源
      最近更新 更多