156

Spring Boot allows us to replace our application.properties files with YAML equivalents. However, I seem to hit a snag with my tests. If I annotate my TestConfiguration (a simple Java config), it is expecting a properties file.

For example this doesn't work: @PropertySource(value = "classpath:application-test.yml")

If I have this in my YAML file:

db:
  url: jdbc:oracle:thin:@pathToMyDb
  username: someUser
  password: fakePassword

And I'd be leveraging those values with something like this:

@Value("${db.username}") String username

However, I end up with an error like so:

Could not resolve placeholder 'db.username' in string value "${db.username}"

How can I leverage the YAML goodness in my tests as well?

Andrzej Sydor
  • 1,373
  • 4
  • 13
  • 28
checketts
  • 14,167
  • 10
  • 53
  • 82
  • Define "doesn't work." What's the exception/error/warning? – Emerson Farrugia Jan 22 '14 at 00:03
  • 1
    Spring Boot flattens the YAML file so it appears as a property file with dot notation. That flattening isn't happening. – checketts Jan 22 '14 at 00:04
  • And just to confirm, this works in non-test code? – Emerson Farrugia Jan 22 '14 at 00:14
  • 3
    Yes. Here is a doc explaining http://projects.spring.io/spring-boot/docs/spring-boot-actuator/README.html#toc_5 and a ways down the page is says 'Note that the YAML object is flattened using period separators.' – checketts Jan 22 '14 at 00:30
  • I know it works in general. :) I meant to confirm that this is somehow test-specific and that YAML-based properties are working in the remainder of your project. There's better info here: http://projects.spring.io/spring-boot/docs/spring-boot/README.html ... there shouldn't be anything test-specific in the YamlPropertySourceLoader, but I haven't tried this stuff yet. – Emerson Farrugia Jan 22 '14 at 00:52
  • Oh, yes. I have SnakeYAML on the classpath, so my other YAML are working. – checketts Jan 22 '14 at 00:53
  • 10
    SpingBoot said it can not load YAML with PropertySource: 24.6.4 YAML shortcomings YAML files can’t be loaded via the @PropertySource annotation. So in the case that you need to load values that way, you need to use a properties file. – Lex Pro Aug 31 '16 at 02:17
  • please see my answer: have suc pic: if you need project info,please upvote me. https://stackoverflow.com/questions/21271468/spring-propertysource-using-yaml/66641155#66641155 – Forest10 Mar 15 '21 at 16:06

19 Answers19

70

Spring-boot has a helper for this, just add

@ContextConfiguration(initializers = ConfigFileApplicationContextInitializer.class)

at the top of your test classes or an abstract test superclass.

Edit: I wrote this answer five years ago. It doesn't work with recent versions of Spring Boot. This is what I do now (please translate the Kotlin to Java if necessary):

@TestPropertySource(locations=["classpath:application.yml"])
@ContextConfiguration(
        initializers=[ConfigFileApplicationContextInitializer::class]
)

is added to the top, then

    @Configuration
    open class TestConfig {

        @Bean
        open fun propertiesResolver(): PropertySourcesPlaceholderConfigurer {
            return PropertySourcesPlaceholderConfigurer()
        }
    }

to the context.

Ola Sundell
  • 764
  • 6
  • 5
  • 3
    dont forget PropertySourcesPlaceholderConfigurer – Kalpesh Soni Apr 30 '19 at 22:26
  • @KalpeshSoni indeed, without said Configurer, it won't work. – Ola Sundell Jun 25 '19 at 13:46
  • I had to add the initializer to @SpringJunitConfig instead `@SpringJUnitConfig(value = {...}, initializers = {ConfigFileApplicationContextInitializer.class})` – Tomas F Oct 11 '19 at 12:11
  • @OlaSundell out of curiosity, why you wrote it does not work with the recent versions of Spring Boot?. I used your solution with 2.3.4.RELEASE and it works. – Enrico Giurin Oct 21 '20 at 10:37
  • 1
    Are you sure @TestPropertySource(locations=["classpath:application.yml"]) is required? ConfigFile initializer will search in default locations on its own. I wonder if non default file location would work this way.. – Vadim Kirilchuk Oct 30 '20 at 09:54
  • It's too much trouble. see this. easy to use:https://stackoverflow.com/questions/21271468/spring-propertysource-using-yaml/66641155#66641155 – Forest10 Nov 10 '21 at 08:03
  • on the latest versions `ConfigFileApplicationContextInitializer` has been replaced for `ConfigDataApplicationContextInitializer`. This conf worked for me : ``` @ExtendWith(SpringExtension.class) @EnableConfigurationProperties(value = { AnalyzerApplicationProperties.class }) @TestPropertySource("classpath:application-test.yml") @ContextConfiguration(initializers = ConfigDataApplicationContextInitializer.class) ``` – wizardInCloud Nov 23 '22 at 16:23
  • 1
    **This is wrong answer: it works accidentally ))**. `TestPropertySource` doesn't support YAML and Spring devs refused to implement support. The key is `ConfigDataApplicationContextInitializer` or `ConfigFileApplicationContextInitializer`: they activate regular Spring Boot loading sequence, like taking `application.yml` from classpath. You can control the name of files indirectly via `@ActiveProfiles`. – gavenkoa Feb 28 '23 at 20:31
