config
Install
For Maven, add a dependency in pom.xml
,
<dependency>
<groupId>org.computelab</groupId>
<artifactId>config</artifactId>
<version>0.2.1</version>
</dependency>
Or, if you use Gradle, in build.gradle
,
compile group: 'org.computelab', name: 'config', version: '0.2.1'
Usage
Suppose we have an app code-named "Foo". Foo runs as a web API that binds to a port. Under the hood, Foo uses another web API, called "Bar", which has an endpoint and requires an access token to access it.
Foo has the following configurable items: a port number, Bar's endpoint, and an access token to access Bar.
DefaultConfig
The easiest is to use DefaultConfig
.
import org.computelab.config.Config;
import org.computelab.config.DefaultConfig;
// The app name will be used for the hidden folder under the user's home directory
// In this case, ~/.foo/app.properties is the config file in the user's home for "foo"
// This file is optional though. Details later.
final String appName = "foo";
final Config config = DefaultConfig.create(appName);
// Read the config entries
final int port = config.getAsInt("port");
final String barEndpoint = config.get("bar.endpoint");
final String barToken = config.get("bar.token");
In order for this to work, configure the Foo app like below,
1. Source code resource
This file is optional but is strongly recommended.
In the source code, under src/main/resources
, add a file app.properties
with the following content,
port = 8080
bar.endpoint = http://localhost:8089/
bar.token = dummy
These are Java properties. Note the keys must match those specified in the code. The values in this app.properties
are default values. Ideally the values are sufficient to launch the app locally.
Note sensitive data should be avoided here. For example, token is given a dummy value here. In a local stack, this token may be checked against the same dummy value or may not be checked at all.
This configuration file is optional but is highly recommended. Remember the goal is for every developer to run the code locally with zero custom configuration needed.
2. User's home directory
Each individual developer can have a custom configuration for the Foo app. In the user's home directory, create a hidden folder .foo
. Make sure only the current user can access the folder and its content. In this hidden folder, create the file app.properties
,
bar.endpoint = https://beta.bar.net:8089/
bar.token = 9C6B9F9B9DCB1
Note that in this file, it overwrites the default values of bar.endpoint
and bar.token
.
This file is optional. It is mainly for local integration test against local or remote resources.
3. Environment variables
When the app is deployed, configuration values can be passed in as environment variables. This further overwrites values defined in the source code and in user's home directory. For example, when deploying Foo to a staging environment, the staging environment can set the following environment variables,
export BAR_ENDPOINT="https://staging.bar.net:8089/"
export BAR_TOKEN="3C53CD2D51F71"
This is usually where sensitive data are passed to the app. As shown here, we are passing in a real token to access Bar.
4. System properties
Alternatively, system properties can be passed to the VM on the java
command. For example, setting the port to 443,
java -jar foo.jar -Dport=443
Define your own config
Tired of typing key names? Hide them by creating your own config type. The following example wraps DefaultConfig
into FooConfig,
import org.computelab.config.Config;
import org.computelab.config.DefaultConfig;
public class FooConfig() {
private static final String APP_NAME = "foo";
private final Config config;
public FooConfig() {
config = DefaultConfig.create(APP_NAME);
}
public int port() {
return config.getAsInt("port");
}
public String barEndpoint() {
return config.get("bar.endpoint");
}
public String barToken() {
return config.get("bar.token");
}
}
Once you have the FooConfig defined, it can be injected using your favorite framework.