管理配置数据的最佳方法是什么

时间:2010-02-24 06:27:49

标签: java configuration-management modularity

我正在开发一款有4种产品的产品套件。现在,所有配置数据都在XML或属性文件中。这种方法不可维护,因为我们必须为不同的环境管理不同的配置文件(例如生产,开发等)。

那么,处理配置数据的最佳方法是什么?

另外,我们可以将其模块化为单独的模块吗?这样所有产品都可以使用这个模块。 我们不想使用属性文件。我正在寻找一种解决方案,我们可以将所有配置特定代码作为新的配置模块移动,并将所有配置数据保存在数据库中。

8 个答案:

答案 0 :(得分:22)

使用commons-configuration您可以使用统一的API来访问属性,无论它们是如何 - .properties,xml,JNDI等。例如:

config.properties

jdbcHost=192.168.12.35
jdbcUsername=dbuser
jdbcPassword=pass

config.xml

<config>
   <jdbcHost>192.168.12.35</jdbcHost>
   <jdbcUsername>dbuser</jdbcUsername>
   <jdbcPassword>pass</jdbcPassword>
</config>

在这两种情况下,都可以通过以下方式访问它们:

String host = config.getString("jdbcHost");

答案 1 :(得分:12)

你几乎就在那里......我将采用相同的方法,为通过类似于以下任一方法的方法运行的应用程序实例提供正确的配置文件:

  1. 以不同的方式命名所有配置文件,并让您的应用程序通过一些独特的标准(用户名,主机名等)将它们拉入:

    • 生产的.properties
    • developer1 的.properties
    • developer2 的.properties
  2. 将它们置于基于应用程序假定的环境变量的位置的代码库之外:

    • YOURAPP_CONFIG_DIR /server_config.xml
    • YOURAPP_CONFIG_DIR /database_config.properties
  3. 我甚至在同一个项目中使用了这些方法的组合(构建过程配置为#1,运行时配置为#2)。

答案 2 :(得分:5)

如果您的应用程序使用数据库,您可以按如下方式创建“配置”表:

create table configuration (mode char(3), key varchar(255), value varchar(1023));

您可以使用init脚本初始化它,例如init.sql,内容如下:

insert into configuration values ('pro', 'param1', 'value1'); -- production
insert into configuration values ('dev', 'param1', 'value1'); -- development
insert into configuration values ('tst', 'param1', 'value1'); -- testing
...

这种方法的好处如下:

  • 你一起编写脚本版本 你的代码
  • 您可以轻松扩展它以包含 每个用户或每个组的设置 添加用户/组ID
  • 您可以更改设置 运行时如果你需要这样做
  • 你可以使用相同的堆栈(JPA + DAO,Cayenne ......)你通常习惯 处理核心应用程序数据 处理配置数据

答案 3 :(得分:4)

对于我们所有的环境,配置数据都以属性文件的形式存在于目标计算机上。我们使用SpringFramework中的PropertyPlaceholderconfigurer将这些属性绑定到我们的应用程序,以便在环境中保持可移植性。

例如,只要我知道/etc/myapp/database.properties将存在于我的应用程序将运行的任何机器上,那么在我的弹簧配置中,我只需要这样的东西:

    <bean id="myPropertyConfigurer"
    class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
    <property name="locations">
        <list>
            <value>/etc/myapp/database.properties</value>
        </list>
    </property>
</bean>
<bean id="myDataSource" class="org.apache.commons.dbcp.BasicDataSource">
    <property name="driverClassName" value="com.mysql.jdbc.Driver" />
    <property name="url"
        value="jdbc:mysql://${db.host}:3306/${db.name}" />
    <property name="username" value="${db.user}" />
    <property name="password" value="${db.pass}" />     
</bean>

Spring类有很多关于属性文件可以存在的选项。您甚至可以将它们替换为环境变量并将其传递出去:

    <bean id="myPropertyConfigurer"
class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
    <property name="searchSystemEnvironment" value="true" />
    <property name="systemPropertiesModeName" value="SYSTEM_PROPERTIES_MODE_OVERRIDE" />
    <property name="locations">
        <list>
            <value>${database.configuration.file.url}</value>
        </list>
    </property>
</bean>

在bash_profile(或其他)中: export JAVA_OPTS =“ - Ddatabase.configuration.file.url = file:///etc/myapp/database.properties”

或者根据你正在做的事情调用“java”时传入相同的-D选项。

FWIW,我们将我们的属性文件作为RPM单独维护。

答案 4 :(得分:2)

有很多不同的策略。所有这些都很好,取决于最适合你的。

  1. 构建单个工件并将配置部署到单独的位置。工件可以有占位符变量,在部署时,可以读入配置。查看Springs属性占位符。它适用于使用Spring的webapps,并且不涉及参与操作。
  2. 拥有一个位于webapp之外的外部化属性配置。保持位置不变并始终从属性配置中读取。在任何阶段更新配置,重新启动将是新值。
  3. 如果您正在修改环境(即正在使用的应用程序服务器或用户/组权限),请查看使用上述方法与puppet或chef。另请参阅使用这些工具管理配置文件。

答案 5 :(得分:0)

环境变量是最简单的方法。像往常一样设置它们,使用System.getenv("...")

访问它们

答案 6 :(得分:0)

Config是一个配置文件管理工具。您可以创建在所有环境中通用的配置,也可以创建特定于环境的配置。您可以继续使用XML和属性文件,并让Config维护环境中的差异。您可以将Config视为您的集中式数据库,它可以以您希望的格式输出配置文件。只要您需要配置文件,只需将其从Config部署(推或拉)到您想要的位置即可。请注意,我是Config团队的一员。

答案 7 :(得分:-4)

这是一个简单的愚蠢解决方案。

代码段,首先尝试使用当前目录中的属性文件。如果失败,请改为使用资源目录(或jar文件)中的属性文件。

    Properties configFile = new Properties();
    try {
        configFile.load(new FileInputStream("production.properties"));
    } catch (Exception e) {
        System.err.println("Can not read properties, try to use default properties file.");
        configFile.load(this.getClass().getClassLoader().
                    getResourceAsStream("development.properties"));
    }