65

As it was mentioned @PropertySource doesn't load yaml file. As a workaround load the file on your own and add loaded properties to Environment.

Implemement ApplicationContextInitializer:

public class YamlFileApplicationContextInitializer implements ApplicationContextInitializer<ConfigurableApplicationContext> {
  @Override
  public void initialize(ConfigurableApplicationContext applicationContext) {
    try {
        Resource resource = applicationContext.getResource("classpath:file.yml");
        YamlPropertySourceLoader sourceLoader = new YamlPropertySourceLoader();
        PropertySource<?> yamlTestProperties = sourceLoader.load("yamlTestProperties", resource, null);
        applicationContext.getEnvironment().getPropertySources().addFirst(yamlTestProperties);
    } catch (IOException e) {
        throw new RuntimeException(e);
    }
  }
}

Add your initializer to your test:

@RunWith(SpringJUnit4ClassRunner.class)
@SpringApplicationConfiguration(classes = Application.class, initializers = YamlFileApplicationContextInitializer.class)
public class SimpleTest {
  @Test
  public test(){
    // test your properties
  }
}
Community
  • 1
  • 1
balbusm
  • 1,646
  • 19
  • 23
  • Actually this should be the best answer, thanks it worked ! – Adelin Jun 01 '16 at 12:37
  • Mateusz, I have posted answer with `YamlFileApplicationContextInitializer` class where YAML location is defined per test case. If you think it is interesting, feel free to merge it into your answer and I will delete mine. Just let me know in a comment bellow my answer. – Michal Foksa Apr 08 '18 at 09:22
  • Yes, this is the best answer – Richard H.M Apr 27 '20 at 09:15
52

@PropertySource can be configured by factory argument. So you can do something like:

@PropertySource(value = "classpath:application-test.yml", factory = YamlPropertyLoaderFactory.class)

Where YamlPropertyLoaderFactory is your custom property loader:

public class YamlPropertyLoaderFactory extends DefaultPropertySourceFactory {
    @Override
    public PropertySource<?> createPropertySource(String name, EncodedResource resource) throws IOException {
        if (resource == null){
            return super.createPropertySource(name, resource);
        }

        return new YamlPropertySourceLoader().load(resource.getResource().getFilename(), resource.getResource(), null);
    }
}

Inspired by https://stackoverflow.com/a/45882447/4527110

  • 2
    This underlying yaml parse throws an `IllegalStateException` when the file doesn't exist instead of the proper `FileNotFoundException` - so in order to make this work with `@PropertySource(..., ignoreResourceNotFound = true)`, you'll need catch and handle this case: `try { return new YamlPropertySourceLoader().load(resource.getResource().getFilename(), resource.getResource(), null); } catch (IllegalStateException e) { throw (IOException) e.getCause(); }` – C12Z Nov 01 '18 at 16:26
  • 2
    If you need to get properties for a specific profile, the third parameter in YamlPropertySourceLoader.load() is the profile name. YamlPropertySourceLoader.load() has changed to return a list rather than a single propertysource. Here's more info https://stackoverflow.com/a/53697551/10668441 – pcoates Dec 10 '18 at 15:53
  • 1
    This is cleanest approach so far. – Michal Foksa Jun 05 '19 at 11:57
  • 10
    for me, it required a little modification in return as follows: `CompositePropertySource propertySource = new CompositePropertySource(name); new YamlPropertySourceLoader().load(resource.getResource().getFilename(), resource.getResource()).stream().forEach(propertySource::addPropertySource); return propertySource;` – xorcus Jun 26 '19 at 09:29
