モダンJavaScript(ES6)で書いたコードがIEで動かなかったので対応ポイントをメモ

ES6で書いていたJavaScriptのコードがIE(※)で動かなかったので、その時に対応した内容のメモです。

IEのバージョンは9以上を想定してます。IE8、あるいはそれ以前となるとさらに面倒さが増すので。

各ブラウザの対応状況を知る

各ブラウザの対応状況を調べるには、以下のサイトが便利でした。

ECMAScript 6 compatibility table

「Show obsolete platforms」にチェックを入れると、サポート切れの古いブラウザについても状況を確認することができます。
なお、IE9以下は、ECMAScriptとして「6」ではなく「5」を選んでおかないと表示されません。ES6はIE10でも絶望的なのに、それより古いバージョンが対応してるわけないですもんね。。

Chromeが良くも悪くも手厚くサポートしているので、普段の動作確認をChromeでのみ行うのはリスクだなと実感。

前提条件

ES6のコードはBabelでトランスパイルして使っていました。 詳しく言うと、Babelはwebpackのloaderを使っており、各バージョンは以下の通りです。

  • babel-core (^6.5.2)
  • babel-loader (^6.2.3)
  • babel-preset-es2015 (^6.5.0)

とはいえ、今回の対応箇所は、webpack関係なく通用するものだと思います。

実際にやったこと

そもそもES6の新しい仕様をフルに使って書いていたわけではないため、実はそこまで手間はかかりませんでした。

Promiseを置き換え

原因)IEではネイティブでPromiseがサポートされていません。

対策)代替ライブラリとしてbluebirdを利用しました。

今回、webpackでビルドしていたため、webpack.ProvidePlugin を使うことで、既存のコードに手を加えることなく Promise をすべて bluebird を使うようにひねることができます。

webpack.config.js に以下を追加してあげればOKです。

  plugins: [
    new webpack.ProvidePlugin({  
      "Promise": "bluebird"  
    })
  ] 

Object.assign を置き換え

原因)Object.assign はオブジェクト同士をマージするメソッドですが、これもIEでは使えません。

対策)代替ライブラリとしてobject-assignを利用しました。

Object.assign を使ったコードをすべて置き換えて対応しました。

Object.assign(foo, bar);objectAssign(foo, bar);

console.log を置き換え

原因)IE9以前では、開発者ツールを起動していない場合、consoleがundefinedになります。

対策)代替ライブラリとしてConsole.log wrapperを使いました。

こちらも前述の Promise のように、単なる log メソッドとして呼び出せるようにしました。

webpack.config.js

  plugins: [
    new webpack.ProvidePlugin({  
      "Promise": "bluebird",
      "log": "consolelog"
    })
  ] 

を追加し、 console.log を使っている箇所を log に置き換えて対応しました。

ちなみに、consoleが undefined だったら自作のオレオレconsoleに差し替える、みたいな方法でももちろん可能なのですが、雑に作ってしまうと、開発者コンソールで見た時のログ出力行が、console.log を呼び出した行ではなく、全てオレオレconsoleの行になってしまう、みたいな残念なことになってしまうので気をつける必要があるかと思います。