昔やったプロジェクトで(Javaではなかったのですが)サーバサイドでstatic変数が単純に定義されていて(スレッドアンセーフな状態)、複数人がある画面を利用すると、ごくまれに変な挙動になる、みたいな障害がありました。
自分が書いたものではなく、引き継いだコードだったのと、再現性が低いため、原因がstatic変数にあることにたどり着くまでに結構時間がかかった記憶があります(^^;
NetBeansにはマルチスレッドデバッグなる機能があって、これを使うとサーバサイドでキナ臭そうな部分を細かくチェックできるので面白いです。
https://netbeans.org/kb/docs/java/debug-multithreaded_ja.html
Java EEのサーバサイドで、例えばですが、以下のような単純なJSF管理対象を作成して
package jp.co.hoge.multithreadtest;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;
@ManagedBean(name = "threadUnSafe")
@ViewScoped
public class ThreadUnSafe {
private static Object singleton;
public void createObject(){
if(singleton == null){
singleton = new Object();
}
}
}
ビューはしょぼしょぼに
<h:body>
<h:form>
<h:commandButton id="btn" value="インスタンス生成するぜ!"
action="#{threadUnSafe.createObject()}" />
</h:form>
</h:body>
で、実行して、2つのブラウザからアクセスしてみます。
まず1つめのブラウザでポチリ。するとブレークポイントで緑矢印が止まります。
2つめのブラウザでポチリすると、歯車のようなマークがでます。これがマルチスレッドなモードのしるしみたいです。
スレッドを切り替えるには歯車を右クリックして「現在のスレッドを設定」で選びます。
上記の例題でいじわるな感じにやると、片方を進めてnewする所で止めて、もう1つのスレッドにスイッチして進めて同じ所で止めます。
この時点ではどちらのスレッドでもnewするところに。
で、各々実行すると、初めのスレッドが作成したインスタンスを次のスレッドが塗り替えてます。
これはちょうど、以下の@it記事でGofSingleton.javaの部分で黄色文字に書いてある「マルチスレッド環境だと…入り込めてしまう」状態にあたります。
http://www.atmarkit.co.jp/fjava/javatips/075java007.html
実際に自分の目でこういうのを見ると、改めて「あぶなっかしいなぁ」と思う点も出てくるので、気になる部分はこうして確認すると良いのかなと。あとは頭の固い人を具体的に説得するときとか。。。
試しにlockしてみたら、スイッチしても入り込めない状況までみえました。
(synchronizedを通過して抜けると、入れる所までみれました)
管理対象Beanが保持する通常の(staticではない)変数などは、スレッドごとに保持されてる値までスイッチして確認できるので、色々と便利です。
あと、新人さんとかにスレッドの説明を具体的に目で見せながら教えるのにも使えそうな気も(^^;