将webapp的资源部署到maven存储库?

时间:2009-07-27 14:23:00

标签: java maven-2

这个问题有点像“最佳实践”问题,我的团队是Maven的新手,我正在寻找关于这个主题的最佳方法:

在处理包装为war的项目时,将其部署到Maven存储库(例如公司范围内的Nexus安装)的最佳方法是什么?

例如,假设您有一个webapp,其中特定于环境的属性文件(例如数据库连接字符串,日志记录配置等,基于dev / QA /生产环境而有所不同)包含在最终打包的应用程序中基于属性或环境变量。在构建这种类型的应用程序时,最有意义的是部署到您的存储库?它应该是具有生产设置的WAR文件,还是所有类的JAR而没有资源?

我要问的原因是,当您构建此类Web应用程序时,您确实拥有一个代码库以及一组特定于环境的资源文件。前者很有意义地部署到您的存储库,因此它可供其他项目使用,但后者没有多大意义分享并提供给其他人。

4 个答案:

答案 0 :(得分:3)

我建议您构建一个原始war项目,其中可能包含一些用于开发的默认文件,并将其部署到存储库。

然后,您可以构建多个依赖于war项目的项目,并提供自己的特定资源。


JavaOne 2009演示文稿Getting Serious About Build Automation: Using Maven in the Real World就如何做到这一点有一个很好的例子

  1. 创建'myapp-deploy'maven项目
  2. 在部署项目中,引用war项目

    <dependency>
        <groupId>myorg.myapp</groupId>
        <groupId>myapp-web</groupId>
        <version>${webapp.version}</version>
        <type>war</type>
    </dependency>
    
  3. 在部署项目中,使用叠加层从Web项目导入文件

    <plugin>
        <artifactId>maven-war-plugin</artifactId>
        <configuration>
            <warName>myapp-web</warName>
            <overlays>
                <overlay>
                    <groupId>myorg.myapp</groupId>
                    <artifactId>myapp-web</artifactId>
                    <excludes>
                         <exclude>WEB-INF/classes/config.properties</exclude>
                    </excludes>
                 </overlay>
              </overlays>
              <!-- some config elements not shown here -->
     </plugin>
    
  4. 在部署项目中,将部署项目中的额外资源包含到Web项目中

    <plugin>
        <artifactId>maven-war-plugin</artifactId>
        <configuration>
            <!-- some config elements not shown here -->
            <webResources>
                <resource>
                    <directory>${patch.path}</directory>
                </resource> 
            </webResources>
         </configuration>
     </plugin>
    

答案 1 :(得分:1)

我认为你应该建立一场战争。对于覆盖层而言,对于开发人员来说,“只是放弃了针对该环境的修复”是一种诱惑。

对环境变量和JNDI resources外部JNDI资源文件使用attach(如果需要,可以为每种类型的环境附加一个)。

当然,您需要一个进程来检索正确的资源文件并将其应用到您的环境中(使用密码和其他敏感变量进行调整),但这是一个相当简单的脚本练习。

答案 2 :(得分:1)

我把属性放在我的maven pom.xml中。首先,我整理了整个网络应用程序,以便为不同的层提供单独的罐子; persistenc / db,service,web(例如,spring mvc的控制器)和war。 war项目在src / main / resources中有jsps和properties / config / xml文件。

例如,我的父pom就是这样开始的:

<project
xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
    http://maven.apache.org/POM/4.0.0
    http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>

<groupId>edu.berkeley.ist.waitlist</groupId>

<artifactId>waitlist-parent</artifactId>

<modules>
    <module>../waitlist-core</module>
    <module>../waitlist-db</module>
    <module>../waitlist-web</module>
    <module>../waitlist-war</module>
    <module>../waitlistd</module>
</modules>

<build>
    <resources>
        <resource>
            <directory>src/main/resources</directory>
            <filtering>true</filtering>
        </resource>

        <resource>
            <directory>src/main/hbm</directory>
            <filtering>true</filtering>
        </resource>
    </resources>

<dependencyManagement>
    <!-- dependencies with exclusions -->
    <dependencies>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-aop</artifactId>

            <version>${version.springframework}</version>

            <exclusions>
                <exclusion>
                    <groupId>commons-logging</groupId>
                    <artifactId>commons-logging</artifactId>
                </exclusion>
            </exclusions>
        </dependency>

然后我有一堆配置文件,用于各种构建:

<profiles>
    <!-- ========================================================== -->
    <!-- local, hsql                                                -->
    <!-- ========================================================== -->
    <profile>
        <id>localhost-hsql</id>

        <activation>
            <activeByDefault>false</activeByDefault>
        </activation>

        <properties>
            <!-- need to specify ${basedir} so that hsql creates its files in the right place -->
            <db2.url>jdbc:hsqldb:file:${basedir}/target/waitlistv2;shutdown=true</db2.url>

            <db2.user>sa</db2.user>
            <db2.password />

            <jdbc-db2.driverClass>org.hsqldb.jdbcDriver</jdbc-db2.driverClass>

            <db2.schema>public</db2.schema>

            <db2.hibernate.default_schema>public</db2.hibernate.default_schema>

            <db2.hibernate.dialect>org.hibernate.dialect.HSQLDialect</db2.hibernate.dialect>

            <dbunit.dataTypeFactoryName>org.dbunit.ext.hsqldb.HsqldbDataTypeFactory</dbunit.dataTypeFactoryName>

            <hbmtool.haltOnError>false</hbmtool.haltOnError>

            <log.filename>/tmp/waitlist.log</log.filename>
        </properties>
    </profile>

例如,在waitlist-war / src / main / resources中是文件logback.xml,它以

开头
<configuration debug="true">
<appender class="ch.qos.logback.core.rolling.RollingFileAppender" name="RootFileAppender">
    <!-- set in the pom.xml file -->
    <file>${log.filename}</file>

因此,您可以看到由于maven的过滤,如何使用pom中的log.filename属性。

(我正在指定父pom中的所有版本,而子项目只是指定他们使用的依赖项,但是没有版本号。我不确定这是否是正确的方法,最佳实践等。

此外,waitlist-war依赖于waitlist-web,waitlist-web依赖于waitlist-core(我的服务层),waitlist-core依赖于waitlist-db。 Waitlistd是一个单独的应用程序,没有ui可以说,它取决于waitlist-core。)

答案 3 :(得分:0)

我非常喜欢只有一个版本的每个可部署版本。如果您有生产版本,测试版本等,这将通过必要的检查和重建减慢您的速度。 建立战争一次并对每个环境使用相同的战争。

这引出了一个问题,您如何处理特定于环境的属性。我通常采用混合方法。在可能的情况下,所有环境所需的所有属性都打包在战争中。然后战争根据它所处的环境加载正确的属性。应用程序可以确定使用系统属性的环境。

请参阅此处获取使用spring的示例:http://www.developer.com/java/ent/article.php/3811931

这可以很容易地适用于没有弹簧的情况。

某些属性不适合在战争中打包,例如生产密码。对于这些,上面链接的方法可以很容易地用于从外部文件路径加载属性。