Swagger documentation for Spring Pageable interface

34,916

Solution 1

This is a known issue with Spring-Fox. See Issue #755. Based on zdila's comment 2 at this time alternative is to add @ApiImplicitParams which is not ideal but it does work.

@ApiImplicitParams({
    @ApiImplicitParam(name = "page", dataType = "integer", paramType = "query",
            value = "Results page you want to retrieve (0..N)"),
    @ApiImplicitParam(name = "size", dataType = "integer", paramType = "query",
            value = "Number of records per page."),
    @ApiImplicitParam(name = "sort", allowMultiple = true, dataType = "string", paramType = "query",
            value = "Sorting criteria in the format: property(,asc|desc). " +
                    "Default sort order is ascending. " +
                    "Multiple sort criteria are supported.")
})

[Swagger UI showing @ApiImplicitParams for Pageable]

1 https://github.com/springfox/springfox/issues/755

2 https://github.com/springfox/springfox/issues/755#issuecomment-135059871

Solution 2

Building on Vineet Bhatia's answer, you can wrap the solution up in a custom annotation for reusability:

@Target({ ElementType.METHOD, ElementType.ANNOTATION_TYPE, ElementType.TYPE })
@Retention(RetentionPolicy.RUNTIME)
@ApiImplicitParams({
    @ApiImplicitParam(name = "page", dataType = "int", paramType = "query", value = "Results page you want to retrieve (0..N)"),
    @ApiImplicitParam(name = "size", dataType = "int", paramType = "query", value = "Number of records per page."),
    @ApiImplicitParam(name = "sort", allowMultiple = true, dataType = "string", paramType = "query", value = "Sorting criteria in the format: property(,asc|desc). "
            + "Default sort order is ascending. " + "Multiple sort criteria are supported.") })
@interface ApiPageable {
}

Which can then be used like so:

@ApiPageable
public Page<Data> getData(Pageable pageRequest) {

Solution 3

Vineet Bhatia's answer with @ApiImplicitParams looks fine. But I faced with situation, when @ApiIgnor and @ApiParam(hidden = true) doesn't work and you can still observe the asembler and pageable params. I fixed this problem by adding next line

docket.ignoredParameterTypes(Pageable.class, PagedResourcesAssembler.class);

to the Docket bean in my SwaggerConfig.

Solution 4

Java example:

Bean:

@Bean
public Docket api() {
    return new Docket(DocumentationType.SWAGGER_2)
        .select()
        .paths(PathSelectors.any())
        .build()
        .directModelSubstitute(Pageable.class, SwaggerPageable.class);
}

SwaggerPageable:

@Getter
private static class SwaggerPageable {

    @ApiParam(value = "Number of records per page", example = "0")
    @Nullable
    private Integer size;

    @ApiParam(value = "Results page you want to retrieve (0..N)", example = "0")
    @Nullable
    private Integer page;

    @ApiParam(value = "Sorting criteria in the format: property(,asc|desc). Default sort order is ascending. Multiple sort criteria are supported.")
    @Nullable
    private String sort;

}

Swagger:

enter image description here

Solution 5

Here is the version of the annotation that was integrated into springdoc-openapi-data-rest for OpenAPI v3:

@Target({ ElementType.METHOD, ElementType.ANNOTATION_TYPE })
@Retention(RetentionPolicy.RUNTIME)
@Parameter(in = ParameterIn.QUERY
        , description = "Zero-based page index (0..N)"
        , name = "page"
        , content = @Content(schema = @Schema(type = "integer", defaultValue = "0")))
@Parameter(in = ParameterIn.QUERY
        , description = "The size of the page to be returned"
        , name = "size"
        , content = @Content(schema = @Schema(type = "integer", defaultValue = "20")))
@Parameter(in = ParameterIn.QUERY
        , description = "Sorting criteria in the format: property(,asc|desc). "
        + "Default sort order is ascending. " + "Multiple sort criteria are supported."
        , name = "sort"
        , content = @Content(array = @ArraySchema(schema = @Schema(type = "string"))))
public @interface PageableAsQueryParam {

}

See https://springdoc.github.io/springdoc-openapi-demos/faq.html#how-can-i-map-pageable-spring-date-commons-object-to-correct-url-parameter-in-swagger-ui

Share:
34,916
Laurent
Author by

Laurent

I run some businesses: https://contentshowcase.app https://medicalid.app https://noticeable.io

Updated on July 09, 2022

Comments

  • Laurent
    Laurent almost 2 years

    I have developed a microservice using Spring Boot. The documentation for the REST API is made with Swagger. Some REST resources make use of Spring concepts to provide pagination for free. Below is an example:

    @RequestMapping(value = "/buckets", method = GET)
    public PagedResources list(Pageable pageable, PagedResourcesAssembler assembler) {
        return bucketService.listBuckets(pageable, assembler);
    }
    

    If I open the Swagger page, the following form is available for the resource:

    enter image description here

    The issue I have is that the pageable parameter is detected with content-type application/json and I don't know how to pass a value to change the page size for example. All values seem to be ignored.

    Is it possible to pass the query parameters as JSON object? or is it possible to configure Swagger to generate independent query parameter fields for getters contained by the Pageable interface?

    Please note that I am using Springfox with Gradle:

    compile 'io.springfox:springfox-spring-web:2.3.1'
    compile 'io.springfox:springfox-swagger2:2.3.1'
    compile 'io.springfox:springfox-swagger-ui:2.3.1'
    
  • pillingworth
    pillingworth about 7 years
    I found I had to use dataType = "int" otherwise the data type comes out as Undefined as shown in the picture.
  • Niccolò
    Niccolò over 5 years
    It seems the issue has been fixed and the answer could consequentially be updated..
  • mor222
    mor222 about 5 years
    with this class I get the following error: Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionExcept‌​ion: No qualifying bean of type 'org.springframework.data.rest.core.config.RepositoryRestCon‌​figuration' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {}
  • Ultimate Fighter
    Ultimate Fighter almost 5 years
    This can't work like this. 'ApiImplicitParams' not applicable to annotation type
  • a1eksandre
    a1eksandre almost 5 years
    Worked just fine for version 2.8.0
  • Yubaraj
    Yubaraj almost 5 years
    Make sure to use @ApiIgnore annotation to the Pageable parameter.
  • PAA
    PAA over 4 years
    @Sean - How can we configure Pagination for the OpenAPI 3 or Swagger 3 ?
  • PAA
    PAA over 4 years
    How can we use Pageable in Open API 3 version?
  • PAA
    PAA over 4 years
    Looks like this doesn't works with the SpringDocs-openapi-ui. Any guidance how to make it work ?
  • Sean Connolly
    Sean Connolly over 4 years
    @PAA what did you try? It would be a good contribution to the community if you figured it.
  • PAA
    PAA over 4 years
    Could you please guide me here: stackoverflow.com/questions/59967447/… ?
  • nimai
    nimai about 4 years
    @SeanConnolly he put his version in a question here: stackoverflow.com/questions/60058976/…
  • PAA
    PAA about 4 years
    Could you please guide me here : stackoverflow.com/questions/60834165/…
  • PAA
    PAA about 4 years
    Is there any way to send query parameters in single Parameter ?
  • Hamza Belmellouki
    Hamza Belmellouki almost 4 years
    any solution for springdoc?
  • Lewis Munene
    Lewis Munene about 2 years
    @mor222 - you can remove RepositoryRestConfiguration altogether and replace restConfiguration.getPageParamName() with "page", restConfiguration.getLimitParamName() with "size" and restConfiguration.getSortParamName() with "sort" respectively