バグだらけのWebアプリケーションのクローンをSpring Bootでつくってみました

## 概要

[以前紹介した](http://qiita.com/tamura__246/items/7275c7406706fb0057e8)バグだらけのWebアプリケーション[「EasyBuggy」](https://github.com/k-tamura/easybuggy/blob/master/README.jp.md)のクローンをSpring Bootベースでつくってみました([「EasyBuggy Boot」](https://github.com/k-tamura/easybuggy4sb/blob/master/README.jp.md))。

[ここ](https://github.com/k-tamura/easybuggy4sb/releases/latest)からダウンロードして、以下のコマンドで起動できます。

```bash
java -jar ROOT.war
```

<table width="100%"><tr><td>※起動するにはJava 7以上が必要です。`java -jar ROOT.war --port=9000`とすると9000番ポートで起動します。</td></tr><table>

以下のようにJavaオプションを付加すれば、ログ出力やデバッグ、JMXによる監視ができます(※Java 7用のオプションです)。また、最大メモリ使用量を制限しているので、OutOfMemoryErrorなどの問題がより発生しやすくなります。

```bash
java -Xmx256m -XX:MaxPermSize=64m -XX:MaxDirectMemorySize=90m -XX:+UseSerialGC -Xloggc:logs/gc.log -XX:+PrintHeapAtGC -XX:+PrintGCDetails -XX:+PrintGCDateStamps -XX:+UseGCLogFileRotation -XX:NumberOfGCLogFiles=5 -XX:GCLogFileSize=10M -XX:GCTimeLimit=15 -XX:GCHeapFreeLimit=50 -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=logs/ -XX:ErrorFile=logs/hs_err_pid%p.log -agentlib:jdwp=transport=dt_socket,server=y,address=9009,suspend=n -Dderby.stream.error.file=logs/derby.log -Dderby.infolog.append=true -Dderby.language.logStatementText=true -Dderby.locks.deadlockTrace=true -Dderby.locks.monitor=true -Dderby.storage.rowLocking=true -Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.port=7900 -Dcom.sun.management.jmxremote.ssl=false -Dcom.sun.management.jmxremote.authenticate=false -ea -jar ROOT.war
```

以下のようなメッセージが表示されたら、Webアプリケーションの起動は完了しています。

```
2017-08-11 22:05:25.233  INFO 81661 --- [           main] o.t.e.Easybuggy4sbApplication            : Started Easybuggy4sbApplication in 8.404 seconds (JVM running for 10.723)
```

http://localhost:8080 にアクセスすると、メインページが表示されます。

![Screenshot from 2017-08-27 13-49-32.png](https://qiita-image-store.s3.amazonaws.com/0/43869/4c8d3912-8760-bcc1-884e-4e5a14e6711d.png)

## 上記以外の起動方法

`git clone`して、`mvn clean spring-boot:run`しても起動できます。

```bash
$ git clone https://github.com/k-tamura/easybuggy4sb
$ cd easybuggy4sb
$ mvn clean spring-boot:run
```

<table width="100%"><tr><td>`src/main/resources/application.properties`の`server.port=${port:8080}`の行を`server.port=9000`にとすると9000番ポートで起動します。</td></tr><table>

また、Tomcat 8.5などのJavaコンテナにROOT.warをデプロイしても同様に動作します。

## このアプリの用途

「EasyBuggy」と同様に、様々な障害を再現させて、解析し、理解が深めることが目的です。なぜ同等の機能を持つものをつくったかというと、次のことを知りたかったからです(個人的な興味です)。

 - 最新のフレームワーク(Spring Boot)ベースのアプリにも脆弱性やリソースリークをつくり込むことは簡単にできるか
 - レガシーアプリをSpring Bootに移行する上で必要な作業は何か
 - レガシーアプリをSpring Bootに移行することで可読性は向上するか
 - レガシーアプリと比較して、Spring Bootの開発生産性はどの程度の違うか

これらについては後日、別の記事で公開しようと思います。個人的な興味でつくりましたが、次のような用途にも役立つのではないかと思います。

 - Spring Bootベースのアプリに脆弱性をつくり込んでしまう実装例を把握する
 - レガシーアプリからSpring Bootベースのアプリへ移行する際の参考にする

## 構成の相違点

「EasyBuggy」と「EasyBuggy Boot」の主な構成の相違点は以下の通りです。

|相違点|EasyBuggy|EasyBuggy Boot|
--------|--------|--------
|ベースとなる技術|Servlet 3.0.1|Spring Boot 1.5.6 (Servlet 3.0.1)|
|プレゼンテーション層|未使用 (一部 JSP 2.2 + JSTL 1.2)|Thymeleaf 2.1.5 (一部 JSP 2.3 + JSTL 1.2)|
|DBクライアント/サーバー|JDBC / Derby 10.8.3.0|Spring JDBC 4.3.9 / Derby 10.12.1.1 (Java 7の場合)、または10.13.1.1 (Java 8の場合)|
|LDAPクライアント/サーバー|Apache DS Client API 1.0.0 / Server 1.5.5|Spring LDAP 2.3.1 / unboundid-ldapsdk 3.2.1|
|メール|JavaMail 1.5.1|JavaMail 1.5.1 (Spring Boot Mailで導入されるJavaMail 1.5.6をオーバーライド)|
|開発ツール|無し|Spring Boot Developer Tools 1.5.6|
|Java|Java 6以上をサポート|Java 7以上をサポート|

※この検証をする上で、Spring Securityも導入すべきではあったのですが、残念ながら現時点ではまだできていません...。

## ビルドの方法

以下のコマンドで、実行可能かつデプロイ可能なwarファイルを作成することができます。

```bash
$ mvn clean package
```

## 開発の方法

STS (Spring Tool Suite)を使用して、EasyBuggy Bootのソースコードを参照したり、開発、デバッグする方法についても載せておきます。STSはEclipseベースのIDEで、Springベースのアプリケーションの開発が簡単にできるようにカスタマイズされています。

1. [このページ](https://spring.io/tools/sts/all)からSTSをダウンロードして下さい。
1. [GitHub](https://github.com/k-tamura/easybuggy4sb)からEasyBuggy Bootを`git clone`して下さい。

	```bash
	$ git clone https://github.com/k-tamura/easybuggy4sb
	$ cd easybuggy4sb
	```
2. 以下のコマンドを実行します。このコマンドでSTSでの開発に必要なファイル(`.project`ファイルや`.classpath`ファイル)が作成されます。また、依存するライブラリのソースコードも参照できます。

	```bash
	$ mvn dependency:sources
	$ mvn eclipse:eclipse
	```
3. STSを起動します。
4. パッケージエクスプローラからクローンしたプロジェクトをインポートします。「Existing Maven Projects」を選択して、「Next」をクリックして下さい。
	![Screenshot-Import .png](https://qiita-image-store.s3.amazonaws.com/0/43869/95c523db-eb74-0c5d-facc-b19139358274.png)
	「Root Directory」にクローンしたプロジェクトへのパスを入力し、「Finish」をクリックします。
	![Screenshot-Import Maven Projects .png](https://qiita-image-store.s3.amazonaws.com/0/43869/c9333d6a-7da1-6e4b-c9de-b92c7ed89172.png)
	<br>
	
5. パッケージエクスプローラの`easybuggy4sb`プロジェクトを右クリックし、「Debug As」、「Spring Boot App」と選択すると、デバッグモードでEasyBuggy Bootが起動します。
	![Screenshot-Spring - easybuggy4sb-src-main-java-org-t246osslab-easybuggy4sb-Easybuggy4sbApplication.java - Spring Tool Suite .png](https://qiita-image-store.s3.amazonaws.com/0/43869/0330a834-c415-7e5d-f9df-f3f73149bf4a.png)

ソースコードを修正すると、自動的にリロードされて、修正が反映されることも確認してみて下さい。