有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java Spring引导管理页面客户端开放端点

我有一个spring boot管理服务器。以下是服务器的文件:

pom.xml

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>1.5.17.RELEASE</version>
    <relativePath/> <!-- lookup parent from repository -->
</parent>

<properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
    <java.version>1.8</java.version>
    <spring-boot-admin.version>1.5.7</spring-boot-admin.version>
</properties>

<dependencies>
    <dependency>
        <groupId>de.codecentric</groupId>
        <artifactId>spring-boot-admin-server</artifactId>
    </dependency>
    <dependency>
        <groupId>de.codecentric</groupId>
        <artifactId>spring-boot-admin-server-ui</artifactId>
    </dependency>
    <dependency>
        <groupId>de.codecentric</groupId>
        <artifactId>spring-boot-admin-server-ui-login</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-security</artifactId>
    </dependency>
</dependencies>

<dependencyManagement>
    <dependencies>
        <dependency>
            <groupId>de.codecentric</groupId>
            <artifactId>spring-boot-admin-dependencies</artifactId>
            <version>${spring-boot-admin.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
    </dependencies>
</dependencyManagement>

<build>
    <plugins>
        <plugin>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-maven-plugin</artifactId>
        </plugin>
    </plugins>
</build>

application.properties

spring.application.name=spring-boot-admin-server

security.user.name=admin
security.user.password=admin
server.port = 9090

WebSecurityConfig.java

@Configuration
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
                .formLogin()
                .loginPage("/login.html")
                .loginProcessingUrl("/login")
                .permitAll();
        http
                .logout().logoutUrl("/logout");
        http
                .csrf().disable();
        http
                .authorizeRequests()
                .antMatchers("/login.html", "/**/*.css", "/img/**", "/third-party/**")
                .permitAll();
        http
                .authorizeRequests()
                .antMatchers("/**")
                .authenticated();
        http.httpBasic();
    }
}

服务器已启动并运行,可在^{访问。但是,当我启动客户端应用程序时,它会注册到服务器上,但由于安全原因,我认为没有一个端点是可访问的

以下是管理页面的外观: enter image description here

由于某些原因,应用程序总是显示为关闭。我在服务器控制台中遇到以下错误:

2018-11-21 15:02:21.475  INFO 1893 --- [    updateTask1] d.c.boot.admin.registry.StatusUpdater    : Couldn't retrieve info for Application [id=d83f0885, name=PETE, managementUrl=http://localhost:8081/demo/, healthUrl=http://localhost:8081/demo/health/, serviceUrl=http://localhost:8081/demo/]: 403 - {timestamp=1542834141473, status=403, error=Forbidden, message=Access Denied, path=/demo/login}

我的演示应用程序是一个带有登录页面的web应用程序。它具有以下依赖性:

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-hateoas</artifactId>
</dependency>
<dependency>
    <groupId>de.codecentric</groupId>
    <artifactId>spring-boot-admin-starter-client</artifactId>
    <version>1.5.7</version>
</dependency>

它具有spring boot安全性,下面是安全配置类:

@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
  @Autowired
  private AuthenticationManager authenticationManager;
  @Autowired
  private AuthenticationFailureHandler failureHandler;
  @Autowired
  private JwtAuthenticationProvider jwtAuthenticationProvider;
  @Autowired
  private Environment env;

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.csrf().disable()
                .addFilterBefore(buildJwtTokenAuthenticationProcessingFilter(),
                        UsernamePasswordAuthenticationFilter.class)
                .logout().invalidateHttpSession(true).deleteCookies("token", "JSESSIONID")
                .logoutSuccessUrl(Routes.LOGOUT.getValue()).and().exceptionHandling().accessDeniedPage("/403");
        // Disable HSTS so that "proceed anyways" works for SSL certs
        http.headers().httpStrictTransportSecurity().disable();
    }

    protected JwtTokenAuthenticationProcessingFilter buildJwtTokenAuthenticationProcessingFilter() throws Exception {
        List<String> pathsToSkip = Arrays.asList("/login", "/loginPost", "/login-failure", "/error",
                "/**/*.js", "/**/*.png", "/**/*.css", "/**/*.woff*", "/**/*.ttf");
        SkipPathRequestMatcher matcher = new SkipPathRequestMatcher(pathsToSkip, "/**");
        JwtTokenAuthenticationProcessingFilter filter = new JwtTokenAuthenticationProcessingFilter(failureHandler,
                matcher, env);
        filter.setAuthenticationManager(this.authenticationManager);
        return filter;
    }

    @Bean
    @Override
    public AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }

    @Override
    protected void configure(AuthenticationManagerBuilder auth) {
        auth.authenticationProvider(jwtAuthenticationProvider);
    }

    @Bean(name = "loginAuthenticationRestTemplateBean")
    RestTemplate restTemplate() {
        return new RestTemplate();
    }
}

