springfox icon indicating copy to clipboard operation
springfox copied to clipboard

Aggregate API Docs in Spring Gateway failed

Open hantsy opened this issue 4 years ago • 8 comments

Please take the time to search the repository, if your question has already been asked or answered.

  • [x] What version of the library are you using? 3.0.0

What kind of issue is this?

  • [x] Bug report. If you’ve found a bug, spend the time to write a failing test.

The reproducer codes: https://github.com/hantsy/spring-puzzles/blob/master/springfox-gateway/

I tried to add an aggregated Swagger UI for all downstream service in a Microservices architecture, but failed.

    @Primary
    @Bean
    public SwaggerResourcesProvider swaggerResourcesProvider(InMemorySwaggerResourcesProvider defaultResourcesProvider) {
        return () -> {
            SwaggerResource customersResource = new SwaggerResource();
            customersResource.setName("Customers Endpoints");
            customersResource.setSwaggerVersion("3.0");

            customersResource.setUrl("/customers/v3/api-docs");
            //customersResource.setUrl("http://localhost:8001/v3/api-docs");

            SwaggerResource ordersResource = new SwaggerResource();
            ordersResource.setName("Orders Endpoints");
            ordersResource.setSwaggerVersion("3.0");
            ordersResource.setUrl("/orders/v3/api-docs");
            //ordersResource.setUrl("http://localhost:8002/v3/api-docs");

            List<SwaggerResource> resources = new ArrayList<>(defaultResourcesProvider.get());
            resources.add(customersResource);
            resources.add(ordersResource);
            return resources;
        };
    }

The router config in the gateway application.yml is similar to this.


spring:
  cloud:
    gateway:
      routes:
        - id: customers
          uri: http://localhost:8001
          predicates:
            - Path=/customers/**
          filters:
            - RewritePath=/customers/(?<segment>.*), /$\{segment}
        - id: orders
          uri: http://localhost:8002
          predicates:
            - Path=/orders/**
          filters:
            - RewritePath=/orders/(?<segment>.*), /$\{segment}

The swagger resources url added the gateway URL by default, I can not set a full URL with HTTP/HTTPS protocol.

When running the application, the Swagger UI is displayed, but when I tried to run the endpoints in the downstream service(eg. hosted on http://localhost:8001), it always called on the gateway host(hosted on http://localhost:8080), it is incorrect.

Excepted: If it called on http://localhost:8080/customers, it will work due to rewrite rules, but it seems there is no way to set up the rewrite rules. Or called on the target host address: http://localhost:8001.

hantsy avatar Sep 04 '21 04:09 hantsy

Hope there is a baseUrl. When it is set, the API Docs can be discovered via $baseUrl +"/v3/api-docs", and API endpoints test can be executed on the baseUrl directly.

So we can set the baseUrl to the gateway customers endpoints(http://localhost:8080/customers) instead of the target service.

hantsy avatar Sep 04 '21 04:09 hantsy

Hope there is a baseUrl. When it is set, the API Docs can be discovered via $baseUrl +"/v3/api-docs", and API endpoints test can be executed on the baseUrl directly.

So we can set the baseUrl to the gateway customers endpoints(http://localhost:8080/customers) instead of the target service.

@hantsy I think my blog would help you about it.

https://blog.yuebaix.com/2021/10/04/%E4%B8%83%E5%A4%A9%E6%9E%84%E5%BB%BAspringcloud%E9%9B%86%E7%BE%A4/

I suppose the maintainer has not maintained for a long time.

yuebaix avatar Oct 05 '21 11:10 yuebaix

This is the key solution.

@Primary
@Configuration
public class GatewayRoutesOasSwaggerResourcesProvider extends InMemorySwaggerResourcesProvider {
    protected static final String API_DOCS_URI = "/v3/api-docs";
    private static final String SWAGGER_VERSION = "3.0";
    private final RouteLocator routeLocator;
    private final GatewayProperties gatewayProperties;

    public GatewayRoutesOasSwaggerResourcesProvider(
            RouteLocator routeLocator, GatewayProperties gatewayProperties,
            Environment environment, DocumentationCache documentationCache, DocumentationPluginsManager pluginsManager) {
        super(environment, documentationCache, pluginsManager);
        this.routeLocator = routeLocator;
        this.gatewayProperties = gatewayProperties;
    }

    @Override
    public List<SwaggerResource> get() {
        List<SwaggerResource> resources = new ArrayList<>();
        resources.addAll(super.get());
        List<String> routes = new ArrayList<>();
        routeLocator.getRoutes().subscribe(route -> routes.add(route.getId()));
        gatewayProperties.getRoutes().stream().filter(routeDefinition -> routes.contains(routeDefinition.getId())).forEach(route -> {
            route.getPredicates().stream()
                    .filter(predicateDefinition -> ("Path").equalsIgnoreCase(predicateDefinition.getName()))
                    .forEach(predicateDefinition -> resources.add(swaggerResource(route.getId(),
                            predicateDefinition.getArgs().get(NameUtils.GENERATED_NAME_PREFIX + "0")
                                    .replace("/**", API_DOCS_URI))));
        });
        return resources;
    }

    private SwaggerResource swaggerResource(String name, String location) {
        SwaggerResource swaggerResource = new SwaggerResource();
        swaggerResource.setName(name);
        swaggerResource.setLocation(location);
        swaggerResource.setSwaggerVersion(SWAGGER_VERSION);
        return swaggerResource;
    }
}

yuebaix avatar Oct 05 '21 11:10 yuebaix

This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.

stale[bot] avatar Jan 05 '22 09:01 stale[bot]

@yuebaix Thanks.

It seems SpringFox development is not active now.

hantsy avatar Jan 07 '22 01:01 hantsy

This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.

stale[bot] avatar Apr 11 '22 01:04 stale[bot]

There is no update for several months, not sure this project is still active.

hantsy avatar Apr 11 '22 06:04 hantsy

This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.

stale[bot] avatar Jul 10 '22 15:07 stale[bot]

This issue has been automatically closed because it has not had recent activity. Please re-open a new issue if this is still an issue.

stale[bot] avatar Aug 13 '22 06:08 stale[bot]