programing

Spring Pageable 인터페이스용 Swagger 문서

testmans 2023. 2. 24. 13:21
반응형

Spring Pageable 인터페이스용 Swagger 문서

Spring Boot을 사용한 마이크로 서비스를 개발했습니다.REST API 문서는 Swagger로 작성되었습니다.일부 REST 리소스는 스프링 개념을 사용하여 페이지 번호를 무료로 제공합니다.다음은 예를 제시하겠습니다.

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

Swagger 페이지를 열면 리소스에서 다음 양식을 사용할 수 있습니다.

여기에 이미지 설명 입력

content-type application/json에서 pageable parameter가 검출되어 예를 들어 페이지 크기를 변경하기 위한 값을 전달하는 방법을 모르는 문제가 있습니다.모든 값이 무시되는 것 같습니다.

쿼리 파라미터를 JSON 오브젝트로 전달할 수 있습니까?아니면 Swagger가 Pageable 인터페이스에 포함된 getter에 대해 독립된 쿼리 파라미터 필드를 생성하도록 설정할 수 있습니까?

Springfox를 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'

이것은 Spring-Fox에서 이미 알려진 문제입니다.제755호 참조.이 시점에서 zdila의 코멘트2에 근거해, @ApiImplicitParams를 추가하는 것도 이상적이지만 동작합니다.

@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.")
})

[@ApiImplicitParams for Pagable을 표시하는 Swagger UI

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

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

Vineet Bhatia의 답변을 바탕으로 솔루션을 커스텀 주석으로 정리하여 재사용할 수 있습니다.

@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 {
}

다음과 같이 사용할 수 있습니다.

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

Vineet Bhatia의 답변은@ApiImplicitParams괜찮아 보여요.하지만 난 상황에 직면했어@ApiIgnor그리고.@ApiParam(hidden = true)동작하지 않고, 앙상블러와 페이지 가능한 파라메스를 관찰할 수 있습니다.다음 행을 추가하여 이 문제를 해결했습니다.

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

내 안에 있는 Docket bean에SwaggerConfig.

Java의 예:

콩:

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

Swagger Pageable:

@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;

}

스웨거:

여기에 이미지 설명 입력

다음은 Open을 위해 springdoc-openapi-data-rest에 통합된 주석 버전입니다.API 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 {

}

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 를 참조해 주세요.

Open API 3.0은 매끄러운 통합을 제공합니다.

예를들면,

@GetMapping("/filter")
public Page<Employee> filterEmployees(Pageable pageable) {
     return repository.getEmployees(pageable);
}

springdoc-openapi-data-rest 의존관계 추가

implementation 'org.springdoc:springdoc-openapi-data-rest:1.5.2'

참고: 여러 매개 변수가 있는 경우 '@ParameterObject'를 추가할 수 있습니다.

public Page<Employee> filterEmployees(@ParameterObject Pageable pageable)

이 솔루션은 모든 컨트롤러의 모든 API 메서드에 주석을 달 필요가 없습니다.먼저 다음 대체품을 만듭니다.Pageable올바른 속성 이름과 설명을 가진 클래스(Kotlin 코드, Java용 인터페이스를 사용할 수 있음):

data class SwaggerPageable(
        @ApiModelProperty("Number of records per page", example = "20")
        val size: Int?,

        @ApiModelProperty("Results page you want to retrieve (0..N)", example = "0")
        val page: Int?,

        @ApiModelProperty("Sorting criteria in the format: property(,asc|desc)." +
                "Default sort order is ascending. Multiple sort criteria are supported.")
        var sort: String?
)

다음 Swagger Swagger의 직접 합니다.PageableKotlin (Kotlin ), Java (Java) :

@Bean
fun api(): Docket {
    return Docket(DocumentationType.SWAGGER_2)
            .select()
            .paths(PathSelectors.any())
            .build()
            .directModelSubstitute(Pageable::class.java, SwaggerPageable::class.java)
}

결과는 다음과 같습니다.

여기에 이미지 설명 입력

할 수 입니다.ApiModelProperty하지만 이 정도면 제 프로젝트에는 충분합니다.

로컬 호스트에서 실행 중이 아닌 경우 Vineet Bhatia의 응답에 검증 문제가 발생합니다.이는 정수 파라미터가 json 스키마에 대응하지 않는 것을 인수합니다.

