What will be done here?

In the third part of this series on Spring Boot, we implemented a service that calls Github’s API to retrieve data on a user’s repositories. So far we use a hard-coded string for the URL. This might be ok for test or demonstration purposes. In real applications it is better to store the URL (or parts of it) in properties.
Spring provides a couple of ways to read properties and in the following two of them are described.

Using @Configuration

A class that is annotated with @Configuration will be handled as a bean. Spring loads the properties at application start and stores the values in member variables of the class. In the context of the sample application we could store parts of the URL: The member variables are annotated with @Value followed by a parameter that represents the key in the properties file.

@Configuration
public class GithubRepositoryServiceConfiguration {
  @Value("${github.base.url}")
  private String githubBaseUrl;

  @Value("${github.user.path}")
  private String githubUserPath;

  @Value("${github.userrepo.path}")
  private String githubUserRepos;
...
}

The properties themselves are stored in the file application.properties that is located in the src/main/resourcesfolder.

github.base.url=https://api.github.com/
github.user.path=users/
github.userrepo.path=repos

Next, we can use the values in the service class

public List<Repository> getRepositoriesForUser(String username) {
  ResponseEntity<Repository[]> responseEntity = restTemplate.getForEntity(
    String.format(configuration.getGithubBaseUrl() + configuration.getGithubUserPath() + "%s/"
    + configuration.getGithubUserRepos(), username), Repository[].class);
  Repository[] response =  responseEntity.getBody();
  return Arrays.asList(response);
}

Using @ConfigurationProperties

Another approach to load such properties is to use @ConfigurationProperties followed by a parameter called prefix.

@ConfigurationProperties(prefix = "github.api")
public class GithubRepositoryServiceConfiguration {
  private String baseUrl;
  private String userPath;
  private String userRepoPath;
...
}

Here we do not need to annotate the member variables. However, their names have to match exactly the naming in the properties file.

github.api.baseUrl=https://api.github.com/
github.api.userPath=users/
github.api.userRepoPath=repos

Classes annotated with @ConfigurationProperties are no treated as beans. When the application is started, the following error occurs:

Field configuration in se.mbaeumer.githubhero.part6.services.GithubRepositoryService required a bean of type 'se.mbaeumer.githubhero.part6.config.GithubRepositoryServiceConfiguration' that could not be found.

Action:

Consider defining a bean of type 'se.mbaeumer.githubhero.part6.config.GithubRepositoryServiceConfiguration' in your configuration.

To resolve this, the annotation @EnableConfigurationProperties is required in the main class:

@EnableConfigurationProperties(GithubRepositoryServiceConfiguration.class)
public class SpringBootLabGithubHeroApplication {
  public static void main(String[] args) {
    SpringApplication.run(SpringBootLabGithubHeroApplication.class, args);
  }
	
  @Bean
  public RestTemplate restTemplate() {
    return new RestTemplate();
  }
}

The annotation takes the configuration class as parameter.

Further resources

Configuration example
ConfigurationProperties example