16.4 保护 Actuator

对于 Actuator 提供的信息,可能您并不想被间谍窥探到。此外,由于 Actuator 提供了可以更改环境属性,以及调整日志记录级别的操作,那么使只允许具有适当访问权限的客户,才能使用 Actuator 是必要的。

尽管确保 Actuator 的安全非常重要,但 Actuator 并没有提供安全措施的责任。相反,您需要使用 Spring Security 来保护 Actuator。因为 Actuator 端点只是应用程序中的路径,这与应用程序中的任何其他路径没什么区别,所以确保 Actuator 的安全措施,与保证应用程序其他路径的安全措施相比,没有什么独特之处。我们在第 4 章中讨论的所有内容都适用 Actuator 端点。

因为所有的 Actuator 端点都集中在路径 /actuator 下(或者其他路径,如果设置了 management.endpoints.web.base-path 属性),很容易将授权规则应用于 Actuator 端点。例如,要求用户具有要 ROLE_ADMIN 权限,以调用 Actuator 端点,您可以重写 WebSecurityConfigurerAdapter 的 configure() 方法,如下所示:

  1. @Override
  2. protected void configure(HttpSecurity http) throws Exception {
  3. http
  4. .authorizeRequests()
  5. .antMatchers("/actuator/**").hasRole("ADMIN")
  6. .and()
  7. .httpBasic();
  8. }

这要求,所有请求都要来自具有 ROLE_ADMIN 权限的用户。另外还配置了 HTTP 基本身份验证,以便客户端应用程序,可以在请求头 Authorization 属性中,传输编码过的身份验证信息。

以这种方式保护 Actuator 的真正问题是,端点的路径硬编码为 /actuator/** 了。如果修改了 management.endpoints.web.base-path 属性,它将不再工作。为解决这个问题,Spring Boot 还提供了 EndpointRequest,这是一个请求匹配器类。它更容易使用,而且不依赖于给定的字符串路径。使用 EndpointRequest,您可以对 Actuator 端点应用相同的安全配置,而无需硬编码 /actuator/** 路径:

  1. @Override
  2. protected void configure(HttpSecurity http) throws Exception {
  3. http
  4. .requestMatcher(EndpointRequest.toAnyEndpoint())
  5. .authorizeRequests()
  6. .anyRequest().hasRole("ADMIN")
  7. .and()
  8. .httpBasic();
  9. }

EndpointRequest.toAnyEndpoint() 方法返回一个请求匹配器,该匹配器匹配任何 Actuator 端点。如果要从中排除某些端点,可以调用 excluding(),并按名称指定它们:

  1. @Override
  2. protected void configure(HttpSecurity http) throws Exception {
  3. http
  4. .requestMatcher(EndpointRequest.toAnyEndpoint().excluding("health", "info"))
  5. .authorizeRequests()
  6. .anyRequest().hasRole("ADMIN")
  7. .and()
  8. .httpBasic();
  9. }

另一方面,您如果希望对少数 Actuator 进行保护,您可以通过调用 to() 方法,而不是 toAnyEndpoint() 方法:

  1. @Override
  2. protected void configure(HttpSecurity http) throws Exception {
  3. http
  4. .requestMatcher(EndpointRequest.to("beans", "threaddump", "loggers"))
  5. .authorizeRequests()
  6. .anyRequest().hasRole("ADMIN")
  7. .and()
  8. .httpBasic();
  9. }

这将 Actuator 的安全性仅限于 /bean/threaddump/loggers 端点。所有其他 Actuator 端点完全开放。