Filtering for API parts in swagger
Asked Answered
O

3

14

I have a REST API and springfox swagger v2.6.1 included and working. But now, I would like to not always display all the controllers I have, because some of them are very technical and not intended for the average user, but I want to be able to choose what I show without having to recompile the code. There is this dropdown field on top of the page which says 'default (/v2/api-docs)' (or whatever you configured it to), with only this one entry. My hunch is that it should be possible to have multiple options there, and according to the option show certain controller classes or not.

As I don't really know how to upload images, I cannot provide screenshots. I hope that my question is clear anyway.

The code that does the swagger in my project is the simplest possible:

@Bean
public Docket api() {

    return new Docket( DocumentationType.SWAGGER_2 )
            .select()
                .apis( RequestHandlerSelectors.any() )
                .paths( PathSelectors.any() )
                .build()
            .apiInfo( metadata() );
}

private ApiInfo metadata() {
    return new ApiInfoBuilder()
            .title( "My awesome ACS API" )
            .description( "All the requests that the server will respond to." )
            .version( "1.0.0" )
            .build();
}

I tried several approaches like adding some Properties, doing two .select() and selecting for different things, but I don't really seem to get anywhere close to what I hope to achieve.

Thanks for any help!

Osteoclasis answered 12/5, 2017 at 10:7 Comment(0)
B
24

Some of the options I can think of

  1. You can add Authentication to different endpoints using SpringSecurity and make the endpoints not accessible at all(But will be visible in Swagger UI).

  2. The drop down you are mentioning on the top can be configured something like this

    @Bean
    public Docket orderApi() {
        // This will group the endpoints strting with /order.   
        // And it will be visible as a separate group in the drop down(In Swagger UI) 
        // with the name 'order' as specified in the groupName(..)
        return new Docket(DocumentationType.SWAGGER_2)
                .groupName("order")
                .apiInfo(metadata())
                .select()
                .paths(PathSelectors.ant("/order/**"))
                .build();
    }
    
    @Bean
    public Docket orderValidationApi() {
        return new Docket(DocumentationType.SWAGGER_2)
                .groupName("product")
                .apiInfo(metadata())
                .select()
                .paths(PathSelectors.ant("/product/**"))
                .build();
    }
    
  3. You can completely exclude the endpoint from being visible in Swagger UI with someting like this in your Docker configuration

       return new Docket( DocumentationType.SWAGGER_2 )
            .select()
                .apis( RequestHandlerSelectors.any() )
                .paths(PathSelectors.regex("(?!/error).+")).paths(PathSelectors.regex("(?!/product).+"))
                .build()
            .apiInfo( metadata() );  
    

    This will make all the endpoints which are not /error and /product available. you can filter out endpoints like this.

Brede answered 12/5, 2017 at 10:17 Comment(2)
Thanks a lot! The second answer was exactly what I was looking for - the .groupName("") was the key (as I didn't want to change anything in accessability, just for the display). Now, the titles in the dropdown don't look very nice, in my case : Advanced (/acs/docs?group=Advanced). Any way I can change that to something a litte more user friendly? Otherwise I can also live with that .. Thanks a lot !!Osteoclasis
Need to filter based on HTTP verb...for instance if I want to disable PATCH how do I do this?Sublunary
S
2

You can also Provide package name

@Bean
public Docket api() {

    return new Docket( DocumentationType.SWAGGER_2 )
            .select()
            .apis(RequestHandlerSelectors.basePackage("com.hello.world.controller.user"))
            .paths( PathSelectors.any() )
            .build()
            .apiInfo( metadata() );
}

or you can use custom Annotation for your API classes or API methods as below:

@Bean
public Docket api() {

    return new Docket( DocumentationType.SWAGGER_2 )
            .select()
            .apis(RequestHandlerSelectors.withClassAnnotation(MyCustomClassAnnotation.class))
            .paths( PathSelectors.any() )
            .build()
            .apiInfo( metadata() );
}



@Bean
public Docket api() {

    return new Docket( DocumentationType.SWAGGER_2 )
            .select()
            .apis(RequestHandlerSelectors.withMethodAnnotation(MyCustomMethodAnnotation.class))
            .paths( PathSelectors.any() )
            .build()
            .apiInfo( metadata() );
}
Sulfate answered 5/6, 2020 at 1:25 Comment(0)
B
2

The @Hidden anottation worked for me.

@GetMapping("/ping")
@Hidden
public String ping() {
Brickkiln answered 5/8, 2022 at 20:31 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.