React.jsをWebstorm上でミニマムでLiveEditする


# 背景
ごちゃごちゃダウンロード・インストールせずにindex.html, style.css, script.jsくらいで新しいライブラリの味見をしたかった。

久しぶりにWebの技術の勉強を始め、ブランクの間に出てきたJSライブラリを触ってみようとした。PlunkerなどのWebエディタでも良いのだが、キーバインドは勉強でも本番と同じものを使いたいのでJetbrainsのエディタを使いたい。LiveEditは（昔自分がやっていたような）gruntとかgulpを導入してnodeパッケージを管理してwatchするリソースをTaskRunnerで定義してgrunt/gulp serveでローカルサーバを立ち上げるというやり方があるが、これだと特定のライブラリの勉強をするのに本質的でないファイルをいくつも導入しないといけない。
WebstormのLiveedit機能を使うことで、ほぼindex.html, style.css, script.jsのみの最小構成で実験できるようにする。これによって勉強したいライブラリのコードにフォーカスできる。

# やってみたら
いまいち思った通り動かなかったり、そもそも新しいプロジェクトを作ろうとすると相変わらず巨大なBoilerplateからスタートすることになって最小構成にならないとかだったのでメモを残しておく。
なおタイトルにはWebStormと書いたがもちろんIntelliJやPHPStormやRubyMineなどWebStormの上位版なら同じ手順でできるはず（というか僕もRubyMineを使っています）

# 環境
今回は僕がWebやってた頃にはなかったReact.jsを勉強するために構築します。
WebStormのバージョンは現時点で最新の2016.1、OSはUbuntu14.04です（他でもやり方は変わらないと思いますが。）

# 手順
webstormのインストールは終わっていてパスが通っているとします。
またNodeJSのインストールは済んでいるとします。
まずディレクトリと元ファイルを作成します。

```
$ mkdir -p <project-name>/src
$ cd <project-name>
$ touch index.html style.css src/script.js
```

WebStormを起動します。
ここで、いまプロジェクトフォルダにいるからといって

```
$ webstorm.sh .
```

とすると、上で作ったファイルがWebStorm的にはProjectのファイルじゃないとみなしてしまうので、単純に以下のように引数なしで起動します。

```
$ webstorm.sh
```

起動時のダイアログでOpen→先ほど作ったディレクトリを選択。
WebStormのメニューから、File->Settings->Plugins->Browse repositoriesと進み、検索窓にLiveeditと入力してLiveeditのインストールを行います。
続いてChromeにJetbrainsのIDEサポートのAddOnを↓のリンクから入れます。
https://chrome.google.com/webstore/detail/jetbrains-ide-support/hmhgeddbohgjknpmjagkdomcpobmllji

