如何将用户的身份验证(和授权)传播到其他微服务

时间:2019-09-09 03:01:25

标签: spring-boot spring-security microservices

我已经为登录页面创建了一个微服务(使用Spring Boot)。用户提供凭据,成功登录后,他可以看到仪表板。我使用了 RestTemplate 以便从仪表板遍历到其他微服务。下面是代码片段:

    @Autowired
private RestTemplate restTemplate;

@GetMapping("/employeeCenter")
public String openEmployeeCenterApp() {
    logger.info("Invoking EmployeeCenter micro-service");
    return restTemplate.getForEntity("http://EMPLOYEE-SERVICE/empCenter/", String.class).getBody();
}

哪个工作正常。但是我想将用户的身份验证(和授权)传播到任何其他微服务。这样我就可以根据用户的权限显示/隐藏内容。合适的方法是什么?

2 个答案:

答案 0 :(得分:0)

您可以尝试使用WebSecurityConfigurerAdapter并覆盖AuthenticationManagerBuilder bean的配置,这将使您设置角色。

本文有一个很好的例子:https://www.journaldev.com/8748/spring-security-role-based-access-authorization-example

答案 1 :(得分:0)

这里有很多问题。

当“着陆页”服务(简称为“ A”)显示身份为“ Foo”的用户的仪表板并尝试通过Rest模板联系另一个服务“ B”(这是另一个过程)时,您应该实施“ Foo”的身份传播,而不是弹簧安全性的工作。 Spring安全性将帮助您在用户“ Foo” 内部的服务“ A”中进行身份验证/授权,但与身份传播无关。

毕竟,服务“ B”可能根本不是用spring或java编写的,甚至根本不是外部系统的。

根据需求,这里有很多方法,通常归结为:

  1. 仅靠着陆页(服务A)是您通往外部世界的“门户”,因此此服务需要安全性

  2. 保护所有服务(例如在每个服务中放置spring安全性或任何其他安全性组件)

  3. 类似于“ 1”,但区分安全网关和登录页面-具有两个微服务,因此网关将受到保护,并且将“开放”给最终用户,也将开放给内部通信。区别在于,如果需要从服务“ A”调用服务“ B”,则可以通过网关进行操作,它将检查安全性

这里的另一个问题是从服务A调用服务B的“行为”的确切含义。

  • 一件事是告诉“我是Foo用户(当前在服务A中),我将B称为Foo。
  • 另一件事是告诉“我是服务A(具有其自己的身份),并且我代表用户Foo调用服务B”。

所有这些问题都在与安全性相关的体系结构领域中,可以采用许多解决方案。如果您必须进行这样的分析(尽管这种分析超出了此问题的范围),请确保您了解每种方法对性能的影响:  -HTTP跃点可能很昂贵  -DB跃点(以防万一您不得不转向数据库)很昂贵 尽可能应用缓存

现在,从技术上来讲,如果您运行反应堆,您应该提供一些过滤器,该过滤器将添加从线程本地或类似解决方案中获取的身份标头。 因此,在最简单的情况下,您可以将标识对象放在本地的某个线程上,并将其放入过滤器中以添加请求。

因此,当您在RestTemplate中构造请求时(取决于okHttp,Apache Http Client或其他东西),最重要的一点是它将具有附加的标头,这些标头将提供身份信息(由您自己决定是什么)正是这里的“身份”。

服务“ B”又应使用某种过滤器再次解析该对象(如果“ B”也处于弹簧状态,则最好在到达其余控制器之前),或者如果已经将其安装在服务中,则具有弹簧安全性B,然后根据该身份做出“保护决定”,然后再次将其放置在线程本地,以供B查询其他服务等等。