标签: spring-boot-test

对于 @TestConfiguration 类的 @SpringBootTest @Import 不执行任何操作,而 @ContextConfiguration 按预期覆盖

考虑以下集成测试注释:

@RunWith(SpringRunner.class)
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.NONE,
                properties = "spring.main.allow-bean-definition-overriding=true")
@ContextConfiguration(classes = {WorkerTestConfig.class})
//@Import(value = {WorkerTestConfig.class})
@ActiveProfiles({"dev","test"})
public class NumberServiceITest {
Run Code Online (Sandbox Code Playgroud)

WorkestTestConfig 的作用是在集成启动期间覆盖真实 bean/一组 bean,每当我使用@ContextConfiguration真实 bean 时,真实 bean 就会退出并使用 WorkerTestConfig 中的 bean,每当我使用真实 bean 时,@Import仍然会创建真实 bean 并导致测试失败。

WorkerTestConfig本身尽可能简单:

@TestConfiguration
public class WorkerTestConfig {

    @Primary
    @Bean
    public ScheduledExecutorService taskExecutor() {
        return DirectExecutorFactory.createSameThreadExecutor();
    }
}
Run Code Online (Sandbox Code Playgroud)

谁能解释一下 @SpringBootTest 注释的另一个神奇行为?如果您重现相同的行为,请确认,以便我可以转到问题跟踪器,因为我已经看到人们在此处 使用@Importwith ,并且在 Spring Boot 文档中没有任何内容禁止它:https: //docs.spring.io/spring-boot/文档/current/reference/html/boot-features-testing.html#boot-features-testing-spring-boot-applications-排除-config@SpringBootTest

完全不知道发生了什么。

版本:2.1.2.RELEASE

更新:

还尝试删除真正的bean,看看问题是否只是覆盖,但@Import注释只是死在水中,不起作用 - >甚至无法创建bean,@ContextConfiguration具有附加/覆盖行为,导入在全部。注释的完全限定导入是: import org.springframework.context.annotation.Import;

也试图从 到 …

spring-boot spring-boot-test

5
推荐指数
1
解决办法
8403
查看次数

如何使用@TestConfiguration来避免src/test/java扫描?

根据25.3.3。排除测试配置,此功能存在:

当放置在顶级类上时,@TestConfiguration表示 不应通过扫描拾取src/test/java中的类

我在项目的根路径/包中创建了@Configuration FilledWithBeanTestConfig和。我的包含方法的类故意注释为只是为了意外地选择; 对于这种情况Spring特别警告: @TestConfiguration DummyTestConfigsrc/test/java/com/example/mvctries/main@ComponentScanFilledWithBeanTestConfig

如果您的应用程序使用组件扫描(例如,如果您使用 @SpringBootApplication 或 @ComponentScan),您可能会发现仅为特定测试创建的顶级配置类被意外地到处拾取。

我在放置在的带注释的测试类@Import(DummyTestConfig.class)中使用了;我原以为会被忽略,但事实并非如此。搬到也没有帮助 。@WebMvcTestsrc/test/java/com/example/mvctries/controller/@Configuration FilledWithBeanTestConfigDummyTestConfigsrc/test/java/com/example/mvctries/controller/

在测试上述src/test/java扫描忽略功能的方式时,我做错了什么?
我应该如何正确使用@TestConfiguration才能使用这种src/test/java扫描忽略功能?
我如何通过@SpringBootApplication仅使用组件扫描而不是使用进行有意扫描来测试此功能@ComponentScan

虽然上述问题可能看起来太多,但它们实际上是提出以下问题的另一种方式如何制作一个项目,以清楚地证明@TestConfiguration使用情况如何导致src/test/java 中的类不应该通过扫描来获取

更新

这是示例项目:https ://github.com/adrhc/spring-boot-test-checks.git ;运行应用程序时使用端口 8083;更好地运行测试类。

spring-boot-test

5
推荐指数
1
解决办法
1774
查看次数

SpringBootTest - 如果上下文加载失败如何断言

我编写了一个ApplicationListener来检查上下文初始化期间是否准备好环境。由于我在configure()main()方法中手动添加侦听器,因此我在测试该场景时遇到了问题。

应用程序监听器类:

public class EnvironmentPrepared implements ApplicationListener<ApplicationEnvironmentPreparedEvent> {

