Springboot 系列(十七)迅速使用 Spring Boot Admin 监控你的 Spring Boot 程序(下)

简介: Springboot 系列(十七)迅速使用 Spring Boot Admin 监控你的 Spring Boot 程序

4. Spring Boot Admin 功能


点击监控页面上的在线的应用实例,可以跳转到应用实例详细的监控管理页面,也就是 Vue.js 实现的 web 展示。


image.png

Spring Boot Admin Server 监控页面


Spring Boot Admin Server 可以监控的功能很多,使用起来没有难度,下面描述下可以监测的部分内容:


  • 应用运行状态,如时间、垃圾回收次数,线程数量,内存使用走势。
  • 应用性能监测,通过选择 JVM 或者 Tomcat 参数,查看当前数值。
  • 应用环境监测,查看系统环境变量,应用配置参数,自动配置参数。
  • 应用 bean 管理,查看 Spring Bean ,并且可以查看是否单例。
  • 应用计划任务,查看应用的计划任务列表。
  • 应用日志管理,动态更改日志级别,查看日志。
  • 应用 JVM 管理,查看当前线程运行情况,dump 内存堆栈信息。
  • 应用映射管理,查看应用接口调用方法、返回类型、处理类等信息。


上面提到的日志管理,可以动态的更改日志级别,以及查看日志。默认配置下是只可以动态更改日志级别的,如果要在线查看日志,就需要手动配置日志路径了。


客户端上可以像下面这样配置日志路径以及日志高亮。


# 配置文件:application.yml
logging:
  file:
    name: boot.log
  pattern:
#     日志高亮
    file: '%clr(%d{yyyy-MM-dd HH:mm:ss.SSS}){faint} %clr(%5p) %clr(${PID}){magenta} %clr(---){faint} %clr([%15.15t]){faint} %clr(%-40.40logger{39}){cyan} %clr(:){faint} %m%n%wEx'


下面是在 Spring Boot Admin 监测页面上查看的客户端应用日志。


image.png


Spring Boot Admin Server 查看日志


5. Spring Boot Admin 进阶


5.1. 邮件通知


Spring Boot Admin Server 支持常见的通知方式,比如邮件通知、电报通知、PagerDuty 通知等,下面将会演示常见的通知方式 - 邮件通知,最后也会演示如何通过监听时间进下设置自定义通知方式。


Spring Boot Admin Server 的邮件通知通过 Thymeleaf 模板发送 HTML 格式的电子邮件。因此,想要使用邮件通知首先要引入 Thymeleaf 依赖以及 spring-boot-starter-mail 依赖,并配置邮件发送者信息和接受者信息。


1. 添加依赖


<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
    <groupId>de.codecentric</groupId>
    <artifactId>spring-boot-admin-starter-server</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-mail</artifactId>
</dependency>
<!-- Thymeleaf 模版,用于发送模版邮件 -->
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>


2. 配置邮件


主要设置发送者信息和接收者信息。


spring:
  boot:
    admin:
      notify:
        mail:
          # 逗号分隔的邮件收件人列表
          to: xxxx@126.com
          # 开启邮箱通知
          enabled: true
          # 不需要发送通知的状态:从状态A:到状态B
          ignore-changes: {"UNKNOWN:UP"}
          # 逗号分隔的抄送收件人列表
          cc: xxxx@126.com
          # 发件人
          from: Spring Boot Admin<xxxx@126.com>
# 邮件发送者信息
  mail:
    host: smtp.126.com
    port: 25
    username: xxxx@126.com
    default-encoding: utf-8
    password: xxxx


如果想了解更多关于 Spring Boot 邮件发送信息,可以参考 Spring Boot 系列文章第十三篇


配置好邮件通知之后,重启服务端和客户端,等客户端注册到服务端之后直接终止客户端的运行,稍等片刻就可以在配置的通知接收邮箱里收到客户端实例下线通知了。


image.png


Sping Boot Admin Server 邮件通知


邮件通知使用的模板存放在 server 依赖的 classpath:/META-INF/spring-boot-admin-server/mail/status-changed.html 路径,如果想要自定义模板内容。可以拷贝这个文件放到自己的 templates 目录下,修改成自己想要的效果,然后在配置中指定自定义模板路径。


spring:
  boot:
    admin:
      notify:
        mail:
          # 自定义邮件模版
          template: classpath:/templates/notify.html


