当前位置: 首页 > 知识库问答 >
问题:

使用Spring Security进行Spring Boot测试。如何启动替代安全配置?

申高峯
2023-03-14

我的spring boot应用程序有一个application类。当我(作为应用程序)运行它时,它会在嵌入式servlet容器(在我的例子中是Tomcat)中启动自己。以某种方式(我想是通过应用程序的@Annotations),加载了同一包中的WebSecurityConfig(扩展WebSecurityConfigurerAdapter)。

WebSecurityConfig包含两个重要的配置信息块:

@Configuration
@Order(SecurityProperties.ACCESS_OVERRIDE_ORDER)
@EnableGlobalMethodSecurity(prePostEnabled = true) // enables method-level role-checking
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {

    @Autowired
    public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
      auth
         .ldapAuthentication()
         .userSearchBase("CN=Users,DC=some,DC=domain,DC=com")   
         .userSearchFilter("(sAMAccountName={0})")
         .groupSearchBase("OU=Groups,DC=some,DC=domain,DC=com")                 
         .groupSearchFilter("(member={0})")
         .contextSource()
            .managerDn("cn=ad-bind,cn=users,dc=some,dc=domain,dc=com")
            .managerPassword("APASSWORD!") 
            .url("ldaps://some.domain.com:636");
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
         System.out.println("***************** WebSecurityConfig.configure *************************");
         http.csrf().disable();

         http
            .headers()
                .frameOptions()
                    .disable();

         http
                .authorizeRequests()
                    .antMatchers("/resources/images/*", "/me", "/products", "/product/**", "/offerings", "/offering/**", "/client/**")
                            .permitAll()
                    .anyRequest().authenticated()
                    .and()
                    .formLogin()
                    .loginPage("/login").defaultSuccessUrl("/me")
                    .permitAll()
                    .and()
                    .logout()
                    .permitAll();

         http.logout().logoutSuccessUrl("/me");
    }
}

configureGlobal()包含我们内部LDAP系统的配置,它工作得很好。

configure()指定哪些URL是公共的,哪些URL只显示给登录的用户,以及在用户登录时将其发送到哪些相对URL。

@RunWith(SpringJUnit4ClassRunner.class)
@SpringApplicationConfiguration(classes = TestApplication.class) // fires up with TestApplication.class instead of Application.class
@WebAppConfiguration
public class ProductControllerTests {
    // test methods here, this time with username/password included
}

@Configuration
@EnableAutoConfiguration
public class TestApplication extends SpringBootServletInitializer {

    public static void main(String[] args) {
        SpringApplication.run(applicationClass, args);
    }

    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(applicationClass);
    }

    private static Class<TestApplication> applicationClass = TestApplication.class;

}

@Configuration
@Order(SecurityProperties.ACCESS_OVERRIDE_ORDER)
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {

    @Autowired
    public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
      auth.inMemoryAuthentication().withUser("testuser").password("userpass").roles("USER");
      auth.inMemoryAuthentication().withUser("testadmin").password("adminpass").roles("ADMIN");
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
         System.out.println("***************** WebSecurityConfig.configure *************************");
         http.csrf().disable();

         http
            .headers()
                .frameOptions()
                    .disable();

         http
                .authorizeRequests()
                    .antMatchers("/resources/images/*", "/me", "/products", "/product/**", "/offerings", "/offering/**", "/client/**")
                            .permitAll()
                    .anyRequest().authenticated()
                    .and()
                    .formLogin()
                    .loginPage("/login").defaultSuccessUrl("/me")
                    .permitAll()
                    .and()
                    .logout()
                    .permitAll();

         http.logout().logoutSuccessUrl("/me");
    }
}

所以我的问题是:当我执行单元测试类时,我相信TestApplication正在触发。但是,它并没有接收替代的WebSecurityConfig类及其auth.inMemoryAuthentication()测试用户。如何强制应用程序在正常运行应用程序时使用一个WebSecurityConfig,而在运行单元测试时使用另一个WebSecurityConfig?

共有1个答案

汤飞羽
2023-03-14

您可以将TestApplication配置为只包含您想要测试的bean。换句话说,确保您的websecurityconfig不是测试配置的一部分。如果您阅读了@SpringBootApplication的javadoc,您会注意到它是一个复合注释,其中包括@ComponentScan注释。因此,applicationtestapplication将从类所在的包执行递归扫描。Spring reference docs有一个关于使用过滤器自定义扫描的特定章节。

或者,如果您使用的是Spring Security版本4或更高版本,您可能会发现@WithMockUser和@WithUserDetails的添加很有趣。

 类似资料:
  • 本文向大家介绍如何使用SpringSecurity保护程序安全,包括了如何使用SpringSecurity保护程序安全的使用技巧和注意事项,需要的朋友参考一下 首先,引入依赖: 引入此依赖之后,你的web程序将拥有以下功能: 所有请求路径都需要认证 不需要特定的角色和权限 没有登录页面,使用HTTP基本身份认证 只有一个用户,名称为user 配置SpringSecurity springsecur

  • 我为spring-boot创建了一个spring安全配置类。我的登录页面有资源css、js和ico文件。这些资源由于安全原因而被拒绝,并且每次都被重定向到登录页面。为什么EnableWebMVCSecurity不添加类路径资源位置。在更改代码后,如第二个代码片段所示,将添加I Classpath资源位置。不明白第一段代码中的资源缺少什么。 我通过将代码更改为 在更改代码之后,我注意到忽略路径被添加

  • 从2.0.6开始使用spring boot starter test会带来JUnit 4依赖性。如何使用spring boot starter test(通过Gradle),但使用JUnit 5,而不引入JUnit 4依赖项? 如果有帮助,这是Gradle的部分依赖输出: 这是我的身材。gradle文件: 添加JUnit 5依赖项并执行注释中提到的排除就完成了。测试依赖项现在如下所示:

  • 我想测试我的SpringBoot应用程序,它使用cassandra作为CrudRepository。我最终得到了 具有 和 这就导致了 如果我使用旧版本的cassandra-unit-Spring 它以NullPointerException结束,因为没有注入值repo。 来源https://github.com/StephanPraetsch/spring.boot.cassandra.unit

  • 我正在使用Spring引导安全层来验证和授权user.Now,我想使用多超文本传输协议安全配置做一些示例应用程序。我有这样的场景,比如将有两个具有不同URL映射的登录页面(“/Management ementLogin”、“/thersLogin”)。 我可以理解如何配置多httpSecurity配置,但我需要验证用户从两个tables.If管理用户登录我需要验证用户从管理表通过DAO层使用否则,

  • 我有一个依赖Spring批处理JobLauncher的类。 我想使用这个JobLauncher的异步版本,所以我创建了一个配置: 我不得不使用,否则当应用程序运行时,其他一些同步JobLauncher会被选中。 现在,在我的测试中,我想使用同步版本来验证作业执行的结果。因此,我在配置中定义了同步bean: 然而,当我的测试运行时。。它总是使用异步版本,我的结果不正确。 是否有一种方法可以在我的测试