我正在使用spring-data-rest-webmvc:jar:2.5.3.RELEASE来编写REST API并在springfox-data-rest-2.6.0中呈现资源。招摇使得所有方法都存在于RestEntityController
中。我使用@RestResource(exported = false)
在存储库级别中排除了一些方法。但是,swagger加载了所有其他HTTP方法,如OPTIONS,HEAD和PATCH,我无法从RepositoryRestResource
中排除。
如何使用仅包含我的CRUD和搜索方法的干净资源渲染我的招摇?需要在使用spring-data-rest配置或使用springfox配置时支持此功能。
答案 0 :(得分:5)
在深入研究springfox文档并放弃一些死胡同的想法之后,我想出了两个可能解决您问题的解决方案。根据您的需要涂抹并混合。
提示#1 - 使用RequestHandlerSelectors
告诉springfox你想在swagger-ui中显示哪些方法端点。因此,您可以设置RequestHandlerSelector
来扫描您的整个应用程序,一个特定的包或您使用共享注释注释的类和方法。
//Example for the method scan based on springfox's @ApiOperation annotation
@Bean
public Docket api() {
return new Docket(DocumentationType.SWAGGER_2)
.select()
.apis(RequestHandlerSelectors.withMethodAnnotation(ApiOperation.class)).paths(PathSelectors.any())
.build();
}
// Within your dao or repository class
public interface QueuedMessageDao extends CrudRepository<QueuedMessage, Integer> {
@ApiOperation(value = "This method finds all messages that are queued with the recipient's email address")
List<QueuedMessage> findByRecipientEmail(String email);
}
这会从你的招摇文档中切断很多弹簧数据休息开销。但是,您仍会(令人惊讶地)在您的swagger-ui中看到不需要的HTTP方法,例如技术GET
端点的HEAD
,OPTIONS
和/<entity>/search
方法。我说技术,因为这些端点只是为了发现其他端点,它们不会为您提供来自实体的数据。
提示#2 - 使用PathSelectors
如果您想要摆脱swagger中的技术/<entity>/search
端点,可以使用正则表达式排除它们,过滤掉所有搜索端点,但保留与您相关的端点。要在实体中仍然拥有搜索的业务端点,您只需要设置一个隐式GET端点。
//Example for the method scan based on springfox's @ApiOperation annotation
@Bean
public Docket api() {
return new Docket(DocumentationType.SWAGGER_2)
.select()
.apis(RequestHandlerSelectors.withMethodAnnotation(ApiOperation.class)).paths(PathSelectors.regex("^(?!(/.*(/search)$)).*$"))
.build();
}
// Within your dao or repository class
public interface QueuedMessageDao extends CrudRepository<QueuedMessage, Integer> {
@ApiOperation(value = "this generates a business search endpoint")
List<QueuedMessage> findById(int id);
@ApiOperation(value = "This method finds all messages that are queued with the recipient's email address")
List<QueuedMessage> findByRecipientEmail(String email);
}
现在你摆脱了搜索端点,但仍然在你的招摇文档中进行业务搜索。 希望这有帮助!
答案 1 :(得分:2)
我遇到了和你一样的问题,我只想通过Swagger UI向我的客户展示CRUD操作。在深入研究Springfox文档之后,我创建了自己的谓词来过滤端点,仅用于CRUD操作,检查所请求的方法。
@Bean
public Docket api() {
return new Docket(DocumentationType.SWAGGER_2)
.select()
.apis(customRequestHandlers())
.build();
}
private Predicate<RequestHandler> customRequestHandlers() {
return new Predicate<RequestHandler>() {
@Override
public boolean apply(RequestHandler input) {
Set<RequestMethod> methods = input.supportedMethods();
return methods.contains(RequestMethod.GET)
|| methods.contains(RequestMethod.POST)
|| methods.contains(RequestMethod.PUT)
|| methods.contains(RequestMethod.DELETE);
}
};
}
答案 2 :(得分:1)
创建自定义拦截器:
public class MyInterceptor extends HandlerInterceptorAdapter{
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
//let's disable OPTIONS and HEAD
if (request.getMethod().equalsIgnoreCase("OPTIONS") || request.getMethod().equalsIgnoreCase("HEAD")) {
response.sendError(HttpServletResponse.SC_FORBIDDEN, "Unauthorized Request");
return false;
} else {
return true;
}
}
}
然后将其添加到配置
@Configuration
@EnableWebMvc
public class AppConfig extends WebMvcConfigurerAdapter {
@Override
public void addInterceptors(InterceptorRegistry registry){
registry.addInterceptor(new MyInterceptor()).addPathPatterns("/**");
}
}
答案 3 :(得分:0)
使用SpringPox排除特定的HttpMethods非常简单,它的ApiSelectorBuilder接受Guavas Predicates。
此代码段将排除api-docs和swagger-ui.html中OPTIONS,HEAD或PATCH的所有方法。
@Bean
public Docket api() {
return new Docket(DocumentationType.SWAGGER_2)
.select()
.apis(Predicates.not(requestHandler -> {
// exclude all methods being OPTIONS, HEAD or PATCH
final Set<RequestMethod> methods = requestHandler.getRequestMapping().getMethodsCondition().getMethods();
return !Collections.disjoint(methods, Arrays.asList(RequestMethod.OPTIONS, RequestMethod.HEAD, RequestMethod.PATCH));
}))
.build();
}
这可以轻松扩展为另外排除常见/错误控制器。
@Bean
public Docket api() {
return new Docket(DocumentationType.SWAGGER_2)
.select()
.apis(Predicates
.and(
// exclude /errors
Predicates.not(requestHandler -> requestHandler.getRequestMapping().getPatternsCondition().getPatterns().contains("/error")),
// exclude all methods being OPTIONS, HEAD or PATCH
Predicates.not(requestHandler -> !Collections.disjoint(requestHandler.getRequestMapping().getMethodsCondition().getMethods(),
Arrays.asList(RequestMethod.OPTIONS, RequestMethod.HEAD, RequestMethod.PATCH)))
)
)
.build();
}
答案 4 :(得分:0)
对于spring数据,我们可以在此处过滤http方法:
private Predicate<RequestHandler> httpRequestHandler() {
return p -> p.supportedMethods().contains(RequestMethod.GET)
|| p.supportedMethods().contains(RequestMethod.POST);
}
@Bean
public Docket api() {
return new Docket(DocumentationType.SWAGGER_2)
.groupName("test-api")
.apiInfo(apiInfo())
.select()
.apis(httpRequestHandler())
.paths(PathSelectors.any()).build()
.securitySchemes(Arrays.asList(securityScheme()))
.securityContexts(Arrays.asList(securityContext()));
}