Here are some possible practices that I have used or encountered. Their combination is usually necessary in practice.
Substituting variable values in conffiles when building
Here is an example of how this can be done with Apache Ant. Ant properties ( ${var.name} ) can be controlled using build configuration files:
<filterset id="variables.to.replace"> <filter token="APPNAME" value="${app.name}"/> <filter token="WEBAPP-PATH" value="${webapp.path}"/> <filter token="ENCRYPT-ALGORITHM" value="${encrypt.algorithm}"/> <filter token="ERROR-MAILTO" value="${error.mailTo}"/> </filterset> <copy todir="${properties.target.dir}"> <fileset dir="${basedir}/env/${run.env}/webapp/WEB-INF/classes" /> <filterset refid="variables.to.replace"/> </copy>
It's good that you get great control over the various configurations during build. The bad news is that the system tends to grow very difficult and difficult to maintain if you use this method extensively for a large number of different configurations. In addition, the need to create conffiles also means slower development cycles.
Variable substitution from conf inside war when launching webapp
This is what I usually do when using the Spring Framework, even if there is only one configuration to consider, taking advantage of the separation of concerns. With Spring, you can replace conf values with PlaceholderPropertyConfigurer inside the Spring context when running webapp. In this case, you should at any time choose the correct configuration that you can configure, for example, during assembly.
Compared to replacing build time, it is easier to temporarily manipulate values in uncompressed webapp if necessary. Of course, webapp needs to be reloaded if you change something, and manual changes will not be saved when the webapp is redistributed. Spring is also limited by the Spring context, so this does not work, for example. in web.xml (but with variables in web.xml, probably should be avoided due to its limitations).
Reading local conf from a predefined file
This approach is probably the easiest to configure: just come up with a path to the configuration file, for example. $HOME/mywebapp/conf.properties and make your webapp somehow read at startup.
Good thing you don't have to worry about conf when creating / deploying webapp. In any case, you should have reasonable conf settings, which can then be overridden by local conf.
The presence of conf in the database
This is the most flexible solution for overriding conf parameters, but can also be complicated in some cases. Having conf in a table with name and value columns should work in most cases.
Of course, you cannot configure the JDBC connection URLs in the database table, but this is a good solution for plain text / numeric conf, which affects the operation of webapp after the db connection has been configured. To avoid a performance penalty, make sure you cache the config in some way, if it is often available.
Additional practices
As indicated by kgiannakakis, it also helps to customize the configuration page for your application.