6

I am wondering whether there is an option in Swagger to authorize request to url containing external documentation.

I have the following configuration, what I am interested in is urls[1] part

springdoc.swagger-ui.urls[0].url=/v3/api-docs
springdoc.swagger-ui.urls[0].name=default
springdoc.swagger-ui.urls[1].url=https://asdasd.blob.core.windows.net/my-api/docs.spec
springdoc.swagger-ui.urls[1].name=additional

I am able to access the docs from the server (curl directly from the machine) however from the Swagger (so the browser) I can't. I am wondering if there is an option to add eg. Authorization Bearer xxxx to this request or actually make server issue the request, not the client.

To clarify - I want to fetch second file with OpenAPI definition from the remote server so I am talking about this: enter image description here

Not the Authorize part enter image description here


Solution I implemented:

What Helen pointed out would work - intercepting the request and adding the headers - however unfortunately in my case there was also an issue connected to firewall settings of a storage. Only traffic coming from the server, not the client (browser) was passing through so I:

  1. Set the url to something in my domain
    springdoc.swagger-ui.urls[1].url=v3/api-docs/additional
  2. Specified another property for the url to the remote host
    mydomain.swagger-ui.additionalDocsUrl=...
  3. Implemented a custom controller handing that url - it fetches json from the remote as a server, instead of a client so firewall passes that request through
@Hidden
@RestController
@RequestMapping("/v3/api-docs/additional")
@RequiredArgsConstructor
public class AdditionalOpenApiController {

    @Value("${mydomain.swagger-ui.additionalDocsUrl}")
    private String additionalDocsUrl;

    @Cacheable(value = "ADDITIONAL_API_DOCS", unless = "#result != null")
    @GetMapping(produces = "application/json")
    public String getAdditionalDocs() {
        // in my case remote produces application/octet-stream so it needs to be byte[]
        return Optional.ofNullable(new RestTemplate().getForObject(additionalDocsUrl, byte[].class)) 
                .map(String::new)
                .orElseThrow(() -> new ResourceNotFoundException("Cannot load Additional OpenAPI from storage"));
}
michelson
  • 686
  • 9
  • 22
  • I'm not sure I understand your question, but you can add any authentication for separated requests, based on the [documentation](https://swagger.io/docs/specification/authentication/). – M. Dudek Dec 19 '21 at 16:49
  • 1
    I clarified the question. – michelson Dec 19 '21 at 17:00
  • 1
    You need to add a [`requestInterceptor`](https://stackoverflow.com/a/46892528/113116) to your Swagger UI configuration. The `requestInterceptor` can be used to mutate outgoing requests, e.g. add auth headers to the spec fetch request. I'm not sure how to do configure the `requestInterceptor` in Springdoc though. – Helen Dec 19 '21 at 19:23

1 Answers1

1

This can be achieved only programmatically.

  • First: Implement your own requestInterceptor : See on AbstractSwaggerIndexTransformer samples for implementing your request programmatically (for example addCSRF method).
  • Second Implement your own MySwaggerIndexPageTransformer and define it as a spring bean and it will be loaded instead of the springdoc SwaggerIndexPageTransformer. enter image description here
brianbro
  • 4,141
  • 2
  • 24
  • 37