Java 如何在spring测试中设置环境变量或系统属性?

Java 如何在spring测试中设置环境变量或系统属性?,java,spring,environment-variables,spring-test,Java,Spring,Environment Variables,Spring Test,我想编写一些测试来检查已部署WAR的XMLSpring配置。不幸的是,有些bean需要设置一些环境变量或系统属性。在使用@ContextConfiguration的方便测试样式时,如何在初始化Springbean之前设置环境变量 @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration(locations = "classpath:whereever/context.xml") public class TestWarSpring

我想编写一些测试来检查已部署WAR的XMLSpring配置。不幸的是,有些bean需要设置一些环境变量或系统属性。在使用@ContextConfiguration的方便测试样式时,如何在初始化Springbean之前设置环境变量

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath:whereever/context.xml")
public class TestWarSpringContext { ... }

如果使用注释配置应用程序上下文,则在初始化spring上下文之前,我看不到可以执行某些操作的钩子。

您可以在静态初始值设定项中初始化系统属性:

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath:whereever/context.xml")
public class TestWarSpringContext {

    static {
        System.setProperty("myproperty", "foo");
    }

}

静态初始化器代码将在初始化spring应用程序上下文之前执行。

从spring 4.1开始,正确的方法是使用
@TestPropertySource
注释

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath:whereever/context.xml")
@TestPropertySource(properties = {"myproperty = foo"})
public class TestWarSpringContext {
    ...    
}

请参阅和中的@TestPropertySource。

还可以使用测试应用程序ContextInitializer初始化系统属性:

public class TestApplicationContextInitializer implements ApplicationContextInitializer<ConfigurableApplicationContext>
{
    @Override
    public void initialize(ConfigurableApplicationContext applicationContext)
    {
        System.setProperty("myproperty", "value");
    }
}

如果应该为所有单元测试设置特定的系统属性,则可以通过这种方式避免代码重复。

如果希望变量对所有测试有效,可以在测试资源目录(默认情况下:
src/test/resources
)中设置一个
应用程序.properties
文件,该文件如下所示:

MYPROPERTY=foo

除非您通过
@TestPropertySource
或类似方法有定义,否则将加载并使用该属性-加载属性的确切顺序可以在Spring文档一章中找到。

您可以将系统属性设置为VM参数

如果您的项目是maven项目,则可以在运行测试类时执行以下命令:

mvn test -Dapp.url="https://stackoverflow.com"
public class AppTest  {
@Test
public void testUrl() {
    System.out.println(System.getProperty("app.url"));
    }
}
测试等级:

mvn test -Dapp.url="https://stackoverflow.com"
public class AppTest  {
@Test
public void testUrl() {
    System.out.println(System.getProperty("app.url"));
    }
}
如果要在eclipse中运行单个测试类或方法,请执行以下操作:

1) 转到运行->运行配置

2) 在左侧,选择Junit部分下的测试类

3) 请执行以下操作:


这里的所有答案目前只讨论系统属性,这些属性不同于更复杂的环境变量,特别是测试。谢天谢地,下面的类可以用于此,类文档有很好的示例

文档中的一个快速示例,已修改为使用@SpringBootTest

@SpringBootTest
public class EnvironmentVariablesTest {
   @ClassRule
   public final EnvironmentVariables environmentVariables = new EnvironmentVariables().set("name", "value");

   @Test
   public void test() {
     assertEquals("value", System.getenv("name"));
   }
 }

对于单元测试,当我执行“mvn clean install”时,系统变量尚未实例化,因为没有运行应用程序的服务器。因此,为了设置系统属性,我需要在pom.xml中进行设置。像这样:

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-surefire-plugin</artifactId>
    <version>2.21.0</version>
    <configuration>
        <systemPropertyVariables>
            <propertyName>propertyValue</propertyName>
            <MY_ENV_VAR>newValue</MY_ENV_VAR>
            <ENV_TARGET>olqa</ENV_TARGET>
            <buildDirectory>${project.build.directory}</buildDirectory>
        </systemPropertyVariables>
    </configuration>
</plugin>

org.apache.maven.plugins
maven surefire插件
2.21.0
财产价值
新价值
奥尔卡
${project.build.directory}

愚蠢的我-好吧,那就行了。更好的是:可能是一个
@BeforeClass
方法来设置系统属性,一个
@AfterClass
方法来删除它也会起作用,并且在它自己之后会很好地清理。(虽然没有尝试过。)尝试了@BeforeClass——在测试实例中设置其他属性之前设置系统属性效果很好。静态的东西不起作用,但是一个带有@BeforeClass的小方法起作用了!如果更改Log4j2配置文件属性,此机制将不起作用。似乎在静态代码之前加载了Spring(因此日志记录不正确)。此批注还支持属性文件路径。我可以在测试期间使用
@TestPropertySource(properties={“Spring.Cloud.Config.label=feature/branch”})切换Spring Cloud配置客户端标签。
回答得好,但遗憾的是,使用Spring4.2.9,属性总是空的,这对我来说不起作用。只有静态块工作。。。适用于应用程序属性,但不适用于系统属性。首先,我看到并尝试了静态版本(有效),但此注释更干净、更可取(对我来说,它也像一个符咒)。它提供了一个
环境
属性,与“环境变量”不同。这也适用于Spring Boot 2.x和Junit 5.x(使用
@SpringBootTest
或任何注释)。EnvironmentVariables规则是第三方库的一部分,使用hacky反射更改JVM内存中环境的缓存值,甚至不更改实际的环境变量。所以,我不想使用它,也不建议任何人使用它。它似乎还有一个ProvideSystemProperty规则,奇怪的是,还有一个restoresystemproperty规则。因此,这也适用于系统属性。