Java Maven:自定义web-app项目的web.xml

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3298763/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-13 21:51:49  来源:igfitidea点击:

Maven: Customize web.xml of web-app project

javaweb-applicationsmaven-2profileweb.xml

提问by Markos Fragkakis

I have a web application Maven project, and I want to customize the web.xml file depending on the Profile that is running. I am using the Maven-War-plugin, which allows me to define a "resources" directory, where the files may be filtered. However, filtering alone is not sufficient for me.

我有一个 Web 应用程序 Maven 项目,我想根据正在运行的配置文件自定义 web.xml 文件。我正在使用 Maven-War-plugin,它允许我定义一个“资源”目录,其中可以过滤文件。但是,仅过滤对我来说是不够的。

In more detail, I want to include (or exclude)the whole section on security, depending on the profile I an running. This is the part:

更详细地说,我想包括(或排除)整个安全部分,具体取决于我正在运行的配置文件。这是部分:

....
....

<security-constraint>

    <web-resource-collection>
        <web-resource-name>protected</web-resource-name>
        <url-pattern>/pages/*.xhtml</url-pattern>
        <url-pattern>/pages/*.jsp</url-pattern>
    </web-resource-collection>

    <auth-constraint>
        <role-name>*</role-name>
    </auth-constraint>

    </security-constraint>
        <login-config>
        <auth-method>${web.modules.auth.type}</auth-method>
        <realm-name>MyRealm</realm-name>
    </login-config>

<security-constraint>

....
....

If this is not done easily, is there a way to have two web.xml files and select the appropriate one depending on the profile?

如果这不容易完成,有没有办法拥有两个 web.xml 文件并根据配置文件选择适当的一个?

采纳答案by matt b

is there a way to have two web.xml files and select the appropriate one depending on the profile?

有没有办法拥有两个 web.xml 文件并根据配置文件选择合适的文件?

Yes, within each profile you can add a configuration of the maven-war-pluginand configure each to point at a different web.xml.

是的,在每个配置文件中,您可以添加 的配置并将每个配置文件maven-war-plugin配置为指向不同的web.xml.

<profiles>
    <profile>
        <id>profile1</id>
        <build>
            <plugins>
                <plugin>
                    <groupId>org.apache.maven.plugins</groupId>
                    <artifactId>maven-war-plugin</artifactId>
                    <configuration>
                        <webXml>/path/to/webXml1</webXml>
                    </configuration>
                </plugin>
                 ...

As an alternative to having to specify the maven-war-pluginconfiguration in each profile, you can supply a default configuration in the main section of the POM and then just override it for specific profiles.

作为必须maven-war-plugin在每个配置文件中指定配置的替代方法,您可以在 POM 的主要部分提供默认配置,然后仅针对特定配置文件覆盖它。

Or to be even simpler, in the main <build><plugins>of your POM, use a property to refer to the webXmlattribute and then just change it's value in different profiles

或者更简单,在<build><plugins>你的 POM 中,使用一个属性来引用该webXml属性,然后在不同的配置文件中更改它的值

<properties>
    <webXmlPath>path/to/default/webXml</webXmlPath>
</properties>
<profiles>
    <profile>
        <id>profile1</id>
        <properties>
            <webXmlPath>path/to/custom/webXml</webXmlPath>
        </properties>
    </profile>
</profiles>
<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-war-plugin</artifactId>
            <configuration>
                <webXml>${webXmlPath}</webXml>
            </configuration>
        </plugin>
        ...

回答by Brian M. Carr

"matt b" has already posted the answer that is the most maven way of doing it. It is the way I'd recommend doing it 99% of the time.

“matt b”已经发布了答案,这是最行之有效的方法。这是我建议在 99% 的情况下都这样做的方式。

However, occasionally, your configuration file might be quite complicated, and it doesn't make much sense to duplicate the whole file for each environment when only one XML stanza differs. In these cases, you can abuse property filtering to accomplish your goal.

但是,有时,您的配置文件可能非常复杂,当只有一个 XML 节不同时,为每个环境复制整个文件没有多大意义。在这些情况下,您可以滥用属性过滤来实现您的目标。

Warning, a very duct-tape-y solution follows, and will not be for the faint of heart:

警告,下面是一个非常像胶带一样的解决方案,不适合胆小的人:

In your pom.xml:

在你的 pom.xml 中:

Attention StackOverflow Editors!!!!

请注意 StackOverflow 编辑器!!!

The html entity escaping is a part of the solution. The solution will NOT work if you replace it all with greater-than and less-than signs. Please leave the answer as is...

html 实体转义是解决方案的一部分。如果您将其全部替换为大于号和小于号,则该解决方案将不起作用。请按原样保留答案...

<properties>
    <test.security.config>
        &lt;security-constraint&gt;
            &lt;web-resource-collection&gt;
                &lt;web-resource-name&gt;protected&lt;/web-resource-name&gt;
                &lt;url-pattern&gt;/pages/*.xhtml&lt;/url-pattern&gt;
                &lt;url-pattern&gt;/pages/*.jsp&lt;/url-pattern&gt;
            &lt;/web-resource-collection&gt;

            &lt;auth-constraint&gt;
                &lt;role-name&gt;*&lt;/role-name&gt;
            &lt;/auth-constraint&gt;

            &lt;/security-constraint&gt;
                &lt;login-config&gt;
                &lt;auth-method&gt;${web.modules.auth.type}&lt;/auth-method&gt;
                &lt;realm-name&gt;MyRealm&lt;/realm-name&gt;
            &lt;/login-config&gt;

        &lt;security-constraint&gt;
    </test.security.config>
</properties>

in your web.xml

在你的 web.xml

....
${test.security.config}
....

Because non-existent properties evaluate to an empty string, your configurations which do not have this property set (or the property is an empty xml tag) will evaluate to a blank line here.

由于不存在的属性计算为空字符串,因此未设置此属性(或该属性为空 xml 标记)的配置将计算为空行。

It's ugly, and the xml is hard to modify in this form. However, if your web.xml is complex and you pose a greater risk of 4-5 copies of the web.xml getting out of sync, this may be an approach that will work for you.

很难看,这种形式的xml很难修改。但是,如果您的 web.xml 很复杂并且您带来了 4-5 个 web.xml 副本不同步的更大风险,那么这可能是一种适合您的方法。

回答by Chris Clark

There's a third, compromise option which I implemented in my project. It keeps everything in one web.xml while still making both it and the pom.xml readable. In my case, I had a need to sometimes have security and sometimes have no security, depending on the environment.

我在项目中实施了第三个折衷方案。它将所有内容保存在一个 web.xml 中,同时仍然使其和 pom.xml 都可读。就我而言,我有时需要有安全性,有时需要没有安全性,这取决于环境。

So what I did was:

所以我所做的是:

In the pom.xml, define two profiles (or however many you need). Within the profiles, include two properties. When you want security, you leave them empty, like this:

在 pom.xml 中,定义两个配置文件(或您需要的任意多个)。在配置文件中,包括两个属性。当你想要安全时,你把它们留空,就像这样:

<enable.security.start></enable.security.start>
<enable.security.end></enable.security.end>

When you want to exclude all of the security, you define them as follows:

如果要排除所有安全性,请按如下方式定义它们:

<enable.security.start>&lt;!--</enable.security.start>
<enable.security.end>--&gt;</enable.security.end>

Then, you have a single web.xml file with the following:

然后,您就有了一个包含以下内容的 web.xml 文件:

${enable.security.start}
<security-constraint>
  ...
  // all of the XML that you need, in a completely readable format
  ...
</login-config>  
${enable.security.end}

The pom.xml maven-war-plugin has to be configured to use filtering. Mine looks like this:

pom.xml maven-war-plugin 必须配置为使用过滤。我的看起来像这样:

   <configuration>
      <webResources>
        <resource>
          <filtering>true</filtering>
          <directory>src/main/webapp</directory>
          <includes>
            <include>**/web.xml</include>
          </includes>
        </resource>
      </webResources>
      <warSourceDirectory>src/main/webapp</warSourceDirectory>
      <webXml>src/main/webapp/WEB-INF/web.xml</webXml>
      ...

