[備忘録] maven-war-plugin で WAR ファイルを作らせない方法

# 1. はじめに

:::note info
***はじめにのはじめに***
この記事は
[How to get Maven to run war:exploded but not war:war - Stack Overflow](https://stackoverflow.com/questions/352612/how-to-get-maven-to-run-warexploded-but-not-warwar)
の内容の一部(pom.xml の定義)を引用させていただいています。
この情報を探し出すのに手間取ったので、メモとしてここに残すことにしました。
:::

「maven-war-plugin を使っているのに WAR ファイルを作らないのって意味があるのだろうか」
という疑問をお持ちになった方もいらっしゃるのではないでしょうか。
その疑問は尤もなことであり、maven-war-plugin を使うと普通は WAR ファイルを作ることになりますし、WAR ファイルを作るために maven-war-plugin を使っているともいえます。

しかしながら、Web アプリの開発では WAR ファイルを必要としない場面が稀にあったりします。たとえば、デプロイ先のサービスが WAR ファイルを受け付けないとか、WAR ファイルでのリリースが運用ルールで禁止されているとか、試作でローカル実行したいだけなんだとか、理由は様々です。

その場合、ビルドでは (WAR ファイルが展開された状態と同等の) Web ディレクトリ構造が出力されるだけでよく、WAR ファイルとその作成処理は不要なものになります [^1]。また、WAR ファイルを作成するとビルド完了までの時間も無駄に長くなるため、この問題をなんとか解消したいと考えました。

# 2. pom.xml の定義

今回は、Maven の最小コマンドで簡潔に処理したい、具体的には **package** コマンド(```mvn package```)を実行するだけで実現したいという願望もありました[^2]。
それを実現したものが、以下の pom.xml の定義になります。
これで Maven のパッケージビルドを行うと、出力先には WAR ファイルは作成されず、その代わりに Web ディレクトリ構造が作成されます。

```xml:pom.xml (該当部分のみ抜粋)
    <build>
        <pluginManagement>
            <plugins>
                <plugin>
                    <groupId>org.apache.maven.plugins</groupId>
                    <artifactId>maven-war-plugin</artifactId>
                    <executions>
                        <execution>
                            <id>default-war</id>
                            <phase>none</phase>
                        </execution>
                        <execution>
                            <id>war-exploded</id>
                            <phase>package</phase>
                            <goals>
                                <goal>exploded</goal>
                            </goals>
                        </execution>
                    </executions>
                </plugin>
            </plugins>
        </pluginManagement>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-war-plugin</artifactId>
                <version>3.3.2</version>
            </plugin>
        </plugins>
    </build>
```

上記を簡単に解説すると、```<pluginManagement>```内で maven-war-plugin に対し、
```
<execution>
    <id>default-war</id>
    <phase>none</phase>
</execution>
```
の定義で、package フェーズに関連付けられているデフォルトの『WAR ファイル作成処理(default-war)』[^3] を実行不可(none)に上書きしています。

さらに、
```
<execution>
    <id>war-exploded</id>
    <phase>package</phase>
    <goals>
        <goal>exploded</goal>
    </goals>
</execution>
```
の定義で、『展開された(exploded) Web ディレクトリ構造の作成処理』を package フェーズに関連付けることで、maven-war-plugin のデフォルトの挙動を置き換えています。

この定義を使って Maven のパッケージビルド(```mvn package```)を実行すると
*[INFO] --- maven-war-plugin:3.3.2:**exploded (war-exploded)** @ myapp ---*
のようなログが出力されることより、置き換え後の ID『war-exploded』の処理が呼び出されていることが分かります。

# 3. おわりに

今回の件はやりたいことは明確だったのですが、どのようなキーワードでそれを探せばよいのか見当がつかず、とても困りました。
自分用の記録として残したものですが、この情報が誰かのお役に立てれば幸いです。

# 4. 参考にさせていただいた情報

How to get Maven to run war:exploded but not war:war - Stack Overflow
https://stackoverflow.com/questions/352612/how-to-get-maven-to-run-warexploded-but-not-warwar

[^1]: WAR ファイルを解凍すると Web ディレクトリ構造を出力することはできますが、WAR ファイル自体が無駄なものなので、この手段は選択肢から外しました。

[^2]: Maven の実行には、フェーズ指定(package)ではなく、ゴール指定(war:exploded)で行う方法もあり、これでも WAR ファイルを作らない条件を満たせます。しかし、ゴール指定での実行では特定のフェーズ(validate etc.)が実行されず、プロジェクト構成によっては不都合が生じる場合があるため、検討対象から外しました。
これについては、たとえば ```mvn validate war:exploded``` とすれば、validate フェーズに続けて war:exploded ゴールを実行できますが、運用をシンプルにする上で（私にとっては）あまり良い方法とは思えませんでした。

[^3]: 通常は Maven のパッケージビルド(```mvn package```)を実行すると
*[INFO] --- maven-war-plugin:3.3.2:war **(default-war)** @ myapp ---*
のようなログが出力されることより、『default-war』が maven-war-plugin でデフォルト実行される処理のIDであることが分かります。