モダン JavaScript プログラミングを始めるために知っておきたい技術セット

元々は社内向けとして書いたものですが、転載許可が出たので Qiita 向けに加筆・修正した文章です。

僕は普段~~ペチパー~~バックエンド領域を担当することが多いのですが、フロントエンド領域を含めて社内の技術アップデートを一緒に頑張っていきたい、という思いから書きました。

なんせ~~ペチパー~~バックエンドエンジニアの拙い知識なので一部情報が古かったり間違っているかもしれません。
フロントエンドガチ勢の皆様、間違い等ございましたら温かく指摘して頂ければと思います。

# 前書き

JavaScript は一応書けるけど、将来心配。なんかすごく進化してるって聞くけど、調べてみても訳が分からない。
僕も勉強し始めは同じことを何度も思いました。
そこで、僕の仕事環境を想定し、導入すべきツールを役割ごとに選定してみました。
上から順に読んで、インストールして、使えるようになるとそれなりにモダンなフロントエンドの知識を手に入れられます。

_※この情報は 2019/05/20 付近の情報です。ただでさえ技術の流行り廃りが激しいフロントエンドの世界なので、概要が掴めたらなるべく最新の情報をググってみて下さい。_

# 実行環境: node.js
モダンな JavaScript を使用するためには「__変換__」がつきものです。
複数の .js ファイルを結合する、圧縮する、古いブラウザに対応させる………。
で、この変換をいちいち人間がやっていては日が暮れるので、PHP がデータベースの内容を一瞬で納品書 PDF に組み替えるように、JavaScript も自動でこの「__変換__」を行うプログラムと環境が必要です。

