Seven Techniques to Retrieve Spring Boot Properties

This article demonstrates seven practical ways to access configuration properties in a Spring Boot 3.5.0 application, covering ContextRefreshedEvent listeners, ConfigurableEnvironment, the Environment interface, @Value, @ConfigurationProperties, ConfigurableBeanFactory, and the Actuator /env endpoint, each with code examples and usage notes.

Spring Full-Stack Practical Cases
Spring Full-Stack Practical Cases
Spring Full-Stack Practical Cases
Seven Techniques to Retrieve Spring Boot Properties

1. Introduction

Spring Boot properties are a powerful mechanism for configuring applications. They can originate from property files, environment variables, and other sources. When debugging or documenting, it is useful to locate and log specific properties.

2. Preparing Sample Properties

pack:
  app:
    name: MyApp
    description: ${pack.app.name} is a Spring Boot application
---
xxgg:
  title: xxxooo

These custom properties will be used throughout the examples.

3. Using ContextRefreshedEvent

Listen for ContextRefreshedEvent and log every property available in the environment.

@Component
public class EventPropertiesPrinter {
  @EventListener
  public void handleContextRefreshed(ContextRefreshedEvent event) {
    ConfigurableEnvironment env = (ConfigurableEnvironment) event.getApplicationContext().getEnvironment();
    env.getPropertySources()
       .stream()
       .filter(ps -> ps instanceof MapPropertySource)
       .map(ps -> ((MapPropertySource) ps).getSource().keySet())
       .flatMap(Collection::stream)
       .distinct()
       .sorted()
       .forEach(key -> LOGGER.info("{}={}", key, env.getProperty(key)));
  }
}

The console output (shown in the image) lists all keys and their values.

4. Filtering for Application.yml Only

Modify the filter to keep only property sources whose name contains application.yml:

env.getPropertySources()
   .stream()
   .filter(ps -> ps instanceof MapPropertySource && ps.getName().contains("application.yml"))
   // ... same processing as above
   .forEach(key -> LOGGER.info("{}={}", key, env.getProperty(key)));

This prints only the properties defined in the main YAML file.

5. Using the Environment Interface

The Environment API can retrieve individual values when the property name is known.

@Component
public class EnvironmentPropertiesPrinter {
  private static final Logger logger = LoggerFactory.getLogger(EventPropertiesPrinter.class);
  private final Environment env;
  public EnvironmentPropertiesPrinter(Environment env) { this.env = env; }
  @PostConstruct
  public void printProperties() {
    logger.info("{} = {}", "xxgg.title", env.getProperty("xxgg.title"));
    logger.info("{} = {}", "pack.app.name", env.getProperty("pack.app.name"));
    logger.info("{} = {}", "pack.app.description", env.getProperty("pack.app.description"));
  }
}

The limitation is that you must know each property name; the API does not provide a way to enumerate all keys.

6. Using @Value

The most common approach is to inject values directly into fields with @Value:

@Component
public class ValuePropComponent {
  @Value("${xxgg.title}")
  private String title;
  @Value("${pack.app.name}")
  private String name;
  // ...
}

This method requires a field for each property, which can become cumbersome for many keys.

7. Using @ConfigurationProperties

Group related properties into a POJO with @ConfigurationProperties:

@Component
@ConfigurationProperties(prefix = "pack.app")
public class AppProperties {
  private String title;
  private String version;
  // getters and setters
}

The corresponding YAML fragment is:

pack:
  app:
    title: xxxooo
    version: 1.0.0

8. Using ConfigurableBeanFactory

The ConfigurableBeanFactory can resolve placeholders programmatically:

@Component
public class GetConfig implements CommandLineRunner {
  private final ConfigurableBeanFactory beanFactory;
  public GetConfig(ConfigurableBeanFactory beanFactory) { this.beanFactory = beanFactory; }
  @Override
  public void run(String... args) throws Exception {
    System.err.println(this.beanFactory.resolveEmbeddedValue("${pack.validation.excludes}"));
  }
}

If the placeholder does not correspond to an existing property, an exception is thrown.

9. Using Spring Boot Actuator

Add the Actuator starter:

<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-actuator</artifactId>
</dependency>

Enable the /env endpoint in application.yml:

management:
  endpoints:
    web:
      exposure:
        include: env

After starting the application, visit http://localhost:8080/actuator/env. The response is a large JSON document containing every environment variable and property, as shown in the screenshot.

Be careful not to expose sensitive data through this endpoint.

10. Summary of Methods

The article covers seven distinct techniques, each with trade‑offs: event‑based enumeration offers a complete list; Environment and @Value are simple for known keys; @ConfigurationProperties groups related settings; ConfigurableBeanFactory resolves placeholders on demand; and Actuator provides a ready‑made HTTP view of the entire environment.

JavaConfigurationSpring Bootenvironmentactuatorproperties
Spring Full-Stack Practical Cases
Written by

Spring Full-Stack Practical Cases

Full-stack Java development with Vue 2/3 front-end suite; hands-on examples and source code analysis for Spring, Spring Boot 2/3, and Spring Cloud.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.