5.2 自定义通知


自定义通知只需要自己实现 Spring Boot Admin Server 提供的监听通知类即可,下面会演示如何在实例状态改变时输出实例相关信息。


import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
import de.codecentric.boot.admin.server.domain.entities.Instance;
import de.codecentric.boot.admin.server.domain.entities.InstanceRepository;
import de.codecentric.boot.admin.server.domain.events.InstanceEvent;
import de.codecentric.boot.admin.server.domain.events.InstanceStatusChangedEvent;
import de.codecentric.boot.admin.server.notify.AbstractEventNotifier;
import de.codecentric.boot.admin.server.notify.LoggingNotifier;
import reactor.core.publisher.Mono;
@Component
public class CustomNotifier extends AbstractEventNotifier {
    private static final Logger LOGGER = LoggerFactory.getLogger(LoggingNotifier.class);
    public CustomNotifier(InstanceRepository repository) {
        super(repository);
    }
    @Override
    protected Mono<Void> doNotify(InstanceEvent event, Instance instance) {
        return Mono.fromRunnable(() -> {
            if (event instanceof InstanceStatusChangedEvent) {
                LOGGER.info("Instance {} ({}) is {}", instance.getRegistration().getName(), event.getInstance(),
                    ((InstanceStatusChangedEvent)event).getStatusInfo().getStatus());
            } else {
                LOGGER.info("Instance {} ({}) {}", instance.getRegistration().getName(), event.getInstance(),
                    event.getType());
            }
        });
    }
}


5.2. 访问限制


上面提到过,因为客户端增加了暴漏运行信息的相关接口,所以在生产环境中使用存在风险,而服务端没有访问限制,谁的可以访问也是不合理的。


下面将会为客户端和服务端分别增加访问限制,客户端主要是限制敏感接口的访问权限,服务端则是全局的访问限制。这些访问限制都通过 spring 安全框架 security 来实现,所以首先要为客户端和服务端都增加 maven 依赖。


<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-security</artifactId>
</dependency>


1. 服务端


在引入安全框架依赖之后,需要配置访问控制,比如静态资源不需要限制,登录登出页面指定等。


import java.util.UUID;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.web.authentication.SavedRequestAwareAuthenticationSuccessHandler;
import org.springframework.security.web.csrf.CookieCsrfTokenRepository;
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
import de.codecentric.boot.admin.server.config.AdminServerProperties;
import io.netty.handler.codec.http.HttpMethod;
@Configuration(proxyBeanMethods = false)
public class SecuritySecureConfig extends WebSecurityConfigurerAdapter {
    private final AdminServerProperties adminServer;
    public SecuritySecureConfig(AdminServerProperties adminServer) {
        this.adminServer = adminServer;
    }
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        // @formatter:off
        SavedRequestAwareAuthenticationSuccessHandler successHandler = new SavedRequestAwareAuthenticationSuccessHandler();
        successHandler.setTargetUrlParameter("redirectTo");
        successHandler.setDefaultTargetUrl(this.adminServer.path("/"));
        http.authorizeRequests()
                .antMatchers(this.adminServer.path("/assets/**")).permitAll()
                .antMatchers(this.adminServer.path("/login")).permitAll()
                .anyRequest().authenticated()
                .and()
                .formLogin().loginPage(this.adminServer.path("/login")).successHandler(successHandler).and()
                .logout().logoutUrl(this.adminServer.path("/logout")).and()
                .httpBasic().and()
                .csrf()
                .csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse())
                .ignoringRequestMatchers(
                        new AntPathRequestMatcher(this.adminServer.path("/instances"), HttpMethod.POST.toString()),
                        new AntPathRequestMatcher(this.adminServer.path("/instances/*"), HttpMethod.DELETE.toString()),
                        new AntPathRequestMatcher(this.adminServer.path("/actuator/**"))
                )
                .and()
                .rememberMe().key(UUID.randomUUID().toString()).tokenValiditySeconds(1209600);
        // @formatter:on
    }
    // 代码配置用户名和密码的方式
    // Required to provide UserDetailsService for "remember functionality"
    // @Override
    // protected void configure(AuthenticationManagerBuilder auth) throws Exception {
    // auth.inMemoryAuthentication().withUser("user").password("{noop}password").roles("USER");
    // }
}