経緯はさておき、この JavaScript を変換するプログラムはなんと、大抵 JavaScript 自身で書かれています。
ただしこの JavaScript が動くのは Chrome や FireFox といった「ブラウザ」ではなく、「[node.js](https://nodejs.org/ja/)」という環境の上です。
この先説明する __webpack__ だとか __Babel__ だとかはこの __node.js__ という環境で動く JavaScript なので、まずは何といってもこれが無いと始められません。

__node.js__ はあなたが使っている OS が Windows であろうが、 Mac であろうが、Linux であろうがインストールできます。まずはこれをインストールしましょう。
なお、そのまま公式ページから直接インストーラを持ってきてもいいですが、今後 __node.js__ のバージョン管理を行いたくなるケースが発生する可能性があるので [nodist](https://github.com/nullivex/nodist) を用いてインストールした方が後々楽かもしれません。

> [初心者向け！3分で理解するNode.jsとは何か?](https://eng-entrance.com/what-is-nodejs)
> [[Node.js] Node.js の導入(Windows編)](https://qiita.com/ksh-fthr/items/fc8b015a066a36a40dc2)


# パッケージマネージャー: npm, Yarn, Bower
__node.js__ がインストールできたら今度は欲しい JavaScript プログラムを自分の PC、またはプロジェクトにインストールするパッケージマネージャーというものを理解しましょう。
荒っぽく言えば、iPhone における __AppStore__ みたいなものでしょうか。

パケージマネージャーの主な役割はプロジェクトに使用するプログラムの定義と、プログラム間の依存解決です。
パッケージマネージャーにプログラムのインストールを任せれば定義ファイルを作ってくれる(npm の場合は package.json)ので、新しいフォルダの中でも同じ package.json を読み込ませれば勝手にインターネットから同じプログラムを取ってきてくれます。
また、あるプログラム A を動かす時には B が必要で、B を動かすときは C と D と Z が必要……みたいな依存関係も、パッケージマネージャーなら自動で芋づる式にインストールしてくれます。

+ 定番、というか node.js をインストールするとき一緒に付いてくるのが [npm](https://www.npmjs.com/) です。
+ 対抗馬は [Yarn](https://yarnpkg.com/ja/) でしょう。一時期は __npm__ より速いと言われていましたが、最近はそんなに差が無いようです。
+ [Bower](https://bower.io/) はかつてフロントエンド系のプログラムをインストールする際に使われていましたが、現在では全ての出番を __npm__ に奪われたと考えて間違いないでしょう。

> [npm入門](https://qiita.com/maitake9116/items/7825d90c09f3e2f87dea)
> [npmから乗り換えてわかった Yarnの4つのメリット](https://ics.media/entry/19384/)


# タスクランナー・モジュールバンドラー: gulp, Grunt, webpack, Parcel
環境とパッケージマネージャーが揃ったら、ようやくですが、ファイルの圧縮・結合等の実益に繋がるツールを用意しましょう。

こういった作業を比較的楽に行ってくれるのが__タスクランナー__と呼ばれるものです。

+ タスクランナーの代表格は [gulp](https://gulpjs.com/) でしょう。
+ [Grunt](https://gruntjs.com/) も有用なタスクランナーでしたが、 __gulp__ にとって代わられた感があります。

しかしこれらの__タスクランナー__は __npm__ に類似の機能である __npm run__ が実装されたのに加え、最近は__モジュールバンドラー__に役目を奪われつつあります。

__モジュールバンドラー__とは、複数のファイルに分割した .js や .css, 各画像ファイルなどを一つの圧縮された .js に結合して出力するというツールです。
__モジュールバンドラー__のメイン機能はまさしくそれなのですが、付随して後述する__コンパイラ__・__トランスパイラ__を挟んだりできるので、事実上のタスクランナーとしても機能しています。

+ __モジュールバンドラー__の代表格かつ、現代のフロントエンドで実質的ディファクトスタンダードと言えるのが [webpack](https://webpack.js.org/) でしょう。
+ ただし、この __webpack__ は設定ファイルを作る学習コストがやや高めなので、設定ファイル要らずのモジュールバンドラーである [Parcel](https://parceljs.org/) も注目を集めているようです。

> [最新版で学ぶwebpack 4入門 JavaScriptのモジュールバンドラ](https://ics.media/entry/12140/)
> [Parcel 入門 ～Parcelはwebpackの代わりになるのか～](https://qiita.com/soarflat/items/3e43368b2d767c730781)


# トランスパイラ・コンパイラ: Babel
JavaScript には __es6__ 等のバージョンが存在するのですが、新しい __es9__ などの書き方で書いた .js ファイルを古いバージョンしか解釈しない IE 11 等で動かすための変換を行うのがこの __トランスパイラ・コンパイラ__ です。

一応、[Prepross](https://prepros.io/) 等の GUI アプリケーションを使えば上記三段階をすっ飛ばしてこの工程に入れるので試してみるのもいいでしょう。
ただ一方で、CLI で動作する環境の方が複雑な設定・自動化が容易だったり、複数人での開発環境を合わせるのに便利だったりするので、実際のプロジェクトではモジュールバンドラーなどに組み込む形が有利かと思われます。

ここに該当するのは [Babel](https://babeljs.io/) という代物で、これを使用する前提の環境が組みあがれば、レガシーな ```var``` や ```function(){}``` ではなく ```let``` や ```const```, ```() => {}``` が使用できるようになるので、是非ともチャレンジしてみて下さい。
```class``` や ```async/await``` が使えるようになると楽しいですよ！

> [【５分でなんとなく理解！】Babel入門](https://qiita.com/Shagamii/items/a87181c22ea777ee2acc)
> [webpack と Babel – React入門](https://www.to-r.net/media/react-tutorial11/)


# Alt JS: CoffeeScript, TypeScript, PureScript
__Babel__ のアプローチが未来の JavaScript を現代のブラウザが解釈できる形へ変換するものだったのに対し、これら Alt JS は別の JavaScript 生成用言語から JavaScript を生み出すというアプローチを取ります。
これはちょうど __Sass__ から __CSS__ を生成する関係と同じです。
これら言語を使えば、他の言語よりもバグへと繋がる罠の多いとされる JavaScript を効率的、または堅牢に開発することができます。

+ [CoffeeScript](https://coffeescript.org/) はかつてこの分野の先駆者でしたが、現在これを新たに採用するプロジェクトはほとんどないでしょう。
  + ただし、そのコンセプトは現在の __TypeScript__ や __PureScript__ へ繋がるものがあります。
+ [TypeScript](https://www.typescriptlang.org/) は __Microsoft__ が開発した静的言語で、動的言語である JavaScript に型の恩恵を与えてくれます。
  + Java 等のように、変数や関数の引数・返り値の型を保証してくれるので潜在的なバグに開発段階で気付くことができるでしょう。
  + さらに JavaScript へのコンパイル時に古いバージョンへと変換する機能も備えているので、実質 __Babel__ の機能を内包しているという利点もあります。
  + 素の JavaScript に比べ、単純な行数は増える傾向にあるため無条件で採用すべきではありませんが、規模の大きなプロジェクトになるほど __TypeScipt__ の価値は大きくなっていくことでしょう。
+ [PureScript](http://www.purescript.org/) は関数型パラダイムで JavaScript 開発を行う言語です。
  + JavaScript は元々プロトタイプベースのオブジェクト指向型プログラミング言語ですが、最近の人気を受けて JavaScript の世界にも関数型プログラミングがやってきました。
  + 変数がそもそも再代入不可能(=イミュータブル)になることでかなり堅牢な開発が可能になるので、関数型言語に興味があるなら試してみてもいいかもしれません。

> [CoffeeScriptは本当に駄目なのか？](https://qiita.com/raccy/items/fae9fc5923d78112d935)
> [TypeScriptで始めるNode.js入門](https://ics.media/entry/4682/)
> [純粋関数型スクリプト言語PureScriptのはじめかた](https://qiita.com/hiruberuto/items/2316b58162cfec150460)

おまけ(筆者が過去に書いた TypeScript の記事です)

> [TypeScript でタワシしか当たらないルーレットを作る](https://qiita.com/Go-Noji/items/5a22a6d1720dba2956f7)
> [ライブラリ無しのTypeScriptでテーブル or リストのドラッグ&ドロップ並び替えをしてみる](https://qiita.com/Go-Noji/items/b1ecfab82e61b7dfcfaf)


# フレームワーク・UIライブラリ: React, Vue.js, Angular, Riot.js
ここまでは _JavaScript をいかに効率的に書くか_という問題を解決するツール群を主に紹介してきましたが、結局 JavaScript でやりたいことはブラウザでのフロントエンド開発でしょう。特に、情報やユーザーの挙動に合わせて__DOM__を変更する、つまりお馴染み [jQuery](https://jquery.com/) でやってきたことですよね？

世間は沢山の誤解で溢れていますが、現代の Web サイトであっても __jQuery__ は有効です。ただしそれは__JavaScript の仕事が少ないうちは。__ という条件付きでです。
例えば Web サイトではなく、最早 Web アプリケーションと呼んだ方が良いサービス、例えば Facebook や Evernote でしょうか。これらサービスはよく観察すると、画面遷移するときにページ全体が更新されるのではなく、一部の DOM のみが書き換えれられています。これがいわゆる SPA(シングルページアプリケーション) です。

> [SPA(Single Page Application)ってなに？](https://digitalidentity.co.jp/blog/creative/about-single-page-application.html)
> [シングルページ参考サイト](http://ad-line.jp/tips/?p=199)

これらページは __jQuery__ でも作成できますが、それには多くの時間と苦労が必要で、出来上がったコードは大方目をそむけたくなるようなスパゲッティコードでしょう。
餅は餅屋、ということで、あなたが作るものが Web サイトではなく Web アプリケーションだと判明したら SPA を設計することに長けたフレームワーク・ライブラリを導入するべきです。

+ [React](https://reactjs.org/) は間違いなくこの領域の代表格です。Facebook が開発したこのUIライブラリをうまく使えば美しい設計の下、アプリケーションを作成することができるでしょう。
  + ただし、慣れないうちは JavaScript の中に html を記述したような __JSX 記法__が気持ち悪いかもしれません。さらに、事実上 __Babel__ を必須としています。
+ [Vue.js](https://jp.vuejs.org/index.html) は __React__ より親しみやすく、コンパクトで LIKE HTML です。
  + __JSX 記法__ や __Babel__ といった新しい概念を勉強しなくても試せます。スケーラビリティも文句なしで、後からアプリケーションの規模が大きくなっても破綻無く再設計可能です。
+ [Angular](https://jp.vuejs.org/index.html) はさらに大規模向けのフレームワークです。
  + 上記二つが足りない機能は他ライブラリで補うのに対し、__Angular__ は最初からほとんどの機能をカバーしています。もっともフレームワークらしいフレームワークでしょう。
  + ただし、ほんの少し試すだけでも __TypeScript__ が必須です。__Angular__ を採用するということはほとんどの場合大規模案件でしょうから、これはメリットでもあります。
+ [Riot.js](https://riot.js.org/ja/) はより素の HTML, CSS, JavaScript に近い構文を持ったフレームワークで、未来の Web 標準と言われる__カスタムタグ__や __Web Components__ を先取りしています。
  + この中で学習コスト・ファイルサイズ共に最小なので、一番とっつきやすく、ミニマムな開発に最適でしょう。
  + ただし現在はそうでなくても、後々規模が大きくなっていくことが予想されるアプリケーションとは相性が悪いかもしれません。

> [Reactを使うとなぜjQueryが要らなくなるのか](https://qiita.com/naruto/items/fdb61bc743395f8d8faf)
> [正真正銘のReactだけの不純物なしでReact入門](https://sbfl.net/blog/2019/02/20/react-only-tutorial/)
> [はじめに — Vue.js](https://jp.vuejs.org/v2/guide/index.html)
> [Angular入門](http://www.tohoho-web.com/ex/angular.html)
> [改めてRiot.jsをその他のFW・ライブラリと比較して客観的に評価した](https://qiita.com/clown0082/items/84e691baa1e4c4f2c61c)


# まとめ
無茶言うな、こんなに覚えられるか、と思うのは当然ですが、世の中のフロントエンジニアは空気を吸うようにこれらを駆使して開発を行っています。

でも、よく思い出してみて下さい。現代文の教科書が一冊あったとして、先生はそれを一朝一夕で全て暗記しろとは言わなかったはずです。
皆さんきっと、一冊を一年かけてじっくり勉強したことでしょう。
Web フロントエンドも一緒です。あなたが必要としている技術をじっくり確実に学んでいきましょう。

もしかしたら学習を終える前にその技術が廃れるかもしれませんが、恐れることはありません。だいたいの新技術の80%は既存技術を弄ったなにかです。学んだことはきっと、次に学ぶことの助けになることでしょう。