그래서 정수를 문자열로 변경했습니다.

    @ApiImplicitParams({
        @ApiImplicitParam(name = "page", dataType = "string", paramType = "query",
                value = "Results page you want to retrieve (0..N)"),
        @ApiImplicitParam(name = "size", dataType = "string", 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.")
})

2019년에 이 문제를 해결하고 싶은 분들을 위해서.springfox 문서를 통한 이 구성은 파라미터에 대한 설명을 설정할 수 없다는 점을 제외하고는 정상적으로 작동합니다.

코드는 여기 있습니다.

https://github.com/springfox/springfox/blob/ef1721afc4c910675d9032bee59aea8e75e06d27/springfox-data-rest/src/main/java/springfox/documentation/spring/data/rest/configuration/SpringDataRestConfiguration.java

여기 springdoc-openapi-ui 솔루션이 있습니다.

SpringDocUtils.getConfig()
.replaceWithClass(org.springframework.data.domain.Pageable.class, SwaggerPageable.class);
    
@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;
    
}

Evgeny가 나타내는 검증 문제에 대한 답변입니다.

사용.

@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.") })

는 예외를 발생시킵니다.

Illegal DefaultValue  for parameter type integer
java.lang.NumberFormatException: For input string: ""
    at java.base/java.lang.NumberFormatException.forInputString(NumberFormatException.java:68)
    at java.base/java.lang.Long.parseLong(Long.java:709)
    at java.base/java.lang.Long.valueOf(Long.java:1151)
    at io.swagger.models.parameters.AbstractSerializableParameter.getExample(AbstractSerializableParameter.java:412)
    at jdk.internal.reflect.GeneratedMethodAccessor366.invoke(Unknown Source)
    at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.base/java.lang.reflect.Method.invoke(Method.java:567)
    at com.fasterxml.jackson.databind.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:688)
    at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:719)
    at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:155)
    at com.fasterxml.jackson.databind.ser.impl.IndexedListSerializer.serializeContents(IndexedListSerializer.java:119)
    at com.fasterxml.jackson.databind.ser.impl.IndexedListSerializer.serialize(IndexedListSerializer.java:79)

(적어도 springfox-20002 및 springfox-20002-ui 버전 2.9.2에서는 해당됩니다.)

Evgeny의 답변을 따르거나 정수 파라미터의 기본값과 예제 값을 추가하여 예외를 피할 수 있습니다.

@ApiImplicitParams({
    @ApiImplicitParam(name = "page", dataType = "int", paramType = "query", value = "Results page you want to retrieve (0..N)", defaultValue = "0", example = "2"),
    @ApiImplicitParam(name = "size", dataType = "int", paramType = "query", value = "Number of records per page.", defaultValue = "20", example = "10"),
    @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.") })

업데이트:

org.springdoc.core.converters.models.DefaultPageablePageable 는.@ParameterObjectSwagger JSON 3번지

암묵적인 파라미터를 사용한 솔루션은 기능하지만 많은 추가 취약 코드를 도입합니다.최종적으로는, 다음의 솔루션을 채용했습니다.

@GetMapping(value = "/")
public HttpEntity<PagedResources<Item>> getItems(
    @RequestParam(value = "page", required = false) Integer page,
    @RequestParam(value = "size", required = false) Integer size,
    PagedResourcesAssembler assembler) {
    Page<Item> itemPage = itemService.listItems(PageRequest.of(page, size, Sort.unsorted()));
    return new ResponseEntity<>(assembler.toResource(itemPage), HttpStatus.OK);
}

PageRequest하는 것(실장)Pageable )을를) 입니다.Page ( 에서)org.springframework.data.domain를 참조해 주세요.

org.springframework.data.web.PagedResourcesAssembler을 에 수 .org.springframework.hateoas.PagedResources

동적 정렬이 필요 없기 때문에 생략했습니다.springfox는 org.springframework.data.domain과 잘 어울리지 않기 때문에 정렬을 추가하는 데 어려움이 있습니다.종류.

언급URL : https://stackoverflow.com/questions/35404329/swagger-documentation-for-spring-pageable-interface

반응형