Как настроить WireMock, чтобы он сохранял все заглушки в MongoDB?
Всем привет. Я использую в проекте WireMock от tomakehurst вместе с Spring Boot. Я нашёл информацию как можно задать новый MappingsSource для заглушек, чтобы они сохранялись в БД, но это решение работает только, если запускать сервер вручную через WireMockServer. То есть просто создать свою реализацию MappingsSource и написать нечто вроде такого
new WireMockServer(
WireMockConfiguration.wireMockConfig()
.port(mockConfiguration.getPort())
.mappingSource(new S3MappingSource());
Но Spring Boot сам стартует данный сервер (точнее не совсем сам, а с помощью WireMockHandlerDispatchingServlet, который передается в ServletRegistrationBean и внедряется в контекст Spring) и как в него передать свой собственный MappingsSource я не знаю. Может быть я вообще смотрю не в том направлении( Основная цель: реализовать хранение заглушек не в памяти, а в базе данных, чтобы после перезапуска сервера, они подгружались от туда и не удалялись. Может быть кто-то работал с ним и сможет помочь?
Вот класс приложения, в котором создаются бины для WireMock'а:
@Slf4j
@EnableSwagger2
@SpringBootApplication(scanBasePackages = "ru.ttt.test.at.mock")
public class MockApplication {
private static final String APP_CONTEXT_KEY = "WireMockApp";
private final TypeResolver typeResolver;
private final ServletContext context;
@Autowired
public MockApplication(TypeResolver typeResolver, ServletContext context) {
this.typeResolver = typeResolver;
this.context = context;
}
public static void main(String[] args) {
Velocity.init(getVelocityProperties());
SpringApplication.run(new Class[]{MockApplication.class, SpringWebConfig.class}, args);
}
private static Properties getVelocityProperties() {
final Properties properties = new Properties();
final String directives = Stream.of(XPathDirective.class, GroovyDirective.class)
.map(Class::getName)
.collect(Collectors.joining(","));
properties.setProperty("userdirective", directives);
properties.setProperty(RuntimeConstants.RESOURCE_LOADER, "file");
properties.setProperty(RuntimeConstants.FILE_RESOURCE_LOADER_PATH, "." + File.separator + "velocity");
try (final InputStream stream = Files.newInputStream(Paths.get(VELOCITY_PROPERTIES.getValue()))) {
properties.load(stream);
} catch (Exception e) {
log.warn("Error while loading properties: {}. Using default values", e.getMessage());
}
return properties;
}
@Bean
public FilterRegistrationBean corsFilter() {
FilterRegistrationBean filter = new FilterRegistrationBean(new CorsFilter());
filter.addUrlPatterns("/*");
filter.setOrder(1);
return filter;
}
@Bean
public FilterRegistrationBean convertFilter(BinaryBase64ConvertFilter convertFilter) {
FilterRegistrationBean filter = new FilterRegistrationBean(convertFilter);
filter.addUrlPatterns("/*");
filter.setOrder(2);
return filter;
}
@Bean
@Autowired
public WireMockApp wireMockApp(WarConfiguration configuration) {
WireMockApp wireMockApp = new WireMockApp(configuration, new NotImplementedContainer());
context.setAttribute(APP_CONTEXT_KEY, wireMockApp);
context.setAttribute(StubRequestHandler.class.getName(), wireMockApp.buildStubRequestHandler());
context.setAttribute(AdminRequestHandler.class.getName(), wireMockApp.buildAdminRequestHandler());
context.setAttribute(Notifier.KEY, new Slf4jNotifier(false));
context.setAttribute(MultipartRequestConfigurer.KEY, new DefaultMultipartRequestConfigurer());
return wireMockApp;
}
@Bean
@Autowired
public WarConfiguration customWarConfiguration(ResponseDefinitionTransformer responseTransformer) {
return new CustomWarConfiguration(context, "wiremock", responseTransformer);
}
@Bean
@Autowired
public ResponseDefinitionTransformer responseTransformer(MqProperties properties) {
return new CustomVelocityResponseTransformer(properties);
}
@Bean
public ServletRegistrationBean wiremockAdminHandlerBean() {
ServletRegistrationBean bean = new ServletRegistrationBean(new WireMockHandlerDispatchingServlet(), "/__admin/*");
bean.addInitParameter("RequestHandlerClass", AdminRequestHandler.class.getName());
bean.setLoadOnStartup(1);
bean.setName("wiremockAdmin");
return bean;
}
@Bean
public ServletRegistrationBean wiremockMockHandlerBean() {
Servlet servlet = new WireMockHandlerDispatchingServlet();
ServletRegistrationBean bean = new ServletRegistrationBean(servlet, "/wire-mock/*");
bean.addInitParameter("RequestHandlerClass", StubRequestHandler.class.getName());
bean.addInitParameter(WireMockHandlerDispatchingServlet.MAPPED_UNDER_KEY, "/wire-mock/");
bean.setLoadOnStartup(1);
bean.setName("wiremockStub");
return bean;
}
@Bean
public Docket wiremockApi() {
return new Docket(DocumentationType.SWAGGER_2)
.select()
.apis(RequestHandlerSelectors.any())
//.paths(PathSelectors.regex(".*__admin.*"))
.build()
.pathMapping("/")
.directModelSubstitute(LocalDate.class,
String.class)
.alternateTypeRules(
newRule(typeResolver.resolve(DeferredResult.class,
typeResolver.resolve(ResponseEntity.class, WildcardType.class)),
typeResolver.resolve(WildcardType.class)))
.useDefaultResponseMessages(false)
.globalResponseMessage(RequestMethod.GET,
newArrayList(new ResponseMessageBuilder()
.code(500)
.message("Http error 500")
.build()))
.enableUrlTemplating(true);
}
@Bean
public RestTemplate restTemplate() {
return new RestTemplate();
}
}