6

I can customize OpenAPI from code.
Can I do same over openapi.yaml like swagger-petstore
I create simple springboot project with one @RestController.
I create openapi.yaml and copy it to /src/main/resources/.
But I see default values on open swagger-ui page.

Yura Shinkarev
  • 5,134
  • 7
  • 34
  • 57

4 Answers4

14

This is available from the FAQ page in the spring-doc documentation. See What is a proper way to set up Swagger UI to use provided spec.yml? and How can use custom json/yml file instead of generated one ? of the same page.

Example from the FAQ page

  1. Turn off auto-generation in the project property file springdoc.api-docs.enabled=false
  2. Put your yaml file in src/main/resources/static such as src/main/resources/static/myApiFile.yaml
  3. Set the swagger-ui url for the file springdoc.swagger-ui.url=/myApiFile.yaml
  4. Enable the minimal beans configuration
import org.springdoc.core.SpringDocConfigProperties;
import org.springdoc.core.SpringDocConfiguration;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class SpringDocsConfiguration {

  @Bean
  SpringDocConfiguration springDocConfiguration() {
    return new SpringDocConfiguration();
  }

  @Bean
  public SpringDocConfigProperties springDocConfigProperties() {
    return new SpringDocConfigProperties();
  }
}
antonkronaj
  • 1,237
  • 12
  • 13
1

The code below is all what we needed to do to use openapi.yaml specification file instead of the default one that is generated from code.

Explanation:

  • org.springdoc.webflux.api.OpenApiResource is Controller that handles /v3/api-docs and /v3/api-docs.yaml endpoints. Swagger UI is using that endpoint to show swagger ui page - /swagger-ui.html. You can see the configuration when you hit /v3/api-docs/swagger-config endpoint.

  • org.springdoc.webflux.api.OpenApiResource bean is registered only if missing. You can see it in SpringDocWebFluxConfiguration. The method that creates the bean is annotated with @ConditionalOnMissingBean. So you just need to extend it and adjust OpenApi specification retrieval (see below).

  • org.springdoc.webflux.api.OpenApiResource is using getOpenApi() method to retrieve OpenAPI specification (by default the specification is generated based on the class annotation from code). So you just need to override getOpenApi() method and provide the specification from yaml file itself (getYamlMapper() method is also provided for you in the parent classes, so it's really that easy how it is in the file below)

  • You can see OpenApiResource is in webflux package because we use org.springdoc:springdoc-openapi-webflux-ui, Spring WebFlux. It is done similarly in Spring MVC.

  • Hope this helps :) When you hit /swagger-ui.html you should see the docs directly from .yaml spec. When you hit /v3/api-docs you should see the specs itself in JSON. When you hit /v3/api-docs.yaml you should see the specs itself in YAML. No Spring Configuration code is needed. Just the controller as you see below :)

  • Just to be clear. Our OpenAPI spec is in src/main/resources/openapi/api.yaml


package com.your.package;
...imports omitted for readability...
import org.springdoc.webflux.api.OpenApiResource;

@RestController
public class OpenApiController extends OpenApiResource {

  @Value("classpath:openapi/api.yaml")
  private Resource openAPIResource;

  private OpenAPI openAPI;

  public OpenApiController(ObjectFactory<OpenAPIBuilder> openAPIBuilderObjectFactory, AbstractRequestBuilder requestBuilder, GenericResponseBuilder responseBuilder, OperationBuilder operationParser, RequestMappingInfoHandlerMapping requestMappingHandlerMapping, Optional<List<OperationCustomizer>> operationCustomizers, Optional<List<OpenApiCustomiser>> openApiCustomisers, SpringDocConfigProperties springDocConfigProperties, Optional<ActuatorProvider> actuatorProvider) {
    super(openAPIBuilderObjectFactory, requestBuilder, responseBuilder, operationParser, requestMappingHandlerMapping, operationCustomizers, openApiCustomisers, springDocConfigProperties, actuatorProvider);
  }

  @SneakyThrows
  @PostConstruct
  public void initOpenAPI() {
    openAPI = getYamlMapper().readValue(openAPIResource.getInputStream(), OpenAPI.class);
  }

  @Override
  protected synchronized OpenAPI getOpenApi() {
    return openAPI;
  }
}
rasto
  • 601
  • 4
  • 7
  • 1
    I was also thinking about it if it is or not. But OpenApiResource method is annotated with @ConditionalOnMissingBean bean so I think that was the intention. To let you freely configure it if you need :) Definitely better than making HTTP redirections and registering custom resource handlers for the specification. – rasto Oct 30 '20 at 11:25
  • 2
    Unsatisfied dependency expressed through constructor parameter 1; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'org.springdoc.core.AbstractRequestService' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {} – Vijay Kumar Rajput Feb 10 '21 at 01:25
0

If you need configuration file, you can have a look at the FAQ, documentation:

And here is the link for code samples:

0

This answer is excellent and lead me to the right direction. I applied all steps but the code section had a difference with the link provided. In the link provided the code suggested contains also an ObjectMapperProvider which is absent in that answer.

Also once the changes are applied the endpoint to verify the modification that worked for me was http://localhost:8080/swagger-ui/index.html

Hope this helps clarify, but all the information is already there. Thanks.

import org.springdoc.core.SpringDocConfigProperties;
import org.springdoc.core.SpringDocConfiguration;
import org.springdoc.core.providers.ObjectMapperProvider;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * Provides the capabilities to display the apiDoc in a preconfigured endpoint based on the following information of open-api
 * https://springdoc.org/faq.html#_what_is_a_proper_way_to_set_up_swagger_ui_to_use_provided_spec_yml
 * This apiDoc can be consulted through the endpoint: http://localhost:8080/swagger-ui/index.html
 */
@Configuration
public class SpringDocsConfiguration {

    @Bean
    SpringDocConfiguration springDocConfiguration() {
        return new SpringDocConfiguration();
    }

    @Bean
    public SpringDocConfigProperties springDocConfigProperties() {
        return new SpringDocConfigProperties();
    }

    @Bean
    ObjectMapperProvider objectMapperProvider(SpringDocConfigProperties springDocConfigProperties){
        return new ObjectMapperProvider(springDocConfigProperties);
    }
}
user16217248
  • 3,119
  • 19
  • 19
  • 37