如何在@PostConstruct之前调用@BeforeMethod块

时间:2019-05-13 05:50:00

标签: java spring spring-test-mvc

我正在下面的Spring Unit测试代码中编写代码。单元测试@Before方法未执行。由于它直接运行@PostConstruct,因此我得到了错误Caused by: java.lang.IllegalArgumentException: rate must be positive,因为默认值为0.00。我想设置一些值来请求最大限制,以便postcontstruct块可以顺利通过。我的代码有什么问题?请帮忙。

@Component
public class SurveyPublisher  {

    @Autowired
    private SurveyProperties surveyProperties;

    @PostConstruct
        public void init() {
            rateLimiter = RateLimiter.create(psurveyProperties.getRequestMaxLimit());
        }

    }

    public void publish() {
        rateLimiter.acquire();
        // do something
    }

}

//单元测试类

public class SurveyPublisherTest  extends AbstractTestNGSpringContextTests {

    @Mock
    SurveyProperties surveyProperties;

    @BeforeMethod   
    public void init() {
        Mockito.when(surveyProperties.getRequestMaxLimit()).thenReturn(40.00);
    }

    @Test
    public void testPublish_noResponse() {
        //do some test
    }

}

2 个答案:

答案 0 :(得分:1)

仅意识到在Junit回调方法导致spring优先之前,它将始终运行postConstruct方法。如文档中所述-

  

如果测试类中的方法使用@PostConstruct注释,则   方法在基础测试框架的所有before方法之前运行   (例如,使用JUnit Jupiter的@BeforeEach注释的方法),以及   适用于测试类中的每种测试方法。

为您解决的问题-

  1. 正如@chrylis上面所评论的那样,重构您的SurveyPublisher以使用构造函数注入来注入速率限制器。这样您就可以轻松进行测试了。
  2. 注入引起问题的模拟/间谍豆
  3. 创建测试配置,以为您提供要用作@ContextConfiguration

    的类的实例
    @Configuration
    public class YourTestConfig {
    
        @Bean
        FactoryBean getSurveyPublisher() {
            return new AbstractFactoryBean() {
                @Override
                public Class getObjectType() {
                    return SurveyPublisher.class;
                }
    
                @Override
                protected SurveyPublisher createInstance() {
                    return mock(SurveyPublisher.class);
                }
            };
        }
    }
    

答案 1 :(得分:0)

这是简单的一种。

@Configuration
@EnableConfigurationProperties(SurveyProperties.class)
    static class Config {
}


@ContextConfiguration(classes = {
        SurveyPublisherTest.Config.class })
@TestPropertySource(properties = { "com.test.survey.request-max-limit=1.00" })
public class SurveyPublisherTest extends AbstractTestNGSpringContextTests {

//Remove this mock
//@Mock
//SurveyProperties surveyProperties;
}