Implement SpringBoot Multi-Environment Dynamic Configuration Switching for Dev, Test and Production Environments

Original Project Configuration

Your project's src/main/resources/application.yml might look like the following example (we use MySQL configuration here, other components like Redis follow the same pattern). Manually switching environments requires editing these values directly:

server:
  port: 8080
  tomcat:
    max-connections: 20
    threads:
      max: 20
      min-spare: 10
    accept-count: 10
spring:
  config:
    name: demo-app
  datasource:
    driver-class-name: com.mysql.cj.jdbc.Driver
    url: jdbc:mysql://localhost:3306/local_db?serverTimezone=GMT%2B8
    username: admin
    password: admin123
    type: com.alibaba.druid.pool.DruidDataSource

Use Spring Profile for Environment Switching

2.1 Create Environment-Specific Configuration Files

Create the following files under the src/main/resources directory:

  • application-dev.yml (development environment)
  • application-test.yml (testing environment)
  • application-prod.yml (production environment)

Spring Boot automatically recognizes these files due to its convention-over-configuration design philosophy, wich eliminates manual configuration overhead for most common integrations.

Quick note: Standard Spring Boot configuration file priority order is: bootstrap.properties > bootstrap.yml > application.properties > application.yml

Example content for application-dev.yml:

# Custom flag to verify active environment
appName: demo-app-dev

server:
  port: 8091

spring:
  datasource:
    driver-class-name: com.mysql.cj.jdbc.Driver
    url: jdbc:mysql://localhost:3306/dev_db?serverTimezone=GMT%2B8
    username: dev_user
    password: dev_pass123
    type: com.alibaba.druid.pool.DruidDataSource

The testing and production config files follow the same structure with environment-specific values.

2.2 Add Maven Profile Configuration

Add the following profile definitions to your pom.xml to support environment selection during build/run:

<profiles>
    <profile>
        <id>dev</id>
        <properties>
            <active-environment>dev</active-environment>
            <nacos-config-addr>127.0.0.1:8848</nacos-config-addr>
        </properties>
        <!-- Set this as the default active profile -->
        <activation>
            <activeByDefault>true</activeByDefault>
        </activation>
    </profile>
    <profile>
        <id>test</id>
        <properties>
            <active-environment>test</active-environment>
            <nacos-config-addr>127.0.0.1:8848</nacos-config-addr>
        </properties>
    </profile>
    <profile>
        <id>prod</id>
        <properties>
            <active-environment>prod</active-environment>
            <nacos-config-addr>127.0.0.1:8848</nacos-config-addr>
        </properties>
    </profile>
</profiles>

2.3 Enable Maven Resource Filtering

If you plan to use Maven to select the active environment, add the following resource filtering configuration to your pom.xml to ensure placeholders are replaced correctly:

<build>
    <resources>
        <resource>
            <directory>src/main/resources</directory>
            <filtering>true</filtering>
        </resource>
    </resources>
</build>

Note: If you manually set the active profile directly in application.yml, you can skip this step.

2.4 Update Main Application Configuration File

Modify your root application.yml to dynamically load the selected environment's configuration:

# Use Maven-selected active profile
spring:
  profiles:
    active: @active-environment@

# Alternatively, manually set the profile by uncommenting the line below:
# spring:
#   profiles:
#     active: dev

Test and Validate the Setup

3.1 Create a Test Controller

Add a REST controller to verify the active environment configuration:

import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
@RequestMapping("/env/api")
public class EnvironmentCheckController {

    @Value("${appName}")
    private String applicationName;

    @Value("${server.port}")
    private String serverPort;

    @GetMapping("/check")
    public String checkEnvironment() {
        return String.format("Active Environment: %s | Server Port: %s | App Name: %s", 
                applicationName.split("-")[1], serverPort, applicationName);
    }
}

3.2 Test Development Environment

By default, the dev profile is active. Start the application and visit http://localhost:8091/env/api/check to see the development environment confirmation.

3.3 Switch to Production Environment

Select the prod profile via your IDE's Maven tool window or run the following Maven command:

mvn clean package -Pprod
java -jar target/demo-app-0.0.1-SNAPSHOT.jar

The production configuration uses port 8092, so visit http://localhost:8092/env/api/check to validate.

3.4 Troubleshooting Common Issues

If you ancounter placeholder resolution errors after switching profiles, it is usually caused by cached Maven resources. To fix this:

  1. Clean the project's target directory
  2. Reload all Maven dependencies in your IDE
  3. Re-run the build or startup command

This issue does not affect the final packaged artifact, you can verify the active profile by checking the extracted application.yml inside the built JAR file.

Tags: SpringBoot Maven Profiles Environment Configuration Java Development Configuration Switching

Posted on Thu, 07 May 2026 19:38:09 +0000 by icesolid