Java best practices recommends read properties as constants. So, what do you think is the best approach to reach it? My approach is: A Configuration class to read the properties file only one time (singleton pattern) and use this class to read properties when needed as constants. And a Constants class to store:
public final class Configurations {
private Properties properties = null;
private static Configurations instance = null;
/** Private constructor */
private Configurations (){
this.properties = new Properties();
try{
properties.load(Thread.currentThread().getContextClassLoader().getResourceAsStream(Constants.PATH_CONFFILE));
}catch(Exception ex){
ex.printStackTrace();
}
}
/** Creates the instance is synchronized to avoid multithreads problems */
private synchronized static void createInstance () {
if (instance == null) {
instance = new Configurations ();
}
}
/** Get the properties instance. Uses singleton pattern */
public static Configurations getInstance(){
// Uses singleton pattern to guarantee the creation of only one instance
if(instance == null) {
createInstance();
}
return instance;
}
/** Get a property of the property file */
public String getProperty(String key){
String result = null;
if(key !=null && !key.trim().isEmpty()){
result = this.properties.getProperty(key);
}
return result;
}
/** Override the clone method to ensure the "unique instance" requeriment of this class */
public Object clone() throws CloneNotSupportedException {
throw new CloneNotSupportedException();
}}
The Constant class contains the references to the properties and the Constants.
public class Constants {
// Properties (user configurable)
public static final String DB_URL = "db.url";
public static final String DB_DRIVER = "db.driver";
// Constants (not user configurable)
public static final String PATH_CONFFILE = "config/config.properties";
public static final int MYCONSTANT_ONE = 1;
}
And the properties files would be:
db.url=www.myurl.com
db.driver=mysql
To read the properties and constants would be:
// Constants
int i = Constants.MYCONSTANT_ONE;
// Properties
String url = Configurations.getInstance().getProperty(Constants.DB_URL);
Do you think this is a good approach? What is your way to read properties and constants in Java?
Thanks in advance.
I found a better solution to homogenize the code and has everything as constants. With the same Configurations class and .properties file: Since getInstance() method is static it is possible to init the constants in the class Constants.
A class to store the name to the property in .properties file:
public class Properties {
// Properties (user configurable)
public static final String DB_URL = "db.url";
public static final String DB_DRIVER = "db.driver";
}
And then the Constant class will be:
public class Constants {
// Properties (user configurable)
public static final String DB_URL = Configurations.getInstance().getProperty(Properties.DB_URL);
public static final String DB_DRIVER = Configurations.getInstance().getProperty(Properties.DB_DRIVER );
// Constants (not user configurable)
public static final String PATH_CONFFILE = "config/config.properties";
public static final int MYCONSTANT_ONE = 1;
}
And finally to use them:
// Constants
int i = Constants.MYCONSTANT_ONE;
// Properties
String url = Constants.DB_URL;
I think it is a clean and elegant solution that fix constants and properties problems in tests.