在 application.yml 配置文件中配置用户名和密码。


spring:
  security:
    user:
      name: user
      password: 123


重启服务端,再次访问就需要用户名和密码进行登录了。


image.png


Spring Boot Admin Server 登录


2. 客户端


客户端在引入安全框架之后,也需要配置访问权限,主要是配置哪些路径可以访问,哪些路径访问需要登录限制,默认所有接口都需要登录限制。


同样的,客户端应用也需要在配置中配置客户端应用对于敏感接口的登录用户和密码,同时需要配置 Spring Boot Admin Server 的访问用户和密码,还要把自身的用户和密码注册时告诉服务端,不然服务端不能获取到监测数据。


spring:
  security:
    user:
      # 客户端敏感接口用户和密码
      name: client
      password: 123
  application:
    # 应用名称
    name: sjfx-api-search
  jmx:
    enabled: true
  boot:
    admin:
      client:
        # 服务端 url
        url: http://127.0.0.1:9090
        instance:
          # 客户端实例 url
          service-url: http://127.0.0.1:8080
          prefer-ip: true
          # 客户端实例名称
          name: sjfx-api-search
          metadata:
            # 客户端自身的用户和密码告诉服务端
            user.name: client
            user.password: 123
        # 服务端用户名密码
        username: user
        password: 123


客户端敏感接口访问测试。


image.png


客户端应用访问


到这里,客户端的敏感接口访问需要登录,服务端的管理页面也需要登录,客户端和服务端的访问控制已经完成了。


文中代码已经上传到:github.com/niumoo/springboot/tree/master/springboot-admin


参考资料:


https://github.com/codecentric/spring-boot-admin

https://codecentric.github.io/spring-boot-admin/current/

相关实践学习
日志服务之使用Nginx模式采集日志
本文介绍如何通过日志服务控制台创建Nginx模式的Logtail配置快速采集Nginx日志并进行多维度分析。
相关文章
|
26天前
|
Java 应用服务中间件 Maven
SpringBoot 项目瘦身指南
SpringBoot 项目瘦身指南
40 0
|
1月前
|
Java 测试技术 数据库
SpringBoot:@Profile注解和Spring EL
SpringBoot:@Profile注解和Spring EL
|
1月前
|
存储 安全 Java
Spring Boot整合Spring Security--学习笔记
Spring Boot整合Spring Security--学习笔记
53 0
|
1月前
|
消息中间件 Cloud Native Java
【Spring云原生系列】SpringBoot+Spring Cloud Stream:消息驱动架构(MDA)解析,实现异步处理与解耦合
【Spring云原生系列】SpringBoot+Spring Cloud Stream:消息驱动架构(MDA)解析,实现异步处理与解耦合
|
1月前
|
人工智能 JSON 前端开发
【Spring boot实战】Springboot+对话ai模型整体框架+高并发线程机制处理优化+提示词工程效果展示(按照框架自己修改可对接市面上百分之99的模型)
【Spring boot实战】Springboot+对话ai模型整体框架+高并发线程机制处理优化+提示词工程效果展示(按照框架自己修改可对接市面上百分之99的模型)
|
15天前
|
安全 数据安全/隐私保护
Springboot+Spring security +jwt认证+动态授权
Springboot+Spring security +jwt认证+动态授权
|
1月前
|
消息中间件 JSON Java
Spring Boot、Spring Cloud与Spring Cloud Alibaba版本对应关系
Spring Boot、Spring Cloud与Spring Cloud Alibaba版本对应关系
452 0
|
5天前
|
安全 Java 应用服务中间件
江帅帅:Spring Boot 底层级探索系列 03 - 简单配置
江帅帅:Spring Boot 底层级探索系列 03 - 简单配置
14 0
江帅帅:Spring Boot 底层级探索系列 03 - 简单配置
|
7天前
|
XML Java C++
【Spring系列】Sping VS Sping Boot区别与联系
【4月更文挑战第2天】Spring系列第一课:Spring Boot 能力介绍及简单实践
30 0
【Spring系列】Sping VS Sping Boot区别与联系
|
15天前
|
Java 容器
SpringBoot使用配置注解开启自动配置功能&整合spring-boot-configuration-processor
SpringBoot使用配置注解开启自动配置功能&整合spring-boot-configuration-processor
13 0