Gavin
Gavin

Reputation: 1767

Unable to display Swagger/OpenApi docs when using SpringDoc webflux support

I have a small Spring Boot micro-service that exposes its endpoint as reactive, using webflux.

When I run the application from IntelliJ, Gradle or from the cmd line with the SpringDoc webflux support:
implementation 'org.springdoc:springdoc-openapi-webflux-ui:1.4.4'
and I go to http://localhost:8080/swagger-ui.html I get a 500 error, the logs show:

java.lang.IllegalStateException: No primary or default constructor found for interface org.springframework.http.server.reactive.ServerHttpRequest]

and the root cause:

java.lang.NoSuchMethodException: org.springframework.http.server.reactive.ServerHttpRequest.<init>()

if I use http://localhost:8080/swagger-ui/index.html?configUrl=/v3/api-docs/swagger-config I get a 404 instead of a 500.

However if I change the dependency to the non reactive SpringDoc module:
implementation 'org.springdoc:springdoc-openapi-ui:1.4.4'

The docs are available, they just dont show return schema (I guess this is expected as the response is wrapped in a Mono).

I have looked at this question, but it didnt help

I am using Spring Boot 2.3.3.RELEASE, I have nothing "fancy" in the controller other than an autowired service class, the endpoint is simply annotated with the GetMapping and returns Mono<T>. and I have included the following dependencies:

    implementation 'org.springframework.boot:spring-boot-starter-actuator'
    implementation 'org.springframework.boot:spring-boot-starter-webflux'
    implementation 'org.springframework.boot:spring-boot-starter-web'
    implementation 'org.springdoc:springdoc-openapi-webflux-ui:1.4.4'

Upvotes: 3

Views: 14460

Answers (4)

RAN
RAN

Reputation: 598

It is an old question, but I still ran into the same issue today.

I forgot to change the springdoc-openapi-starter-webmvc-ui dependency to springdoc-openapi-starter-webflux-ui.

After that it worked.

Upvotes: 1

Chayne P. S.
Chayne P. S.

Reputation: 1638

I have the restriction that I need to use Webflux via Servlet 3.1, even though it's not the pure Reactive solution but I can reuse some Spring security filter with Servlet.So, I cannot just remove spring-boot-starter-web as @brianbro suggested.

Therefore, I found a solution to make springdoc-openapi-ui be able to read Flux & Mono by adding WebFluxSupportConverter from springdoc-openapi-webflux-core as an extra converter. See the following code in Groovy.

    @Bean
    public OpenAPI customOpenAPI() {

        ModelConverters.getInstance().addConverter(new WebFluxSupportConverter())

        return new OpenAPI()
            .components(new Components()
                .addSecuritySchemes("JWE", new SecurityScheme()
                    .type(SecurityScheme.Type.HTTP)
                    .scheme("bearer")
                    .bearerFormat("JWE")))
            .info(new Info()
                .title("Marketplace API")
                .version(apiVersion))
    }

So, you just need to include the libraries.

    implementation 'org.springdoc:springdoc-openapi-ui:1.4.6'
    implementation 'org.springdoc:springdoc-openapi-webflux-core:1.4.6'

Upvotes: 4

Marcel Puentes Rojas
Marcel Puentes Rojas

Reputation: 21

For me in a kotlin spring boot project the problem was with an endpoint returning a Flux so it was throwing a graceful exception: jackson BeanDescription.findJsonValueAccessor not found, this could lead to inaccurate result, please update jackson to 2.9+ the approach from @Chayne P. S. solved my problem:

class OpenApiConfigiguration {

    @Bean
    fun configOpenAPI(): OpenAPI? {
        ModelConverters.getInstance().addConverter(WebFluxSupportConverter())
        return OpenAPI()
                .info(Info().title("API")
                        .description("WS restful API")
                        .version("v0.0.1")
                        .license(License().name("License of API")
                        .termsOfService("Terms of service"))
                .externalDocs(ExternalDocumentation()
                        .description("Docs")
                        .url(""))
    }
}

Upvotes: 1

brianbro
brianbro

Reputation: 4809

Your project is using spring-boot-starter-web and spring-boot-starter-webflux.

You just need to remove spring-boot-starter-web from your dependencies.

Upvotes: 4

Related Questions