38

Another option is to set the spring.config.location through @TestPropertySource:

@TestPropertySource(properties = { "spring.config.location = classpath:<path-to-your-yml-file>" }
Doc Davluz
  • 4,154
  • 5
  • 30
  • 32
  • 3
    I have parametrized the input by the following line: `@TestPropertySource(properties = {"spring.config.location=classpath:application-${test.env}.yml" })` IMO yours is the best answer out of all. – leventunver Mar 20 '19 at 16:44
  • 2
    Great idea and very minimalistic for tests, thanks a lot! Just to add, one can include multiple configuration files, per: `@TestPropertySource(properties = {"spring.config.location=classpath:application-config.yml,classpath:test-config.yml,..." })` – stx Jul 22 '19 at 09:13
  • 1
    This is the best answer by far ! note that you need to have `@SpringBootTest` annotation – Mistriel May 05 '20 at 18:43
  • 1
    I don't want to load all the spring configuration just because i need a property from my yml. This is what `@SpringBootTest` does – Enrico Giurin Oct 20 '20 at 19:16
30

@PropertySource only supports properties files (it's a limitation from Spring, not Boot itself). Feel free to open a feature request ticket in JIRA.

UPDATE Already opened and rejected Jira requests:

gavenkoa
  • 45,285
  • 19
  • 251
  • 303
Dave Syer
  • 56,583
  • 10
  • 155
  • 143
  • I'd hoped there was a way to re-use the yaml listener or to manually load the yaml in an Environment which could be passed into the test config. – checketts Jan 22 '14 at 13:45
  • 13
    I suppose you could write an `ApplicationContextInitializer` and add it to the test configuration (just use a `YamlPropertySourceLoader` to enhance the `Environment`). Personally I'd prefer it if `@PropertySource` would support this behaviour natively. – Dave Syer Jan 22 '14 at 17:44
  • is this still the case? does '@PropertySource' not support YAML? – domi Oct 11 '16 at 14:00
24

From Spring Boot 1.4, you can use the new @SpringBootTest annotation to achieve this more easily (and to simplify your integration test setup in general) by bootstrapping your integration tests using Spring Boot support.

Details on the Spring Blog.

As far as I can tell, this means you get all the benefits of Spring Boot's externalized config goodness just like in your production code, including automatically picking up YAML config from the classpath.

By default, this annotation will

... first attempt to load @Configuration from any inner-classes, and if that fails, it will search for your primary @SpringBootApplication class.

but you can specify other configuration classes if required.

For this particular case, you can combine @SpringBootTest with @ActiveProfiles( "test" ) and Spring will pick up your YAML config, provided it follows the normal Boot naming standards (i.e. application-test.yml).

@RunWith( SpringRunner.class )
@SpringBootTest
@ActiveProfiles( "test" )
public class SpringBootITest {

    @Value("${db.username}")
    private String username;

    @Autowired
    private MyBean myBean;

    ...

}

Note: SpringRunner.class is the new name for SpringJUnit4ClassRunner.class

moogpwns
  • 351
  • 3
  • 5
11

The approach to loading the yaml properties, IMHO can be done in two ways:

a. You can put the configuration in a standard location - application.yml in the classpath root - typically src/main/resources and this yaml property should automatically get loaded by Spring boot with the flattened path name that you have mentioned.

b. The second approach is a little more extensive, basically define a class to hold your properties this way:

@ConfigurationProperties(path="classpath:/appprops.yml", name="db")
public class DbProperties {
    private String url;
    private String username;
    private String password;
...
}

So essentially this is saying that load the yaml file and populate the DbProperties class based on the root element of "db".

Now to use it in any class you will have to do this:

@EnableConfigurationProperties(DbProperties.class)
public class PropertiesUsingService {

    @Autowired private DbProperties dbProperties;

}

Either of these approaches should work for you cleanly using Spring-boot.

Biju Kunjummen
  • 49,138
  • 14
  • 112
  • 125
  • Make sure you have snakeyml in your classpath and the above should work. – hoserdude Jan 22 '14 at 20:08
  • 3
    These days (although not at the time this question was asked), `snakeyaml` is pulled in as a transitive dependency by `spring-boot-starter`, so there should be no need to add it to your `pom.xml` or `build.gradle`, unless you have a deep-rooted urge to use a different version. :) – Steve Jun 06 '14 at 09:28
  • 3
    It's now `locations`, not `path`, and the `ConfigFileApplicationContextInitializer` is also required. – OrangeDog Jul 26 '16 at 09:29
7

Since Spring Boot 2.4.0 you can use ConfigDataApplicationContextInitializer as follows:

@SpringJUnitConfig(
    classes = { UserAccountPropertiesTest.TestConfig.class },
    initializers = { ConfigDataApplicationContextInitializer.class }
)
class UserAccountPropertiesTest {

    @Configuration
    @EnableConfigurationProperties(UserAccountProperties.class)
    static class TestConfig { }

    @Autowired
    UserAccountProperties userAccountProperties;

    @Test
    void getAccessTokenExpireIn() {
       assertThat(userAccountProperties.getAccessTokenExpireIn()).isEqualTo(120);
    }

    @Test
    void getRefreshTokenExpireIn() {
        assertThat(userAccountProperties.getRefreshTokenExpireIn()).isEqualTo(604800);
    }
}

See also: https://www.baeldung.com/spring-boot-testing-configurationproperties#YAML-binding

Martín Coll
  • 3,368
  • 3
  • 37
  • 52
Ishak Antony
  • 79
  • 1
  • 2
3

I found a workaround by using @ActiveProfiles("test") and adding an application-test.yml file to src/test/resources.

It ended up looking like this:

@SpringApplicationConfiguration(classes = Application.class, initializers = ConfigFileApplicationContextInitializer.class)
@ActiveProfiles("test")
public abstract class AbstractIntegrationTest extends AbstractTransactionalJUnit4SpringContextTests {

}

The file application-test.yml just contains the properties that I want to override from application.yml (which can be found in src/main/resources).

Poly
  • 195
  • 2
  • 8
  • This is what I was trying to use as well. For some reason it doesn't work (Spring Boot 1.3.3) when I use `@Value("${my.property}")` but it works fine if I use `environment.getProperty("my.property")`. – martin-g Apr 15 '16 at 12:22
2

I have tried all of the listed questions, but all of them not work for my task: using specific yaml file for some unit test. In my case, it works like this:

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(initializers = {ConfigFileApplicationContextInitializer.class})
@TestPropertySource(properties = {"spring.config.location=file:../path/to/specific/config/application.yml"})
public class SomeTest {


    @Value("${my.property.value:#{null}}")
    private String value;

    @Test
    public void test() {
        System.out.println("value = " + value);
    }

}
FedorM
  • 75
  • 1
  • 9
  • Oh for the love of God! Why can't things be simple? I wasted so much time on trying to figure out why the `@TestPropertySource` was not properly loading the yaml values. This seems to be the only way it actually works as expected. I wonder why the TestPropertySource doesn't work, considering Spring is pushing to migrate to yaml files. – tftd Nov 19 '22 at 11:56
2

Here's an improved version of YamlPropertyLoaderFactory which supports the new PropertySource.ignoreResourceNotFound, based on this answer:

Java:

public final class YamlPropertyLoaderFactory extends DefaultPropertySourceFactory {
    private final YamlPropertySourceLoader yamlPropertySourceLoader = new YamlPropertySourceLoader();

    @NotNull
    public PropertySource createPropertySource(
            @Nullable String name,
            @NotNull EncodedResource resource
    ) {
        try {
            String parsedName;
            if (name != null && !name.equals(""))
                parsedName = name;
            else parsedName = resource.getResource().getFilename();
            return yamlPropertySourceLoader.load(parsedName, resource.getResource()).get(0);
        } catch (Exception e) {
            Exception possibleFileNotFoundException = ExceptionUtils.throwableOfType(e, FileNotFoundException.class);
            throw possibleFileNotFoundException != null ? possibleFileNotFoundException : e;
        }
    }
}

// Usage
@PropertySource(
   value = {"file:./my-optional-config.yml"},
   factory = YamlPropertyLoaderFactory.class,
   ignoreResourceNotFound = true
)

Kotlin:

class YamlPropertyLoaderFactory : DefaultPropertySourceFactory() {
    private val yamlPropertySourceLoader = YamlPropertySourceLoader()

    override fun createPropertySource(
        name: String?,
        resource: EncodedResource
    ): PropertySource<*> = try {
        (
            yamlPropertySourceLoader.load(
                if (name != null && name.isNotBlank()) name else resource.resource.filename,
                resource.resource
            )
            )[0]
    } catch (e: Exception) {
        throw ExceptionUtils.throwableOfType(e, FileNotFoundException::class.java) ?: e
    }
}

// Usage
@PropertySource(
    value = ["file:/my-optional-config.yml"],
    factory = YamlPropertyLoaderFactory::class,
    ignoreResourceNotFound = true
)
Il Harper
  • 57
  • 7
1

it's because you have not configure snakeyml. spring boot come with @EnableAutoConfiguration feature. there is snakeyml config too when u call this annotation..

this is my way:

@Configuration
@EnableAutoConfiguration
public class AppContextTest {
}

here is my test:

@RunWith(SpringJUnit4ClassRunner.class)
@SpringApplicationConfiguration(
        classes = {
                AppContextTest.class,
                JaxbConfiguration.class,
        }
)

public class JaxbTest {
//tests are ommited
}
user2582794
  • 153
  • 9
1

I needed to read some properties into my code and this works with spring-boot 1.3.0.RELEASE

@Autowired
private ConfigurableListableBeanFactory beanFactory;

// access a properties.yml file like properties
@Bean
public PropertySource properties() {
    PropertySourcesPlaceholderConfigurer propertySourcesPlaceholderConfigurer = new PropertySourcesPlaceholderConfigurer();
    YamlPropertiesFactoryBean yaml = new YamlPropertiesFactoryBean();
    yaml.setResources(new ClassPathResource("properties.yml"));
    propertySourcesPlaceholderConfigurer.setProperties(yaml.getObject());
    // properties need to be processed by beanfactory to be accessible after
    propertySourcesPlaceholderConfigurer.postProcessBeanFactory(beanFactory);
    return propertySourcesPlaceholderConfigurer.getAppliedPropertySources().get(PropertySourcesPlaceholderConfigurer.LOCAL_PROPERTIES_PROPERTY_SOURCE_NAME);
}
U.V.
  • 572
  • 4
  • 11
0

Loading custom yml file with multiple profile config in Spring Boot.

1) Add the property bean with SpringBootApplication start up as follows