我需要在客户端做些什么来打开执行器端点,以便管理页面可以访问它们并显示正确的状态

编辑1:管理服务器控制台中还有一个错误:

org.springframework.web.client.RestClientException: Could not extract response: no suitable HttpMessageConverter found for response type [interface java.util.Map] and content type [text/html;charset=UTF-8]
    at org.springframework.web.client.HttpMessageConverterExtractor.extractData(HttpMessageConverterExtractor.java:110) ~[spring-web-4.3.20.RELEASE.jar:4.3.20.RELEASE]
    at org.springframework.web.client.RestTemplate$ResponseEntityResponseExtractor.extractData(RestTemplate.java:932) ~[spring-web-4.3.20.RELEASE.jar:4.3.20.RELEASE]
    at org.springframework.web.client.RestTemplate$ResponseEntityResponseExtractor.extractData(RestTemplate.java:916) ~[spring-web-4.3.20.RELEASE.jar:4.3.20.RELEASE]
    at org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:663) ~[spring-web-4.3.20.RELEASE.jar:4.3.20.RELEASE]
    at org.springframework.web.client.RestTemplate.execute(RestTemplate.java:636) ~[spring-web-4.3.20.RELEASE.jar:4.3.20.RELEASE]
    at org.springframework.web.client.RestTemplate.exchange(RestTemplate.java:557) ~[spring-web-4.3.20.RELEASE.jar:4.3.20.RELEASE]
    at de.codecentric.boot.admin.web.client.ApplicationOperations.doGet(ApplicationOperations.java:68) ~[spring-boot-admin-server-1.5.7.jar:na]
    at de.codecentric.boot.admin.web.client.ApplicationOperations.getHealth(ApplicationOperations.java:58) ~[spring-boot-admin-server-1.5.7.jar:na]
    at de.codecentric.boot.admin.registry.StatusUpdater.queryStatus(StatusUpdater.java:111) [spring-boot-admin-server-1.5.7.jar:na]
    at de.codecentric.boot.admin.registry.StatusUpdater.updateStatus(StatusUpdater.java:65) [spring-boot-admin-server-1.5.7.jar:na]
    at de.codecentric.boot.admin.registry.StatusUpdateApplicationListener$1.run(StatusUpdateApplicationListener.java:47) [spring-boot-admin-server-1.5.7.jar:na]
    at org.springframework.scheduling.support.DelegatingErrorHandlingRunnable.run(DelegatingErrorHandlingRunnable.java:54) [spring-context-4.3.20.RELEASE.jar:4.3.20.RELEASE]
    at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) [na:1.8.0_121]
    at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) [na:1.8.0_121]
    at java.util.concurrent.FutureTask.run(FutureTask.java) [na:1.8.0_121]
    at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.access$201(ScheduledThreadPoolExecutor.java:180) [na:1.8.0_121]
    at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:293) [na:1.8.0_121]
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) [na:1.8.0_121]
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) [na:1.8.0_121]
    at java.lang.Thread.run(Thread.java:745) [na:1.8.0_121]

我尝试添加此消息转换器:

@Configuration
public class WebMvcConfig extends WebMvcConfigurerAdapter {
    /**
     * {@inheritDoc}
     * <p>This implementation is empty.
     *
     * @param converters
     */
    @Override
    public void extendMessageConverters(List<HttpMessageConverter<?>> converters) {
        List<HttpMessageConverter<?>> newConverters = converters.stream().filter(c -> !(c instanceof MappingJackson2HttpMessageConverter)).collect(Collectors.toList());
        MappingJackson2HttpMessageConverter converter = new MappingJackson2HttpMessageConverter();
        // Note: here we are making this converter to process any kind of response,
        // not only application/*json, which is the default behaviour
        converter.setSupportedMediaTypes(Collections.singletonList(MediaType.ALL));
        newConverters.add(converter);

        converters.clear();
        converters.addAll(newConverters);
    }
}

还是一样的错误


共 (1) 个答案

  1. # 1 楼答案

    根据this documentation的说明,只需设置下面的属性就可以在没有安全性的情况下暴露执行器端点

    management.security.enabled=false
    

    如果仍然不起作用,那么您可能需要修改客户端configure(HttpSecurity)方法,如下所示

    '''
            .authorizeRequests()
            .antMatchers("/actuator-end-points").permitAll()
            .and()
            .addFilterBefore(jwtTokenAuthenticationFilter(), UsernamePasswordAuthenticationFilter.class)
    '''