Jerry Li
Jerry Li

Reputation: 47

Is there any Spring Boot with Jersey framework that supports OpenAPI 3.0?

There are a ton of tutorials regarding Spring Boot, JAX-RS, and Swagger. However, most of them seem to use the OpenAPI 2 specification. I only found one tutorial that uses Spring, JAX-RS, and OpenAPI 3.0 (that tutorial used Apache CXF).

https://dzone.com/articles/moving-with-the-times-towards-openapi-v300-adoptio

Do any other Spring Boot + JAX-RS implementations work with OpenAPI 3.0? For example, all tutorials with Jersey only seem to output OpenAPI 2.0. Apache CXF is fine for what I'm doing but I would like to know if there are options.

Springdoc-openapi supports spring boot and OpenAPI 3.0, unsure about jaxrs. https://github.com/springdoc/springdoc-openapi

Upvotes: 4

Views: 5626

Answers (3)

gbouget
gbouget

Reputation: 58

Since 1.6, isDisplayQueryParams() has been removed from SwaggerUiConfigProperties but this solution works :

springdoc.swagger-ui.url=/api/openapi.json

Principle :

1) GET /swagger-ui/index.html
2) GET /v3/api-docs/swagger-config
    [Response body]
    configUrl: "/v3/api-docs/swagger-config"
    oauth2RedirectUrl: "(...)"
    operationsSorter: "method"
    url: "/api/openapi.json" // <=> springdoc.swagger-ui.url
    validatorUrl: ""
3) GET /api/openapi.json

Upvotes: 1

Jelemux
Jelemux

Reputation: 176

Adding an answer because I can't comment or edit.

Question: when I try to load the swagger-ui.html, it redirected to /swagger-ui/index.html?configUrl=/api/openapi.json/swagger-config However, there's nothing for swagger-config. Am I missing any configuration?

I had that problem as well. I was able to fix it by adding the following property to my application.properties:

springdoc.swagger-ui.display-query-params=true

The problem is weird and somehow the solution is even weirder. But hey, it works!

Upvotes: 1

Markus Demetz
Markus Demetz

Reputation: 101

Configuration of Spring Boot with JAX-RS producing OpenAPI 3.0 specification

You can use Swagger to generate an OpenAPI 3.0 together with Spring Boot and JAX-RS by doing the following:

  1. Include spring-boot-starter-jersey, swagger-core, swagger-annotations and swagger-jaxrs in pom.xml
  2. Extend ResourceConfig and configure the packages to scan for JAX-RS annotations and register the OpenAPIResource.class of Swagger.
  3. Use Swagger Annotations to annotate your endpoints and your schema.
  4. Optionally include sprindoc-openapi-ui if you want to access Swagger via /swagger-ui.html.

1) Dependencies in pom.xml

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-jersey</artifactId>
    </dependency>
    <dependency>
        <groupId>io.swagger.core.v3</groupId>
        <artifactId>swagger-annotations</artifactId>
        <version>${swagger.version}</version>
    </dependency>
    <dependency>
        <groupId>io.swagger.core.v3</groupId>
        <artifactId>swagger-core</artifactId>
        <version>${swagger.version}</version>
    </dependency>
    <dependency>
        <groupId>io.swagger.core.v3</groupId>
        <artifactId>swagger-jaxrs2</artifactId>
        <version>${swagger.version}</version>
        <exclusions>
            <exclusion>
                <groupId>io.github.classgraph</groupId>
                <artifactId>classgraph</artifactId>
            </exclusion>
        </exclusions>
    </dependency>
    <dependency>
        <groupId>org.springdoc</groupId>
        <artifactId>springdoc-openapi-ui</artifactId>
        <version>1.2.18</version>
    </dependency>

Current swagger-version is 2.1.0.

There is a conflict with springdoc-openapi-ui and swagger-jaxrs2, which leads to an error with io.github.classgraph so this library must be excluded from swagger-jaxrs2.

2: Extending ResourceConfig

@Component
@ApplicationPath("/api")
@Path("/")
public class JaxRsConfig extends ResourceConfig {
    public JaxRsConfig() {
        // register resources
        packages("com.example.jaxrs.resources");
        register(OpenApiResource.class);
    }
}

The JAX-RS annotated resources must be scanned by calling packages("com.example.jaxrs.resources").

Be careful, not to confuse with the register function!

The OpenApiResource.class comes from Swagger and offers the /openapi.json endpoint.

The reason why I use /api as @ApplicationPath is, that when using it together with springdoc-openapi-ui, the swagger-ui.html endpoint is not found when the @ApplicationPath is set to "/". It seems that something is getting overwritten in this case. Maybe someone has an explanation for this.

3) Swagger Annotations

@Schema(name = "Message", description = "This is an object to place a message.")
public class MessageDto {

    @Schema(name="Message", required = true)
    private String message;

    public MessageDto(String message) {
        super();
        this.message = message;
    }
    // ... getters and setters
}

4) Configuring SpringDoc

By default, you should be able to call /swagger-ui.html to open Swagger and browse your OpenAPI 3.0 definition.

Since the @ApplicationPath is set to /api, we need to configure SpringDoc where to look for the definition by setting a property in application.properties:

springdoc.api-docs.path=/api/openapi.json

You can also change the URL of Swagger with:

springdoc.swagger-ui.path=/swagger-ui.html

Other issues:

Another issue may arise, when running the application as a .jar file:

Spring boot application won't run when trying to run from the jar file

In this case I've found a solution by scanning all the components with a reflection library like org.reflections like so:

    private void scan(String... packages) {
        for (String packageName : packages) {
            Reflections reflections = new Reflections(packageName);
            reflections.getTypesAnnotatedWith(Provider.class).parallelStream().forEach(clazz -> register(clazz));
            reflections.getTypesAnnotatedWith(Path.class).parallelStream().forEach(clazz -> register(clazz));
        }
    }

Upvotes: 10

Related Questions