@SpringBootApplication
@ComponentScan({"com.example.as.*"})
public class TestApplication {

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

    @Bean
    @Profile("dev")
    public PropertySourcesPlaceholderConfigurer propertiesStage() {
        return properties("dev");
    }

    @Bean
    @Profile("stage")
    public PropertySourcesPlaceholderConfigurer propertiesDev() {
        return properties("stage");
    }

    @Bean
    @Profile("default")
    public PropertySourcesPlaceholderConfigurer propertiesDefault() {
        return properties("default");

    }
   /**
    * Update custom specific yml file with profile configuration.
    * @param profile
    * @return
    */
    public static PropertySourcesPlaceholderConfigurer properties(String profile) {
       PropertySourcesPlaceholderConfigurer propertyConfig = null;
       YamlPropertiesFactoryBean yaml  = null;

       propertyConfig  = new PropertySourcesPlaceholderConfigurer();
       yaml = new YamlPropertiesFactoryBean();
       yaml.setDocumentMatchers(new SpringProfileDocumentMatcher(profile));// load profile filter.
       yaml.setResources(new ClassPathResource("env_config/test-service-config.yml"));
       propertyConfig.setProperties(yaml.getObject());
       return propertyConfig;
    }
}

2) Config the Java pojo object as follows

@Component
@JsonIgnoreProperties(ignoreUnknown = true)
@JsonInclude(Include.NON_NULL)
@ConfigurationProperties(prefix = "test-service")
public class TestConfig {

