まえがき
最近社内でLT大会がありまして、Angular2について発表したのですが(正式リリース直前でしたが)、結構内容的には、React vs Angular2みたいな内容になってたので、『(私が)ReactとAngular2の選択で迷ったときに考えたいこと』としてちょっと記事にしてみました。
※1 この記事はあくまで両者を触ってみた『個人的な感想』になりますのであしからず。
※2 そして、この記事は2016-09-18の時点での内容になります。
Reactはライブラリ、Angularはフレームワーク
Reactが出始めた頃にはよく比較されることの多かったAngularですが、それは両者が似たような時期に盛り上がってきており、それでいてDOM周りの問題解決で謳っている機能がそれぞれちょっとずつちがっていたからかなと思っています。(それぞれDOMの構築とデータバインディングについての機能を持ち、それぞれがちょっとずつ違っていたので、良い点悪い点が比較されていたように思います。)
何度も沢山の記事で言われていることですが、Reactはあくまでライブラリ、Angularはフレームワークなので解決しようとしている問題そのものが違います。まずはそれぞれにフォーカスをあてて理解を深めていきましょう。
Reactが解決しようとしたもの
Reactが出始めたときにはReactは下記のような言葉を謳い文句にしていました。
(現在はReact本体と取り巻く環境それぞれがちょっとずつ変化してきており、これらの文言はReactのDocumentのサイトには書いてありません。)
- JUST THE UI
- VIRTUAL DOM
- DATA FLOW
JUST THE UI
JUST THE UIについてはReactはあくまでViewライブラリだよと言っているものです。ロジックの部分とViewの部分は分けようという方針です。
『結局私達がjQueryでやりたかったことはDOMの操作とイベントのバインディングだったんじゃない?(それ部分的にReact使うだけでもよくない?)』と考えるきっかけにもなったかもしれません。
(昨今のjQueryいらなくね?の流れ。参考:http://qiita.com/tatesuke/items/b9548dd484b01b139b74 )
jQuery自体はViewとロジックの記述を分けるような思想を持っていないため、こういった意見が出てくるのも頷けるかと思います。
VIRTUAL DOM
そして、DOMの書き換えについて処理速度的にネックにならないことを謳っています
(=それでいてjQueryによるDOM操作よりも早いぜ!)。
DATA FLOW
DATA FLOWについては各人がそれぞれ独自に実装していた、イベント発火→データ書き換え→DOM書き換えの処理部分をReactの片方向データバインディングにのせて作ろうぜという考え方です。
昨今ではここらへんはReduxを代表するFluxの設計思想にうけつがれています。
(React本体じゃなくて周辺ライブラリに役割が移ってきている)
上記のようなJS開発における問題をあくまで『シンプルに』解決しようとしたので、Reactは今でもライブラリというサイズ感で提供されているのかなと思っています[要出典]。
(ちょっと古い指針を出してしまったのですが、その思想の根っこは基本的に今でも変わっていないように思います。)
Learn Once, Write Anywhere
最近では Learn Once, Write Anywhere (ReactNativeに代表されるように、Reactを覚えればほかのアプリケーションも作れるようになるぜ)ということも掲げています。もうReactは設計概念になろうとしているのかなと思ったりもしたり…(個人的な感想)。
情報量はReactのほうがAngularよりも遥かに多く、技術としても安定してきている感じがしますよね。
(Angularは2の正式版が出てまだ間もないし…リリース直前で入ったNgModuleのような大きめな変更はもうしばらく無いとは思いますが…
NgModule導入についてわかりやすいブログ様:https://ng2-info.github.io/2016/07/preparing-for-ngmodule/ )。
Angularが解決しようとしたもの
対してAngularはJSフレームワークという位置づけでした。
(ちなみにAngular2からはTypeScriptでも書けるようになったので『AngularJS2』ではなく『Angular2』と書く方針のようです)
Reactと同じようにDOM周辺の問題解決を目指したもの
AngularもDOM周辺の問題解決を目指したのですが、そちらに関してはReactという強力なライブラリがあったので、これがReactとよく比較される要因になったように思います(悪い意味ではなく)。
Angular2ではReactと同じように片方向データバインディングになるという、Reactの良いところを取り入れる形になっています。
フレームワーク思想
フレームワークとして『Angularである程度完結する』ところを目指しているのがReactと大きく異なる点かなと思います。
これはReactと比べると顕著なのですが、昨今Reactでは周辺状況が複雑化しており、React本体だけで終わることがなくなってきていると思います。
たいていReactの取り巻く環境は下記のようになってきているのかなと思っています。
- React (本体)
- Redux (Fluxアーキテクチャ構築)
- ReactRouter (ルーティング)
- JSX、ES2015( + Babelやそのほかコーディング補助ツールなど)
対してAngular2の基本形は
- Angular
- TypeScript( + TypeScript周辺ツール)
となるのかと思います。 Reactの周辺ライブラリはデファクトスタンダードになりつつありますが、もしかしたらプロダクションによって違ったライブラリ構成が変わる可能性もあるかも?
そういう意味でも個人的にはチーム開発のところで設計思想やコーディングルール、実際の実装方法に ついて全員が同じ認識を持ちやすいところはやはりフレームワークの良い点であるように思います。
(フレームワークがもたらすメリットについては他に優秀な記事が沢山あると思うので、気になる人はそちらでm(_ _)m)
Angular CLI
また、フレームワークとして自動化にも取り組んでおり、最近のフレームワークで多くなってきたCLIツールも用意されてきています。(Angular2から)
https://cli.angular.io/ (本家サイト)
https://github.com/angular/angular-cli (Readmeというか、マニュアル)
今から始める人には嬉しい初期構築をCLIで実行して構築できる機能もあります。
$ ng new [作成するアプリケーション名]
CLIツールと言えば、ファイル作成するときに命名ルールが自動化されたり、設置ディレクトリに勝手に配置してくれたりと、コーディングのルールのところを自動化で支えてくれるメリットが有ると思いますが、Angular-CLIはまだまだ機能としては貧弱です。
ですが今後の発展次第で強力な自動化ツールとして、ほかのJS系フレームワークとは差がついていくのではと思っています。
その他書きたいことをつらつらと
Reactをつかった最近のサービス設計について
本気でReactを使いこなせているところは結構Reactのレバレッジが効いてる感を感じたりします。
先日Reactの勉強会でヒカラボでReact導入実例の講演(https://atnd.org/events/79320 )を見ていたのですが、
- フロントエンド:React
- サーバーサイドレンダリング:Node.js + React
- アプリ(iOS, Android):ReactNative
という構成になっており、ある程度のソースコードの共通化ができていて、これぞReactと言った感じでした。
(ただし、ReactNativeとその他で若干違って共通化が難しい部分もあるとも言っていました)
ちょっとここまで私も構築したこと無いのですが、新規メディアでは選択価値がものすごくありそうです。
Reactはサービスによって取捨選択することができる
最初からReduxやらReactRouterやらを揃えなくても、今の自分のサービスに合わせて使うライブラリを変えていけます。
必要になってから入れる、新しいReactライブラリがでたら試す事ができる。ココらへんが楽しいと思える人は是非Reactを選ぶといいと思います。逆にココらへんが億劫な人はReactを選択した後のキャッチアップとかで苦労するかもしれません…。
デザイナーとの協業について
これは私自身がプロジェクトで使っていて思ったことでもあり、上記のヒカラボの勉強会でも出てきた話題なのですが、Reactだとデザイナーと協業しづらいなと思うことがあります。理由としては、
- コンポーネントの設計がデザイナーに共有されづらく、デザイナーが触りづらいこと
- HTMLの大多数をJSファイルに書く点(それをJSXで)
などがあげられます。
※ ReactのチュートリアルのView部分
// tutorial1.js
var CommentBox = React.createClass({
render: function() {
return (
<div className="commentBox">
Hello, world! I am a CommentBox.
</div>
);
}
});
ReactDOM.render(
<CommentBox />,
document.getElementById('content')
);
Angular2では、ViewのテンプレートはHTMLファイルになり、通常のHTMLの記述にAngularの記述が属性として入ってくる形になります(ng◯◯の形)ので、デザイナーにとっても比較的敷居は低いのかなと思っています。
※ Angular2のチュートリアルのView部分
<h3>Top Heroes</h3>
<div class="grid grid-pad">
<div *ngFor="let hero of heroes" (click)="gotoDetail(hero)" class="col-1-4">
<div class="module hero">
<h4>{{hero.name}}</h4>
</div>
</div>
</div>
<hero-search></hero-search>
Angular2のTypeScriptについて
Angular2はTypeScript推しなんですよね。TypeScriptは最終的にはJSに変換されてからWebでは使われるのですが、要はES6の仕様を取り込みつつ独自のエッセンスも入ったAltJSになります。
TypeScriptという名の通り、型がありますので、片方向データバインディングのデータ書き換えのところで、そこは旨味があるなーと思ったりしました。
基本的にはES2015とか触る人ならそんなに身構えなくても良いかなと言う印象(※個人的な感想です)。
Angular-CLIのお陰で初期構築は
$ ng new [作成するアプリケーション名]
で、TypeScriptの実行環境からビルトインサーバーまで用意してくれますし。
まとめ
なにがいいたかったかというと上記のような現状を把握した上で、『今、自分が置かれている環境でどっちがメリットがあるか』を考えればいいと思います。
どっちが優れているかではなく、何を解決しようとしていて、それはチームにどうもたらすかで選択するものが見えてくるのではないでしょうか。