        @Override
    public void onApplicationEvent(ApplicationEnvironmentPreparedEvent event) {
            //code that checks if conditions are met

            if (checkTrue) {
            throw new RuntimeException();
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

主要类别:

    public class MyApp extends SpringBootServletInitializer {

    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        setRegisterErrorPageFilter(false);
        return application.listeners(new EnvironmentPrepared()).sources(MyApp.class);
    }

    public static void main(String[] args) {
        SpringApplication springApplication = new SpringApplication(MyApp.class);
        springApplication.addListeners(new EnvironmentPrepared());
        springApplication.run(args);
    }
}
Run Code Online (Sandbox Code Playgroud)

我要执行的测试:

@RunWith(SpringRunner.class)
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@ContextConfiguration(loader = OverriddenProfilesTest.CustomLoader.class)
public class …
Run Code Online (Sandbox Code Playgroud)

integration-testing listener spring-boot spring-boot-test

5
推荐指数
1
解决办法
1539
查看次数

使用Flyway和Spring boot迁移docker testcontainers环境中的模式

我正在尝试在 Spring Boot 应用程序中使用 testcontainers 和 Flyway 设置测试环境。所有这一切都应该通过 DinD 方案运行。

目前测试示例如下:

import com.testapp.testapp.entity.TestEntity
import com.testapp.testapp.service.TestService
import org.junit.Test
import org.junit.runner.RunWith
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.boot.autoconfigure.flyway.FlywayAutoConfiguration
import org.springframework.boot.test.context.SpringBootTest
import org.springframework.context.annotation.Import
import org.springframework.test.context.ContextConfiguration
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner
import org.testcontainers.containers.PostgreSQLContainer
import org.testcontainers.spock.Testcontainers
import spock.lang.Shared
import spock.lang.Specification

@Testcontainers
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration
@SpringBootTest
@Import([FlywayAutoConfiguration.class])
class ApplicationTests extends Specification {

    @Shared
    PostgreSQLContainer postgreSQLContainer = new PostgreSQLContainer()
            .withDatabaseName("testdb")
            .withUsername("postgres")
            .withPassword("12345")

    @Autowired
    public TestService testappService;

    @Test
    def "entity_created"(){
        given: "init test entity"
        UUID uuid = UUID.randomUUID();
        when: "create test entity"
        def testEntity = …
Run Code Online (Sandbox Code Playgroud)

spock docker spring-boot-test testcontainers

5
推荐指数
1
解决办法
5372
查看次数

Spring Boot OpenFeign 随机端口测试

我有一个 OpenFeign 客户端设置如下:

@FeignClient(name = "myService", qualifier = "myServiceClient", url = "${myservice.url}")
public interface MyServiceClient {
...
}
Run Code Online (Sandbox Code Playgroud)

Spring Boot 测试设置如下:

@SpringBootTest(webEnvironment = RANDOM_PORT, classes = MyApplication.class)
@RunWith(SpringRunner.class)
@EnableFeignClients(clients = MyServiceClient .class)
public class ReservationSteps {
...
}
Run Code Online (Sandbox Code Playgroud)

该测试应该启动应用程序并使用 Feign 客户端向其发送请求。

问题是 RANDOM_PORT 值。

如何在属性文件中声明“myservice.url”属性,以便它包含正确的端口?

我已经尝试过这个:

myservice.url=localhost:${local.server.port}
Run Code Online (Sandbox Code Playgroud)

但结果是“localhost:0”。

我不想为端口使用常量值。

请帮忙。谢谢!

java spring-boot spring-boot-test openfeign

5
推荐指数
1
解决办法
1602
查看次数

Spring Boot 测试不启动上下文或加载依赖项

这是一个非常初学者的问题,但我无法解决。我有一个基本的 Spring Boot 应用程序,以及一个连接到云图集实例的 Spring Data MongoDB 存储库。问题是,在我的 Spring Boot 测试中,我的存储库未自动连接,并且未创建嵌入式 MongoDB 实例。如果我启动 Spring Boot 应用程序并在主类中自动装配存储库,那么就可以了。为什么它在我的测试中不起作用?

这是我的测试课:

@DataMongoTest
@ExtendWith(SpringExtension.class)
public class SampleServiceTest{


    @Autowired
    private SampleRepository sampleRepository;

    @Test
    public void shouldCreateSample(){
        sampleRepository.save(new Sample());
    }
}
Run Code Online (Sandbox Code Playgroud)

这是我的 pom.xml:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.2.2.RELEASE</version>
        <relativePath></relativePath>
    </parent>
    <modelVersion>4.0.0</modelVersion>



    <groupId>com.comand</groupId>
    <artifactId>business-owner-service</artifactId>
    <version>1.0-SNAPSHOT</version>
    <description>API Gateway</description>

    <properties>
        <maven.compiler.target>1.8</maven.compiler.target>
        <maven.compiler.source>1.8</maven.compiler.source>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-config-client</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-actuator</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId> …
Run Code Online (Sandbox Code Playgroud)

junit spring spring-data-mongodb spring-boot spring-boot-test

5
推荐指数
1
解决办法
2万
查看次数

如何在 Webflux 功能端点测试中禁用 Spring Security

我想在某些单元测试期间禁用端点上的安全性。我正在使用 webflux 功能端点,因此以下配置不起作用。

@AutoConfigureMockMvc(secure = false)

我通过使用配置文件停用它,但这意味着我无法再使用测试配置文件测试安全性。还有另一种方法可以用 webflux 做到这一点吗?

预先感谢您的帮助

java spring-boot spring-boot-test spring-webflux

5
推荐指数
1
解决办法
3657
查看次数

Spring Boot测试@ConfigurationProperties不绑定字段

各位晚上好。我有一个专为与属性绑定而设计的类。在标记为 的类中@Configuration,我将这个 bean 对象设置为:

\n\n
// Into TargetConfiguration class\n\n@Bean("someBeanName")\n@ConfigurationProperties("some.path")\npublic beanProperties() {\n    return new BeanProperties();\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

我想测试此配置的所有功能,为此我创建一个测试类,例如:

\n\n
@WebFluxTest\n@TestPropertySource("classpath:test.properties")\n@ContextConfiguration(classes = {TargetConfiguration.class})\nclass Test {...}\n
Run Code Online (Sandbox Code Playgroud)\n\n

问题是它将BeanProperties包含空字段,但如果我创建一些其他字段并通过inOtherBeanProperties注册它,那么它通常会被填充,但对于我可以\xe2\x80\x99t 这样做,因为这个bean取决于测试中的属性。特性。另外,如果我通过配置创建这个 bean ,那么它将被填充到...@EnableConfigurationPropertiesTargetConfigurationBeanProperties@TestConfiguration

\n\n

任何帮助表示赞赏。

\n\n

UPD-1:第一个假设 - 我注册了一些使用名为 的注释扩展BeanDefinitionRegistryPostProcessor@DependsOnRegistratorClass。我不知道为什么,但是如果我添加@DependsOnRegistratorClass,我会BeanProperties立即构造而不绑定(并传递给想要接收此消息的其他方法BeanProperties)。如果我删除这个注释,RegistratorClass初始化第一个注释,我的BeanProperties将正常构造并绑定到属性。

\n

java spring spring-boot spring-boot-test

5
推荐指数
1
解决办法
1256
查看次数

Spring Boot 测试:@Scheduled beans 在脏上下文后继续执行

语境

我正在开发一个 Spring Boot 项目,该项目大量使用 @Scheduled bean。我们编写了一个非常轻量级的类似事件源的框架,该框架依赖于数据库中的数据:每次检查数据库是否有新记录,这可能会导致触发这些新记录的处理程序。

我们编写集成测试:在数据库中创建一条新记录,等待处理程序拾取它并且数据库得到更新并验证数据库的新状态。

问题

在我们编写一个会弄脏 spring 上下文的测试之前,这一切都很好。上下文可以很好地重新创建,但旧上下文中的 @Scheduled 方法继续运行,从旧上下文而不是新上下文中执行逻辑。

我在这个小例子中演示了这个问题:https ://github.com/stainii/spring-boot-test-scheduled-bean-problem 。当您运行测试时(出于演示目的,最好按字母顺序排列),您将看到每个测试本身都运行良好,但是当需要重新创建上下文时,将运行 2 个计划 bean,而不是 1 个。

有谁知道这是否是预期的行为,以及当上下文被标记为脏时我们是否可以销毁 @Scheduled bean?

java spring-scheduled spring-boot spring-boot-test

5
推荐指数
0
解决办法
649
查看次数

如何在应用程序运行之前执行 SpringBootTest 中的代码?

我有一个基于 SpringBoot 的命令行应用程序。应用程序在数据库中创建或删除一些记录。它不是直接通过 JDBC 而是通过特殊的 API(实例变量dbService)来执行此操作。

应用程序类如下所示:

@SpringBootApplication
public class Application implements CommandLineRunner {

  @Autowired
  private DbService dbService;
  
  public static void main(String[] args) {
    SpringApplication.run(Application.class, args);
  }
  
  @Override
  public void run(String... args) {
    // Do something via dbService based on the spring properties
  }

}
Run Code Online (Sandbox Code Playgroud)

现在我想创建一个 SpringBoot 测试,该测试将使用专门为测试准备的配置来运行整个应用程序。

我使用内存数据库(H2)运行测试,该数据库在测试开始时为空。因此,我想将一些记录插入数据库——作为测试的设置。必须执行插入记录的代码

  1. 在加载 Spring 上下文之后——以便我可以使用该 bean dbService

  2. 在应用程序运行之前——以便应用程序使用准备好的数据库运行。

不知怎的,我未能落实以上两点。

到目前为止我所拥有的是这样的:

@SpringBootTest
@DirtiesContext(classMode = ClassMode.AFTER_CLASS)
@ActiveProfiles("specialtest")
public class MyAppTest {
 
  @Autowired
  private DbService dbService;
  
  private static final Logger logger = LoggerFactory.getLogger(MyAppTest.class); …
Run Code Online (Sandbox Code Playgroud)

spring-boot spring-boot-test

5
推荐指数
1
解决办法
3591
查看次数