Maven Profile和Spring Proflie

一个优秀的构建系统必须足够灵活,它应该能让项目在不同的环境下都能成功地构建。Maven为了支持构建的灵活性,内置了三大特性,即属性、Profile和资源过滤。这里我们只介绍Profile的使用,以及和Spring Profile的整合。

1、Maven Profile

典型的项目一般都会有开发环境、测试环境以及生产环境,在不同的环境中,项目的源码应该使用不同的方式进行构建,这就要求项目构建的时候需要识别所在环境并使用正确的配置。为了能让构建在各个环境下方便的移植,Maven引入了profile的概念,profile可以让我们定义一系列的配置信息,然后指定其激活条件。这样我们就可以定义多个profile,然后每个profile对应不同的激活条件和配置信息,从而达到不同环境使用不同配置信息的效果。

1.1 profile的种类

根据具体需要,可以在以下位置声明profile:
- pom.xml: 很显然,pom.xml中声明的profile只对当前项目有效。
- 用户settings.xml: 用户目录下 .m2/settings.xml中的profile对本机上该用户所有的Maven项目有效。
- 全局settings.xml: Maven安装目录下conf/setting.xml中的profile对本机中上所有的Maven项目有效。
- profiles.xml(Maven2): 还可以在项目根目录下使用一个额外的profiles.xml文件来声明profile,不过该特性已经在Maven3中被移除。建议用户将这类profile移到settings.xml中。

使用最多的两种方式是用户settings.xml和pom.xml方式,下面简要说明下不同位置的profile可使用的元素种类:

POM中的profile可使用的元素,

<project>
    <repositories></repositories>
    <pluginRepositories></pluginRepositories>
    <distributionManagement></distributionManagement>
    <dependencies></dependencies>
    <dependencyManagement></dependencyManagement>
    <modules></modules>
    <properties></properties>
    <reporting></reporting>
    <build>
        <plugins></plugins>
        <defaultGoal></defaultGoal>
        <resources></resources>
        <testResources></testResources>
        <finalName></finalName>
    </build>
</project>

POM外部的profile可使用元素,

<project>
    <repositories></repositories>
    <pluginRepositories></pluginRepositories>
    <properties></properties>
</project>

1.2 激活方式

1.2.1 默认激活方式
<profiles>
    <profile>
        <id>dev</id>  
        <activation>
            <activeByDefault>true</activeByDefault>
        </activation>
        ...
    </profile>
</profiles>

如果POM中任何一个profile通过其他方式激活诶激活了,这个默认配置就会失效。

1.2.2 命令行激活

可以使用mvn命令行参数-P加上profile的id来激活profile,多个id之间以逗号分隔。
$mvn clean install -Pdev

1.2.3 settings文件显示激活

如果希望某个profile一直处于激活状态,就可以配置settings.xml文件的activeProfiles元素。

<settings>
    ...
    <activeProfiles>
        <actvieProfile>dev</activeProfile>
    </activeProfiles>
    ...
</settings>
1.2.4 系统属性激活

用户可以配置当某系统属性存在的时候,自动激活profile。然后在命令行声明系统属性:$mvn clean install -Dtest,这种方式和第2种很像,而且多个profile可以使用同一个系统属性来激活。

<profiles>
    <profile>
        <activation>
            <property>
                <name>test</name>
            </property>
        </activation>
        ...
    </profile>
</profiles>
1.2.5 操作系统环境激活

Profile可以自动根据操作系统环境激活。这里的family的值包括Windows、UNIX和Mac等,而其他几项name、arch、version,用户可以通过查看环境中的系统属性os.name、os.arch、os.version获得。

<profiles>
    <proflie>
        <activation>
            <os>
                <name>Windows XP</name>
                <family>Windows</family>
                <arch>x86</arch>
                <version>5.1.2600</version>
            </os>
            ...
        </activation>
    </profile>
</profiles>
1.2.6 文件存在与否激活

Maven能够根据项目中某个文件存在与否来决定是否激活profile.

<profiles>
    <profile>
        <activation>
        <file>
            <missing>x.properties</missing>
            <exists>y.properties</exists>
        </file>
        </activation>
        ...
    </profile>
</profiles>

1.3 示例

在开发的过程中,我们一般会正在src/main/resource目录下放置配置文件xxx.xml或者xxx.properties。下面以数据库的配置为例来说明profile的使用方式,假设配置文件中有如下数据库配置:

database.jdbc.driverclass=com.mysql.jdbc.Driver
database.jdbc.connectionURL=jdbc:mysql://localhost:3306/test
database.jdbc.username=dev
database.jdbc.passowrd=dev-pwd

如果只是在一个环境中使用就没有什么问题,但是当测试人员想要构建项目进行测试,或者部署上线到生产环境,往往这些环境的信息是不同的,这就需要修改这个配置文件了。将这些配置参数提取到profile中:

database.jdbc.driverclass=${db.driver}
database.jdbc.connectionURL=${db.url}
database.jdbc.username=${db.username}
database.jdbc.passowrd=${db.password}

pom.xml文件中新增prfile:

<profiles>
    <profile>
        <id>dev</id>
        <properties>
            <db.driver>com.mysql.jdbc.Driver</db.driver>
            <db.url>jdbc:mysql://localhost:3306/test</db.url>
            <db.username>dev</db.username>
            <db.password>dev-pwd</db.password>
        </properties>
    </profile>
    <profile>
        <id>deploy</id>
        <properties>
            <db.driver>com.mysql.jdbc.Driver</db.driver>
            <db.url>jdbc:mysql://localhost:3306/deploy</db.url>
            <db.username>deploy</db.username>
            <db.password>deploy-pwd</db.password>
        </properties>
    </profile>
</profiles>

