JavaScript
es2015
ESModules

予習のために調べたことをまとめました。

勘違いや誤りがあるかもしれませんので、修正・指摘歓迎いたします :innocent:


ESModules とは


  • JavaScript から別の JavaScript を読み込む為の仕組み

  • いままで CommonJS で実現していたことをJSの標準仕様にしたという理解

  • 仕様を決めるのに苦労した様子


    • ESModules と CommonJS の相互運用問題

    • ESModules の判定方法をどうするか問題



  • まだ production 環境などに採用するのは時期尚早かも?


対応状況


  • Node.js は v8.5 から実験的に対応されている



    • --experimental-modules フラグを付与する



  • 主要ブラウザは概ね対応済み




利用例


Browser

<script type="module" src="index.mjs">



  • type="module" を指定する

  • 認証も必要なら crossorigin="use-credentials" を付与


Node

node --experimental-modules index.mjs


  • 拡張子を .mjs にする


  • --experimental-modules フラグを付与する


実装例

import hello from './hello'

export default () => {
hello('world')
}


  • ファイルの拡張子は .mjs

  • import の際に .mjs は省略して良い (.mjs -> .js の順で探索される為)

  • 既に ES2015 (with Babel) で実装しているなら慣れ親しんでいるかも


require はできない

const hoge = require('./hoge')


  • CommonJSとは記法が異なる


named import はできない

import { piyo } from './hoge'


  • Babel だとトランスパイルできてしまうので注意

import hoge from './hoge'

const { piyo } = hoge


  • これなら書ける


使えなくなるグローバル変数がある


  • __filename

  • __dirname

  • require

  • module

  • exports

  • arguments


Tips


__dirname を代替する

const __dirname = path.dirname(new URL(import.meta.url).pathname)


エディタで import.meta が syntax error になる場合


何が嬉しいのか


  • webpack などでバンドルしなくていい(遠い将来に)

  • babel などでトランスパイルしなくていい(遠い将来に)

  • HTTP/2 で各モジュールを並列配信できれば速くできるかも?


参考