【问题标题】:Spring Cloud Gateway YML routing - is there a way to check permissions?Spring Cloud Gateway YML 路由 - 有没有办法检查权限?
【发布时间】:2020-07-18 09:09:30
【问题描述】:

我有一些微服务和一个使用 Spring Cloud 的网关。我正在尝试在网关中设置路由。理想情况下,我想在 YML 文件中设置路由,或者使用 RouteLocator bean。

但目前,在我的网关中,我的每条路由都有 REST 端点,这只是使用 WebClient 向前发送请求。

(在此之前,我有一个 ReactiveAuthenticationManager 过滤器来验证 JWT 令牌。它返回一个 UsernamePasswordAuthenticationToken ,其中包括它从令牌中获得的一些用户权限)。

这是一个示例,其中我设置了一条到称为跟踪服务的微服务的路由:

控制器:

@RestController
@RequestMapping("/tracking-service/tracking")
public class TrackingController {

  @Autowired
  private TrackingService trackingService;

  @GetMapping
  public Flux getAllTracking() {
    return trackingService.getAllTracking();
  }

}

服务:

@Service
public class TrackingService {

  private WebClient webClient;

  @PreAuthorize("hasAuthority('MANAGER')")
  public Flux getAllTracking() {
    //Make HTTP call to the tracking service
  }

}

我这样做的原因是@PreAuthorize 注释。如果客户端的 JWT 令牌不包含“MANAGER”令牌,那么这将返回 403 禁止状态。并非所有端点都需要 MANAGER 权限,并且某些端点需要其他权限。

我的问题 - 使用 YML 路由时是否可以这样做?我希望看到像这样的东西,但我不确定这可能吗?我已经阅读了 Spring 文档并查看了所有可用的过滤器,但我没有看到任何可以完成这项工作的内容。

spring:
  cloud:
    gateway:
      routes:
        - id: tracking
          uri: http://tracking-service
          predicates:
            - Path=/tracking-service/**
          filters:
            - StripPrefix=1
            - PreAuthorize=hasAuthority('MANAGER')

谢谢。

【问题讨论】:

  • 不在 yaml 中。您可以使用 spring security java 配置来做到这一点。

标签: java spring-security routing spring-cloud spring-cloud-gateway


【解决方案1】:

API 网关和授权是两个分离的关注点。理想情况下,不应在网关应用程序中混合授权。要获得许可,您可以直接将其映射到这样的服务。

@RestController
public class ResourceREST {

    @RequestMapping(value = "/resource/", method = RequestMethod.GET)
     @PreAuthorize("@customPermissionEvaluator.hasPrivilege(authentication,'somepermission')")
    public Mono<ResponseEntity<?>> user() {
        return Mono.just(ResponseEntity.ok(new Message("Access allowed")));
    }
}

并定义自定义权限评估器

@Service
public class CustomPermissionEvaluator {

    public boolean hasPrivilege(Authentication auth, String permission) {
        String requiredPermissionCheck = permission.toLowerCase();
        for (GrantedAuthority grantedAuth : auth.getAuthorities()) {
            if (grantedAuth.getAuthority().contains(requiredPermissionCheck)) {
                return true;
            }
        }
        return false;
    }
}

因为这样的网关不提供任何理想的路由授权。

【讨论】:

    猜你喜欢
    • 2021-01-23
    • 1970-01-01
    • 2019-11-10
    • 2019-08-03
    • 2019-03-31
    • 2021-03-30
    • 2023-01-21
    • 2019-04-15
    • 2017-12-02
    相关资源
    最近更新 更多