(...) Я вполне уверен, что это можно сделать, например, с помощью плагина antrun, но я не знаком с этим.Какой самый простой способ добиться этого?
Вы действительно можете использовать resources:copy-resources
и несколько <execution>
в своем POM (обратите внимание, что resources:copy-resources
не позволяет изменить имя целифайл хотя).
Предположим, у вас есть следующая структура:
$ tree .
.
├── pom.xml
└── src
├── main
│ ├── filters
│ │ ├── filter-node1.properties
│ │ └── filter-node2.properties
│ ├── java
│ └── resources
│ ├── log4j.properties
│ └── another.xml
└── test
└── java
Где log4j.properties
использует заполнители, а файлы filter-nodeN.properties
содержат значения.Например:
# filter-node1.properties
log.location=D:/logs
log.file.postfix=_1
Затем в вашем pom.xml
настройте плагин ресурсов и определите один <execution>
для каждого узла для вызова copy-resources
с определенным выходным каталогом и специальным фильтром для использования:
<project>
...
<build>
<resources>
<!-- this is for "normal" resources processing -->
<resource>
<directory>src/main/resources</directory>
<filtering>true</filtering><!-- you might still want to filter them -->
<excludes>
<!-- we exclude the file from "normal" resource processing -->
<exclude>**/log4j.properties</exclude>
</excludes>
</resource>
</resources>
<plugins>
<plugin>
<artifactId>maven-resources-plugin</artifactId>
<version>2.4.3</version>
<executions>
<execution>
<id>copy-resources-node1</id>
<phase>process-resources</phase>
<goals>
<goal>copy-resources</goal>
</goals>
<configuration>
<outputDirectory>${basedir}/target/node1</outputDirectory>
<resources>
<resource>
<directory>src/main/resources</directory>
<filtering>true</filtering>
<includes>
<include>**/log4j.properties</include>
</includes>
</resource>
</resources>
<filters>
<filter>src/main/filters/filter-node1.properties</filter>
</filters>
</configuration>
</execution>
<execution>
<id>copy-resources-node2</id>
<phase>process-resources</phase>
<goals>
<goal>copy-resources</goal>
</goals>
<configuration>
<outputDirectory>${basedir}/target/node2</outputDirectory>
<resources>
<resource>
<directory>src/main/resources</directory>
<filtering>true</filtering>
<includes>
<include>**/log4j.properties</include>
</includes>
</resource>
</resources>
<filters>
<filter>src/main/filters/filter-node2.properties</filter>
</filters>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
Запуск mvn process-resources
приведет к следующему результату:
$ tree .
.
├── pom.xml
├── src
│ ├── main
│ │ ├── filters
│ │ │ ├── filter-node1.properties
│ │ │ └── filter-node2.properties
│ │ ├── java
│ │ └── resources
│ │ ├── log4j.properties
│ │ └── another.xml
│ └── test
│ └── java
└── target
├── classes
│ └── another.xml
├── node1
│ └── log4j.properties
└── node2
└── log4j.properties
С соответствующими значениями в каждом log4j.properties
.
$ cat target/node1/log4j.properties
log4j.appender.Application.File=D:/logs/application_1.log
log4j.appender.tx_info.File=D:/logs/tx_info_1.log
Этот вид работает, но многословно, и это может быть проблемой, если у вас приличное количество узлов.
Я пытался написать что-то более краткое и удобное в использовании с помощью плагина Maven AntRun, но не смогполучить задачу for
из ant-contrib
для работы под Maven (по неизвестной причине задача for
не распознается), и я отказался от .
Вот альтернатива, использующаяMaven AntRun Плагин.Ничего сложного, без цикла, я просто копирую исходный файл в другое место, меняю его имя на лету и фильтрую содержимое:
<plugin>
<artifactId>maven-antrun-plugin</artifactId>
<version>1.3</version>
<executions>
<execution>
<id>copy-resources-all-nodes</id>
<phase>process-resources</phase>
<configuration>
<tasks>
<copy file="src/main/resources/log4j.properties" toFile="target/antrun/log4j-node1.properties">
<filterset>
<filter token="log.location" value="D:/logs"/>
<filter token="log.file.postfix" value="_1"/>
</filterset>
</copy>
<copy file="src/main/resources/log4j.properties" toFile="target/antrun/log4j-node2.properties">
<filterset>
<filter token="log.location" value="D:/logs"/>
<filter token="log.file.postfix" value="_2"/>
</filterset>
</copy>
</tasks>
</configuration>
<goals>
<goal>run</goal>
</goals>
</execution>
</executions>
</plugin>
Обратите внимание, что Ant по умолчанию использует @
в качестве разделителей длятокен (не удалось заставить его использовать разделители в стиле maven), поэтому log4j.properties
стал:
log4j.appender.Application.File=@log.location@/application@log.file.postfix@.log
log4j.appender.tx_info.File=@log.location@/tx_info@log.file.postfix@.log
Но, поскольку эти значения кажутся специфичными для узла, вы рассматривали возможность использованиявместо системных свойств (что вы можете поместить в сценарии запуска)?Это то, что я уже сделал (с log4j.xml
), оно работает хорошо, и это сильно упростит вещи.