So, basically, when you select the profile to include security, you get two extra CRLF's in your web.xml. When you select the profile to NOT include security, the XML is all still in the web.xml, but it's commented out so it gets ignored. I like this because you don't have to worry about keeping multiple files in sync, yet the XML is still readable (and it's in the web.xml file where people would naturally look for it).

因此,基本上,当您选择包含安全性的配置文件时,您会在 web.xml 中获得两个额外的 CRLF。当您选择不包含安全性的配置文件时,XML 仍然在 web.xml 中,但它已被注释掉,因此会被忽略。我喜欢这样,因为您不必担心保持多个文件同步,而且 XML 仍然可读(而且它在人们自然会查找的 web.xml 文件中)。

回答by Andrzej Jozwik

Comment to Chris Clarkanswer. You can reverse - so in development you do not want to have any constraints (security or jndi, other)

评论克里斯克拉克的回答。您可以反转 - 因此在开发中您不希望有任何限制(安全或 jndi,其他)

<!-- ${enable.security.end}
<security-constraint>
    ...
</security-constraint>


${enable.security.start} -->

So in development you have commented out section. But in production it will be translated to (with maven profile):

所以在开发中你已经注释掉了部分。但在生产中,它将被转换为(使用 Maven 配置文件):

<!-- -->
<security-constraint>
    ...
</security-constraint>


<!-- -->

and commented section will be visible.

和评论部分将是可见的。

回答by dkateros

is there a way to have two web.xml files and select the appropriate one depending on the profile?

Other than the approach suggested by matt b, it is useful to think it the other way around, mainly because in many cases you will have to bundle application server specific configurations that are not covered by the maven plugins (afaik). These may very well have differences between profiles.

