2SpringBootAdmin-Eureka · SpringCloud微服务实战 · 看云

导航

本节代码地址


上节我们讲解了SpringBoot Admin 的服务端和客户端模式,并且详细介绍了使用。但是有一点非常不方便,就是每个客户端都需要配置服务端的信息,如果应用很多,对应用的维护很不友好。

怎么办呢?

既然我们现在讲的Spring Cloud 是基于服务发现的方式,那么SpringBoot Admin一定也可以使用基于服务发现的方式,如果这样可以的话,那么客户端将不需要指导服务端的地址信息,服务端只需要从注册中心获取已注册上的服务即可。

下面就办它

1 新建服务端

这里我们新建一个服务端模块,方便后续代码的阅读
41d87db91d4d82dc97fb74fac73a7d11_MD5.webp

1.1 添加maven依赖

我们这里使用Eureka演示,因此还是引入spring-cloud-starter-netflix-eureka-client的包,和非Eureka版的相比 maven仅仅多添加了一个包。

<dependencies>
    <dependency>
        <groupId>de.codecentric</groupId>
        <artifactId>spring-boot-admin-starter-server</artifactId>
        <version>2.2.1</version>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-security</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-mail</artifactId>
    </dependency>

    <dependency>
        <groupId>org.springframework.security</groupId>
        <artifactId>spring-security-test</artifactId>
        <scope>test</scope>
    </dependency>

    <dependency>
        <groupId>org.jolokia</groupId>
        <artifactId>jolokia-core</artifactId>
    </dependency>
</dependencies>

1.3 配置Security

这里的配置方式和上一节没有使用Eureka的配置方式一样,这里在重复一遍,我们需要对一些url放行,否则登录页面登录页面无法正常跳转,我们将页面资源和登录退出接口放行。配置好之后,其他url在没有登录的时候会跳转到登录页。

@Configuration
public class FwSecurityConfigure extends WebSecurityConfigurerAdapter {

    private final String adminContextPath;

    public FwSecurityConfigure(AdminServerProperties adminServerProperties) {
        this.adminContextPath = adminServerProperties.getContextPath();
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        SavedRequestAwareAuthenticationSuccessHandler successHandler = new SavedRequestAwareAuthenticationSuccessHandler();
        successHandler.setTargetUrlParameter( "redirectTo" );

        http.authorizeRequests()
                .antMatchers( adminContextPath + "/assets/**" ).permitAll()
                .antMatchers( adminContextPath + "/login" ).permitAll()
                .anyRequest().authenticated()
                .and()
                .formLogin().loginPage( adminContextPath + "/login" ).successHandler( successHandler ).and()
                .logout().logoutUrl( adminContextPath + "/logout" ).and()
                .httpBasic().and()
                .csrf().disable();
    }
}

1.4 新建服务端启动类

这里和非Eureka相比多加了一个@EnableDiscoveryClient注解

@SpringBootApplication
@EnableAdminServer
@EnableDiscoveryClient
public class BootAdminEurekaApplication {
    public static void main(String[] args) {
        SpringApplication.run(BootAdminEurekaApplication.class, args);
    }


}

到此,服务端的配置修改完了

1.2 启动服务端

先启动Eureka注册信息,然后在注册Eureka 上的应用添加配置 ,用于暴露应用的健康信息。

management:
  endpoints:
    web:
      exposure:
        include: "*"
  endpoint:
    health:
      show-details: ALWAYS

16ef386e655d5a57c9e6b240d7ae92e5_MD5.png

浏览器输入http://localhost:8762/,可以看到
496e72cd1b1433b5ca708da0bc71154d_MD5.png

Eureka 上注册的服务信息如下
41f327e0d889175982bc10bdab311e99_MD5.png

可以看到Eureka上注册的应用均在Admin监控中,具体的菜单信息上节已经说明,可以看上节的描述。

自此,SpringBoot Admin 基于Eureka 的改造已经完成。

1.3 Admin 应用异常

如果发现如下异常

java.lang.IllegalStateException: Calling [asyncError()] is not valid for a request with Async state [MUST_DISPATCH]
	at org.apache.coyote.AsyncStateMachine.asyncError(AsyncStateMachine.java:440)
	at org.apache.coyote.AbstractProcessor.action(AbstractProcessor.java:513)
	at org.apache.coyote.Request.action(Request.java:430)
	at org.apache.catalina.core.AsyncContextImpl.setErrorState(AsyncContextImpl.java:401)
	at org.apache.catalina.connector.CoyoteAdapter.asyncDispatch(CoyoteAdapter.java:239)
	at org.apache.coyote.AbstractProcessor.dispatch(AbstractProcessor.java:242)
	at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:53)
	at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:861)
	at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1579)
	at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)
	at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
	at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
	at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
	at java.lang.Thread.run(Thread.java:748)

这个是一个bug ,不影响项目的运行,可以不用关心

如果不想看到这个错误信息,可以将Tomcat 启动换成Jetty

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
            <exclusions>
                <exclusion>
                    <groupId>org.springframework.boot</groupId>
                    <artifactId>spring-boot-starter-tomcat</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-jetty</artifactId>
        </dependency>