    @JsonProperty("id") 
    private  String id;

    @JsonProperty("name")
    private String name;

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }   

}

3) Create the custom yml (and place it under resource path as follows, YML File name : test-service-config.yml

Eg Config in the yml file.

test-service: 
    id: default_id
    name: Default application config
---
spring:
  profiles: dev

test-service: 
  id: dev_id
  name: dev application config

--- 
spring:
  profiles: stage

test-service: 
  id: stage_id
  name: stage application config
0

Enhancing Mateusz Balbus answer.

Modified YamlFileApplicationContextInitializer class where YAML location is defined per test class. It does not work per test, unfortunately.

public abstract class YamlFileApplicationContextInitializer
  implements ApplicationContextInitializer<ConfigurableApplicationContext> {

  /***
   * Return location of a YAML file, e.g.: classpath:file.yml
   *
   * @return YAML file location
   */
  protected abstract String getResourceLocation();

  @Override
  public void initialize(ConfigurableApplicationContext applicationContext) {
    try {
        Resource resource = applicationContext.getResource(getResourceLocation());
        YamlPropertySourceLoader sourceLoader = new YamlPropertySourceLoader();
        PropertySource<?> yamlTestProperties = sourceLoader.load("yamlTestProperties", resource, null);
        applicationContext.getEnvironment().getPropertySources().addFirst(yamlTestProperties);
    } catch (IOException e) {
        throw new RuntimeException(e);
    }
  }
}

Usage:

Create subclass of YamlFileApplicationContextInitializer with defined getResourceLocation() method and add this subclass into @SpringApplicationConfiguration annotation.

This way it is easiest to make the test class itself.

@RunWith(SpringRunner.class)
@SpringApplicationConfiguration(classes = Application.class, initializers = SimpleTest.class)
public class SimpleTest extends YamlFileApplicationContextInitializer {

  @Override
  protected String getResourceLocation() {
    return "classpath:test_specific.yml";
  }

  @Test
  public test(){
    // test your properties
  }
}
Michal Foksa
  • 11,225
  • 9
  • 50
  • 68
0
<dependency>
  <groupId>com.github.yingzhuo</groupId>
  <artifactId>spring-boot-stater-env</artifactId>
  <version>0.0.3</version>
</dependency>

Welcome to use my library. Now yaml, toml, hocon is supported.

Source: github.com

Zhuo YING
  • 972
  • 3
  • 11
  • 19
0

This is not an answer to the original question, but an alternative solution for a need to have a different configuration in a test...

Instead of @PropertySource you can use -Dspring.config.additional-location=classpath:application-tests.yml.

Be aware, that suffix tests does not mean profile...

In that one YAML file one can specify multiple profiles, that can kind of inherit from each other, read more here - Property resolving for multiple Spring profiles (yaml configuration)

Then, you can specify in your test, that active profiles (using @ActiveProfiles("profile1,profile2")) are profile1,profile2 where profile2 will simply override (some, one does not need to override all) properties from profile1.

Betlista
  • 10,327
  • 13
  • 69
  • 110
0

enter image description here

project demo url: https://github.com/Forest10/spring-boot-family/tree/spring-boot-with-yml

I run this answer in my prod env!!! so if you against this ans. please test first!!!

There is no need to add like YamlPropertyLoaderFactory or YamlFileApplicationContextInitializer. You should convert your idea

Follow these steps:

Just add applicationContext.xml like

@ImportResource({"classpath:applicationContext.xml"})

to your ApplicationMainClass.

and your applicationContext.xml should write like this

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns:context="http://www.springframework.org/schema/context"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  default-autowire="byName"
  xmlns="http://www.springframework.org/schema/beans"
  xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd">

  <context:property-placeholder location="classpath*:*.yml"/>
</beans>

This can help scan your application-test.yml

db:
   url: jdbc:oracle:thin:@pathToMyDb
   username: someUser
   password: fakePassword


Forest10
  • 279
  • 3
  • 11
0

Based on answer https://stackoverflow.com/a/51392715/5235756

Just for convenience, here is a kotlin version of the java code:

@PropertySource(value = ["classpath:application-test.yml"], factory = YamlPropertyLoaderFactory::class)

YamlPropertyLoaderFactory:

import org.springframework.boot.env.YamlPropertySourceLoader
import org.springframework.core.env.PropertySource
import org.springframework.core.io.support.DefaultPropertySourceFactory
import org.springframework.core.io.support.EncodedResource

class YamlPropertyLoaderFactory : DefaultPropertySourceFactory() {
    @Throws(IllegalStateException::class)
    override fun createPropertySource(name: String?, resource: EncodedResource): PropertySource<*> {
        return YamlPropertySourceLoader().load(resource.resource.filename, resource.resource).first()
    }
}
DJ-Glock
  • 1,277
  • 2
  • 12
  • 39