除了 matt b 建议的方法之外,换一种方式思考它是有用的,主要是因为在许多情况下,您必须捆绑 maven 插件 (afaik) 未涵盖的应用程序服务器特定配置。这些很可能在配置文件之间存在差异。

Specifically, you can use a parent project that has all the common files between web projects of different profiles. Then child projects can have different web.xml files and the rest id done with profiles and the maven-war-plugin. For example, I have used this layout to achieve unattended builds (other than specifying a profile) for different target environments (development, uat etc.)

具体来说,您可以使用具有不同配置文件的 Web 项目之间的所有公共文件的父项目。然后子项目可以有不同的 web.xml 文件,其余的 id 使用配置文件和maven-war-plugin. 例如,我使用这种布局来实现不同目标环境(开发、uat 等)的无人值守构建(指定配置文件除外)。

WebPc
├── common
│   ├── css
│   ├── images
│   ├── js
│   └── WEB-INF
│   └──├── wsdl
│── pom.xml
│
├── WebPc-DEV
│   ├── pom.xml
│   └── src
│       └── main
│           └── webapp
│               └── WEB-INF
│                   ├── geronimo-web.xml
│                   ├── ibm-web-bnd.xml
│                   ├── ibm-web-ext.xml
│                   └── web.xml
├── WebPc-UAT
│   ├── pom.xml
│   └── src
│       └── main
│           └── webapp
│               └── WEB-INF
│                   ├── geronimo-web.xml
│                   ├── ibm-web-bnd.xml
│                   ├── ibm-web-ext.xml
│                   └── web.xml

The pom of WebPc has the following pom

WebPc的pom有如下pom

<groupId>my.grp</groupId>
<artifactId>WebPc</artifactId>
<packaging>pom</packaging>

<profiles>
    <profile>
        <id>DEV</id>
        <activation>
            <activeByDefault>true</activeByDefault>
        </activation>
        <modules>
            <module>WebPc-DEV</module>
        </modules>
    </profile>
    <profile>
        <id>UAT</id>
        <modules>
            <module>WebPc-UAT</module>
        </modules>
    </profile>
</profiles>

<build>
    <pluginManagement>
        <plugins>

            <!-- copy common resources located on parent
                 project common folder for packaging -->
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-war-plugin</artifactId>
                <version>2.4</version>
                <configuration>
                    <resourceEncoding>${project.build.sourceEncoding}</resourceEncoding>
                    <webResources>
                        <resource>
                            <directory>../common</directory>
                            <excludes>
                                <exclude>WEB-INF/**</exclude>
                            </excludes>
                        </resource>
                        <resource>
                            <directory>../common/WEB-INF</directory>
                            <includes>
                                <include>wsdl/*.wsdl</include>
                                <include>wsdl/*.xsd</include>
                            </includes>
                            <targetPath>WEB-INF</targetPath>
                        </resource>
                    </webResources>
                </configuration>
            </plugin>

        </plugins>
    </pluginManagement>
</build>

And this is the pom for WebPc-DEV

这是 WebPc-DEV 的 pom

<parent>
    <groupId>my.grp</groupId>
    <artifactId>WebPc</artifactId>
    <version>1.0.0-SNAPSHOT</version>
</parent>

<artifactId>WebPc-DEV</artifactId>
<packaging>war</packaging>
<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-war-plugin</artifactId>
        </plugin>
    </plugins>
</build>

回答by Kristof Neirynck

A new configuration was added to maven-war-plugin in version 2.1-alpha-2. Its name is filteringDeploymentDescriptorsand it does exacly what you want.

maven-war-plugin 在 2.1-alpha-2 版本中添加了一个新配置。它的名字是filteringDeploymentDescriptors,它完全符合你的要求。

This works:

这有效:

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-war-plugin</artifactId>
    <version>2.4</version>
    <configuration>
        <filteringDeploymentDescriptors>true</filteringDeploymentDescriptors>
    </configuration>
</plugin>

And this also works:

这也有效:

<properties>
    <maven.war.filteringDeploymentDescriptors>true</maven.war.filteringDeploymentDescriptors>
</properties>

More information is available in the official documentation of filteringDeploymentDescriptors.

更多信息可以在filteringDeploymentDescriptors官方文档中找到

回答by tuckerpm

An improvement to https://stackoverflow.com/a/3298876/2379360

https://stackoverflow.com/a/3298876/2379360的改进

Instead of specifying a custom property, use the default property maven.war.webxml in your different profiles.

不要指定自定义属性,而是在不同的配置文件中使用默认属性 maven.war.webxml。

<profiles>
    <profile>
        <id>profile1</id>
        <properties>
            <maven.war.webxml>path/to/custom/webXml</maven.war.webxml>
        </properties>
    </profile>
</profiles>

Further info can be found at the following link: https://maven.apache.org/plugins-archives/maven-war-plugin-2.4/war-mojo.html#webXml

可以在以下链接中找到更多信息:https: //maven.apache.org/plugins-archives/maven-war-plugin-2.4/war-mojo.html#webXml