次にRun->EditConfigurationsを選択し表示されたダイアログの左上の+マークを選択しJavaScript Debugの設定を追加。
URLに```http://localhost:63342/<project-name>/index.html```と指定。
![Screenshot from 2016-05-23 22:22:31.png](https://qiita-image-store.s3.amazonaws.com/0/47902/4528d129-834f-c4da-4ded-dab190c68390.png "Screenshot from 2016-05-23 22:22:31.png")

これで基本的に設定は終わりなのですが、今回はReact.jsでjsxを使いたいのでPrecompileの設定が必要です。（他にもsassの機能を使いたいときとかcoffeeのライブラリを使いたい時とか）
globalにreact-toolsをインストールします。

```
$ npm install -g react-tools
```

jsxをwatch&precompileするため、以下をプロジェクトルート（```<project-name>```）で実行します。

```
$ jsx --watch src build
```

これでbuildディレクトリ以下にjsxからコンパイルされたjsが生成されます。

IDEがReactを理解できるように、https://facebook.github.io/react/ からreactをダウンロードして```<project-name>/lib```にでもコピーしておきます。（例えば現時点での最新のreact-15.1.0.jsとreact-dom-15.1.0.js）
あとはindex.htmlでコンパイル済みのjs(build/script.js)をロードし、

```index.html
<!DOCTYPE html>
<html>

<head>
    <link rel="stylesheet" href="style.css">
    <script src="lib/react-15.1.0.js"></script>
    <script src="lib/react-dom-15.1.0.js"></script>
</head>

<body>
    <div id="root">tests</div>
    <script src="build/script.js"></script>
</body>

</html>
```

適当にReact.jsのコードを書いて、

```src/script.js
var Button = React.createClass({
    render: function() {
        return (
            <button>Go</button>
        )
    }
});

ReactDOM.render(<Button />, document.getElementById("root"));
```

以上で準備完了。
WebStormのメニューからRun->Debugを実行すると以下のようにChromeが立ち上がり上記のコードの通りdivエレメントがButtonに変更されています。


![Screenshot from 2016-05-23 22:59:25.png](https://qiita-image-store.s3.amazonaws.com/0/47902/0a4eca89-86f9-7d45-0962-1b253c4b7127.png "Screenshot from 2016-05-23 22:59:25.png")

# 注意点1
htmlファイルはこれだけでLiveリロードされるのですが、css、jsはWebStorm上でautoリロードの設定がさらに必要かも知れません。
この場合、File->Settings->Build, Execution, Deployment->LiveEditの”Auto in”にチェックをいれ、Restart if hotswap failsにもチェックを入れておくとcss/jsもLiveリロードされます。

![Screenshot from 2016-05-23 23:02:19.png](https://qiita-image-store.s3.amazonaws.com/0/47902/174c8124-d474-363d-7e07-4d3b1a78f55a.png "Screenshot from 2016-05-23 23:02:19.png")

さらに、jsについては実装した内容が反映されていない（ように思う）ことがあります。これは、jsの変更時にjs自体は再ロードされているがjsが再ロードされただけだと動作上は反映されない（それで正しい）からです。
例えば```window.onload```内で新たにイベントリスナを登録する実装を追加した場合、jsは再ロードされるけれど```window.onload```は（htmlの再ロードはやっていないので）発生しません。なのでイベントの登録のコードを追加したのにLiveEditで反映されていないように見えるのです。一方で既に登録済みのイベントリスナの振る舞いを変更した場合、そのイベント発生時に振る舞いの変更は反映されます。

* 例:
以下のoriginal1.jsからmodified.jsに修正した場合当該エレメントをクリックしてもなにも起きないがorininal2.jsがロードされていてイベントリスナの登録（テキストを"original"にする）が終わっている状態からmodified.jsに修正した時にはクリック時にテキストの内容が"clicked!"に想定通りに変わる。

```orginal1.js
window.onload = function () {
    var elem = document.getElementById("experiment");
};
```
```original2.js
window.onload = function () {
    var elem = document.getElementById("experiment");
    elem.onclick = function() {
        this.textContent = "original"
    };
};
```
```modified.js
window.onload = function () {
    var elem = document.getElementById("experiment");
    elem.onclick = function() {
        this.textContent = "clicked!"
    };
};
```

# 注意点2
途中でwatchしているファイル数が多すぎるよ的なメッセージがでたり、コンソールで"ENOSPC"なんてエラーが発生している場合、inotifyの監視対象数上限を増やすと良いです。Ubuntuだとこの値はデフォルトで8192で、Web開発やったりDropbox使ったりしていると割と簡単に上限に達してしまいます。

```
$ sudo vim /etc/sysctl.conf
# 末尾にこの指定を追加 → fs.inotify.max_user_watches=530000
$ sudo sysctl -p
```

余談ですが、なんでもいいから十分巨大な数を指定しないといけないときにはフリーザへのリスペクトを込めて、53万を入れるようにしています。

# 所感
WebアプリをBoilerplateやyeoman generatorを使って簡単に作る方法はあるけれど、そういうやつはしょっぱなにわっさーテンプレートファイルを落としてくるしたくさんのnode module、bower componentなんかをインストールしないといけないので大掛かりすぎる。しかもあとから見返した時にどこがポイントだったのかわかりづらい。今回のような必要最小限の構成から簡単にスタートする方法って需要ないのかなあ。