有了属性定义,配置文件中也有了这些属性。但是Maven属性默认只有在POM中才会被解析,放在src/main/resources/下并不会被解析。因此需要借助maven-resource-plugin插件来为资源目录开启过滤,这样Maven就能解析资源文件中的Maven属性了。

<resources>
    <resource>
        <directory>${project.basedir}/src/main/resources</directory>
        <filtering>true</filtering>
    </resource>
    <resource>
        <directory>${project.basedir}/src/test/resources</directory>
        <filtering>true</filtering>
    </resource>
</resources>

Maven允许用户声明多个资源目录,并且为每个资源目录提供不同的过滤配置。最后,只需要在命令行激活profile,Maven就能够在构建项目的的时候使用profile中属性值替换数据库配置文件中的属性引用。运行命令行如下:
$mvn clean install -Pdev

2、Spring Profile

Spring profile是Spring 3.1引入的概念,通过定义profile来将若干不同的bean定义组织起来,从而实现不同环境自动激活不同的profile来切换配置参数的功能。

在实际项目的开发过程中,开发环境一般使用项目中自带文件,而在部署生产环境的时候使用指定目录下的配置文件,下面就以配置文件切换为例来说明profile的使用方法:

2.1 在applicationContext.xml里定义profile

  <!-- dev环境 -->
  <beans profile="dev">
      <context:property-placeholder ignore-resource-not-found="true" location="classpath:config/xxxx.properties" />    
  ....
  </beans>
  <!-- deploy环境 -->
  <beans profile="deploy">
      <context:property-placeholder ignore-resource-not-found="true" location="file:D:\xx\xxx\xxxx.properties"/>  
  ....
  </beans>

或者:

  <context:property-placeholder system-properties-mode="OVERRIDE" file-encoding="UTF-8" properties-ref="configProperties" />

  <beans profile="dev">
        <bean id="configProperties" class="org.springframework.beans.factory.config.PropertiesFactoryBean">
            <property name="locations">
                <list>
                    <value>classpath:config/xxxx.properties</value>
                </list>
            </property>
        </bean>
    </beans>

    <beans profile="deploy">
        <bean id="configProperties" class="org.springframework.beans.factory.config.PropertiesFactoryBean">
            <property name="locations">
                <list>
                    <value>file:D:\xx\xxx\xxxx.properties</value>
                </list>
            </property>
        </bean>
    </beans>

2.2 在web.xml定义默认profile

默认profile是指在没有任何profile被激活的情况下,默认profile内定义的内容将被使用。

  <context-param>
        <param-name>spring.profiles.default</param-name>
      <param-value>dev</param-value>
    </context-param>

2.3 激活profile

spring为我们提供了大量的激活profile的方法,可以通过代码来激活,也可以通过系统环境变量、JVM参数、servlet上下文参数来定义spring.profiles.active参数激活profile,这里我们通过定义servlet上下文参数参数实现。

<context-param>
  <param-name>spring.profiles.active</param-name>
  <param-value>${profiles.activation}</param-value>
</context-param>

其中,${profiles.activation}需要在实际运行项目的时候指定环境变量,这样既可以做到不同的环境下切换不同的配置文件,也可以直接设置具体值,这样可以省去2.4节的环境属性设置。

2.4 运行项目

这里以jetty服务器做介绍,如果使用maven内置jetty插件启动,我们需要在pom中定义环境属性,如下图:
"maven-jetty环境变量配置"
如果是使用eclipse jetty插件启动,我们需要在服务器配置中增加环境变量,如下图:
"eclipse-jetty环境变量配置"

3、Maven整合Spring profile

实际项目中我们大多以Maven来管理项目,所以这一部分来介绍如何在Maven中整合Spring profile。
1.3节的示例已经介绍了在maven的pom文件中如何增加profile,并且指定了默认的激活profile,现在我们将其改为

<profiles>
    <profile>
        <id>dev</id>
        <activation>
            <activeByDefault>true</activeByDefault>
        </activation>
        <properties>
            <profiles.activation>dev</profiles.activation>
        </properties>
    </profile>
    <profile>
        <id>deploy</id>
        <properties>
            <profiles.activation>deploy</profiles.activation>
        </properties>
    </profile>
</profiles>

注意这里的<profiles.actviation>属性名称要和2.3 激活profile里配置的属性值${profiles.activation}对应,用于在打包的时候指定激活的profile

3.1 配置Maven插件,进行资源过滤

<plugin>
    <artifactId>maven-war-plugin</artifactId>
    <version>2.0.2</version>
    <configuration>
        <warName>${profiles.activation}</warName>
        <!-- 激活spring profile -->
        <webResources>
            <resource>
                <filtering>true</filtering>
                <directory>${basedir}/src/main/webapp</directory>
                <includes>
                    <include>**/web.xml</include>
                </includes>
            </resource>
        </webResources>
        <warSourceDirectory>${basedir}/src/main/webapp</warSourceDirectory>
        <webXml>${basedir}/src/main/webapp/WEB-INF/web.xml</webXml>
        <warName>实际打包名称或者用${profiles.activation}替代,否则会找不到war包</warName>  
    </configuration>
</plugin>

这一部很关键: 配置的目的是为了打包的时候,替换web.xml中配置的servlet上下文参数值${profiles.activation},如果不配置,会发现打包后的web.xml中${profiles.activation}并没有被替换。

3.2 打包

打包到部署环境
$mvn clean install -Pdeploy

打包到体验环境
$mvn clean install -Pdev

参考书籍:
1. Maven实战 许晓斌著
2. spring proflie参考网上资料以及实际使用


————本文结束感谢您的阅读————

猜你喜欢

转载自blog.csdn.net/hzygcs/article/details/78897989