Apache Maven 2.0 不遗余力确保生成可移植的构建. 这意味着: 容许在POM内的构建配置, 避免全部文件系统的引用(在继承\依赖) , 而且更严重地依赖本地仓库来存储支持该功能的元数据.html
然而, 有时移植性不是彻底可行的. 在某些特定状况下, 插件可能须要使用本地文件系统路径来配置. 在其余状况下, 可能须要一个稍微有点不一样的依赖设置, 且该工程的名字可能须要稍微调整一下. 在其余时候, 你可能甚至须要根据检测到的构建环境, 在构建生命周期中包含一整个插件.linux
针对这些状况, maven 2.0 介绍了构建配置文件的概念(build profile). 配置文件经过使用POM中的元素子集来指定(增长一个额外的section), 在多种状况下被触发. 配置文件在构建时修改POM, 而且为变量设置不一样的目标环境(例如, 在开发, 测试和产品环境中的数据库服务器路径). 这样, 配置文件很容易致使不一样成员产生不一样的构建结果. 然而, 使用得当, 可在保留工程可移植性的同时, 使用配置文件. 这也将最少化使用 –f 操做的次数, 该操做容许用户建立其余不一样参数或配置的POM, 且更加可维护, 毕竟一个工程只能有一个POM.web
类型 | 定义位置 | 路径 |
Per Project 项目级 | POM | pom.xml |
Per User 用户级 | Maven-settings | %USER_HOME%/.m2/settings.xml |
Global 全局 | global Maven-settings | ${maven.home}/conf/settings.xml |
Profile descriptor | project basedir | profiles.xml |
一个配置文件可经过如下方式激活:数据库
该选项有一个参数列表: 用逗号分隔的 profile-ids. 当指定该选项时, 在参数中指定的profile将会被激活, 除了已被激活配置或 settings.xml的<activeProfiles> section激活的profiles以外.apache
mvn groupId:artifactId:goal -P profile-1,profile-2windows
运行结果是在目标目录下, 产生了两个文件, 它们的内容同样.服务器
该节中包含一个<activeProfile>元素列表, 每一个包含了一个profile-id.app
在<activeProfiles>标签下列出的 profiles将会默认地在每次工程使用它时被激活.maven
Maven的 settings.xml 文件能够在 %USER_HOME%/.m2 目录下找到. 若是不存在,则须要建立一个.ide
profile可根据检测出的生成环境的状态, 自动触发. 这些触发在<profile>下的<activation>一节中定义. 当前, 该检测仅限于JDK版本的前缀匹配\ 系统属性是否存在 或一个系统属性的值.
(1) 当JDK的版本号以"1.4"开头时, 下例中的配置将被触发.
(2) Maven 2.1中也可使用范围. 下例中表示版本 1.3, 1.4, 1.5.
注意, 右闭区间, 如: ,1.5], 也不表明包含全部的1.5版本, 由于不少状况下会有额外的 "patch release", 例如, _05就不能包含在这个区间里了.
(3) 系统属性 debug, 不管取何值, 都会触发下例.
(4) 系统属性 enviroment 取值为test时...
注意, 为了触发上例, 须要如下命令:
当文件缺失时, 就会激活:
上述配置设好后, 可以使用 mvn test 来查看 test profile 的结果. 而不是显式的使用-p选项.
能够用来卸载 activeByDefault 或者 经过激活配置 来激活的 profile.
咱们已经讨论了在哪里指定 profile, 以及如何激活它们. 而你能够在一个profile里指定什么将会很是有用. 由于涉及 profile配置的其余方面, 这个答案并不简单.
依据你选择的配置profile的方式, 你能够得到不一样的POM配置.
最严格意义上来讲, 在外置文件(好比 setting.xml 或 profiles.xml)中定义的profile是不可移植的. 任何看似有高机率改变构建结果的东西, 都会被限制在POM中的嵌入profiles. 像仓库列表之类的东西能够简单地做为一个准许工程的存储库, 而且不会改变构建的输出. 所以, 你只可能在settings.xml中修改 <repositories>和<pluginRepositories>节, 再加上一个额外的<properties>节.
<properties>节容许你指定 自由格式的 键值对, 包含在POM的插补过程当中. 这容许你经过格式${profile.provided.path} 指定一个插件配置.
另外一方面, 若是你的profiles能够合理地在pofile内部定义, 你能够有更多的选择. 代价就是你只能修改那个工程和它的子模块. 由于这些profiles 是内嵌定义的, 因此能够更好地保持可移植性. 所以, 你能够添加更多信息, 而避免了这些信息对其余用户不可用的风险.
在POM中定义profiles能够修改如下元素:
咱们不容许修改 POM-profiles 以外的一些pom 元素. 由于这些运行时修改不会在POM部署到资源系统时分发, 形成我的的工程构建彻底不一样于其余人的. 另外一个缘由是POM信息有时会被父POM复用.
外部文件存储, 好比settings.xml和profiles.xml, 也不支持 POM-profiles以外的元素. 当有效的POM文件被部署到一个远程资源库时, 任何人均可以获取它的信息, 而且直接用来构建一个maven工程. 如今,假设咱们能够在对一个构建很是重要的 dependencies 中设置 profiles, 或者其余除POM-profiles以外的元素. 那么最可能的是咱们不但愿其余人能从资源库中使用POM, 甚至 构建它. 咱们也会考虑如何共享settingx.xml. 注意到太多要配置的文件是一件十分困扰的事, 并且难以维护. 底线就是, 既然这是构建数据, 它就应该放在POM中. maven 2 的一个目标就是将全部运行一个构建必须的信息都统一到一个文件中, 或者文件层次结构, 这就是POM.
隐患.
咱们已经提到过, 添加profiles到你的构建中可能会破坏工程的可移植性. 咱们更是强调了那些 profiles可能破坏工程移植性的情景.然而 , 重申这些点是值得的, 这是部分讨论, 关于使用profiles时要避免的隐患.
在使用profiles时, 有两个主要问题领域须要记住. 第一个是外部属性, 一般在插件配置中使用. 这形成了你工程的移植风险. 另外一个, 更微妙的领域, 是一个天然的profiles的不完整规范(Incomplete Specification of a Natural Profile Set).
外部属性定义, 是指那些在pom.xml以外定义的属性值,但又不是定义在一个其内部相关的profile中. 在POM中, 属性的最多见用法是插件配置. 没有属性, 当然可能打破项目的可移植性, 但这也可能致使构建失败. 例如, 在一个定义在settings.xml中的profile中指定一个appserver paths, 可能致使你的集成测试插件发生失败, 当团队中另外一个没有类似settings.xml的用户企图去构建时.
下面是一个web应用工程的pom片断:
在你本身的本地${user.home}/.m2/settings.xml中:
当你构建 集成测试 生命周期阶段时, 你的集成测试将会经过. 由于你提供的路径容许该测试插件安装和测试该web应用.
然而, 当你的同事尝试去构建 集成测试时, 他的构建会完全失败, 由于它不能处理插件配置参数<appserverPath>, 或者更糟地, 警告该参数${appserver.home}的值是无效的.
庆幸的是, 你的工程如今尚未移植. 在你的pom.xml中内联该profile, 能够帮助缓和该问题. 但明显的缺点是, 每一个工程层次(容许继承影响)如今必须指定该信息. 由于maven提供对工程继承的良好支持, 能够把这类配置放到团队级POM或相似的POM中的<pluginManagement>节中, 而后简单地继承路径.
另外, 不那么具备吸引力的答案是开发环境的标准化. 然而, 这每每会损害 maven能提供的生产率.
这个profile看起来很像上一个例子中的. 有一点很重要的不一样: 有一个面向开发环境的, 一个新的profile, 名为 appserverConfig-dev-2, 被添加了, 而且它有一个激活section, 将会在系统属性 env=dev-2时激活.
因此, 执行:
将会成功构建, 应用appserverConfig-dev-2 proflie.
当执行:
也会成功构建, 应用了appserverConfig-dev profile.
然而 , 执行:
不会成功构建. 为何? 由于, ${appserver.home}的值不会是一个有效的路径, 部署和测试你的web应用没法进行. 咱们在编写profiles时尚未考虑env=production的状况. 这样不完整的规范意味着, 咱们已经成功地根据开发环境来限制了有效的目标环境. 你的同事, 也有多是你的manager, 将不会看到这个笑话. 当你建立profiles来处理这些相似的状况时, 必定要解决全部的target集.
用户特定的配置文件能够以相似的方式来进行.
肯定活动的profiles, 将帮助用户了解在一次构建过程当中, 哪些特定的profiles已经被执行了. 咱们可使用maven help plugin来查询一次构建过程当中哪些profiles是生效的.
假设, 分别在pom.xml和settings.xml中配置profile以下:
执行如下命令:
感受我翻译得很差 =,= 理解上有点困难...因此梳理一下...
profile能够看做是pom的一部分. 简单来讲, profile支持定义一系列的配置信息, 而后在不一样的环境中, 能够自动触发不一样的配置. 好比, 在windows下是一套配置, 在linux下是另外一套配置.
能够选择在多个地方定义 profile. 在不一样地方定义, 做用范围不一样. 针对某个项目的配置, 能够写在 pom.xml中. 针对某个用户的配置, 能够在用户目录下的 .m2目录下的 setting.xml 文件中定义. 针对全局的配置, 能够在maven安装目录下的 conf目录中的 setting.xml 文件中定义.
profile中能定义的配置信息与所处位置相关. 若是是在settings.xml中, 是全局意义的, 只能定义一些相对而言做用范围较广的配置, 好比<repositories>, <pluginRepositories>, <properties>. 定义在<properties>中的键值对能够在pom.xml中使用.
若是是在pom.xml中, 能够根据项目的不一样来定义不一样的细节配置信息. 主要有: <repositories>, <pluginRepositories>, <dependencies>, <plugins>, <properties>, <dependencyManagement>, <distributionManagement>, <build>下的子元素.
profile有多种不一样的激活方式. 1) 在profile的<activation>下, 将<activeByDefault>元素的值设为true, 就表示没有指定其余profile为激活状态时, 默认激活该profile. 2) 在settings.xml中使用<activeProfiles>指定自动激活的profile名. 这样的profile在全部状况下都处于激活状态. 3) 显式命令使用-p选项,指定profile. 4) 根据不一样的环境来激活, 如jdk版本, 操做系统, 系统属性, 5) 根据文件是否存在来激活.
可使用 mvn help: active-Profiles来查看处于激活状态的profiles.
http://maven.apache.org/guides/introduction/introduction-to-profiles.html