list the api in swagger based on user roles

泪湿孤枕 提交于 2021-02-05 11:47:29

问题


I have a requirement where I want to list the api methods in swagger based on user roles.

For example :-

  • User A with basic access can use limited api methods.
  • User B with Admin access can use all the listed api methods.

I don't know how to achieve this.

I am using Swashbuckle.AspNetCore Version="1.0.0"


回答1:


Try using an IDocumentFilter, you can limit what the user gets in the SwaggerDocument and the swagger-ui feeds from that.

Here are some examples https://github.com/heldersepu/SwashbuckleTest/blob/master/Swagger_Test/App_Start/SwaggerConfig.cs#L261




回答2:


Possible solution:

  1. Define several dockets in your swagger config with different group names
@Bean
public Docket api1() {
    ...
    return new Docket(DocumentationType.SWAGGER_2)
            ...
            .groupName("api1")
            ...
            .paths(PathSelectors.ant("/api/api1Url/**"))
            .build().apiInfo(metaData());
}

@Bean
public Docket api2() {
    ...
    return new Docket(DocumentationType.SWAGGER_2)
            ...
            .groupName("api2")
            ...
            .paths(PathSelectors.ant("/api/api2Url/**"))
            .build().apiInfo(metaData());
}
  1. Define your own DocumentationCache which overrides Swagger's one
@Primary
@Component
public class RolesAwareDocumentationCache extends DocumentationCache {

    private final Map<String, Set<String>> allowedResourcesPerRole =
            Map.of(SecurityConfig.API1_ROLE, Collections.singleton("api1"),
                    SecurityConfig.API2_ROLE, Collections.singleton("api2"),
                    SecurityConfig.SOME_ADMIN_ROLE, Set.of("api1", "api2"));

    @Override
    public Map<String, Documentation> all() {
        var documentationMap = super.all();
        return documentationMap.entrySet().stream()
                .filter(e -> isAllowedForRole(e.getKey())) // check if has access to this group
                .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
    }

    private boolean isAllowedForRole(String groupName) {
        var userAuthorities = SecurityContextHolder.getContext().getAuthentication().getAuthorities().stream()
                .map(Object::toString)
                .collect(Collectors.toUnmodifiableSet());

        return userAuthorities.stream()
                .map(allowedResourcesPerRole::get) // get allowed resources for all of the user roles
                .filter(Objects::nonNull)
                .flatMap(Collection::stream) // flatMap to collection
                .anyMatch(s -> s.contains(groupName)); // check if result collection has specified group name
    }

}

So this cache will return groups based on the current user's role from the security context. You can actually use any rules to restrict access to different groups.

Also do not forget to define proper permissions for HttpSecurity to restrict the invocation of an API for not allowed roles.



来源:https://stackoverflow.com/questions/44904213/list-the-api-in-swagger-based-on-user-roles

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!