requireとimportの違いを答えられなかったのでまとめてみる

2021-05-14

概要

普段気にすることがなかったモジュールの読み込み、importやらrequireやらとりあえず動くからいいやってなりがちです。

ある時不意に、「requireとimportどっちをつかえばええのん?」って言われたんです。
「そりゃ、、、おま、、importやろ」なんて濁してしまった自分が恥ずかしい。

よって、戒めも含めたモジュール読み込みの違いをまとめてみます。

ESMとCJS

モジュール読み込みの仕様として、まず知っておきたい ESM(ECMAScript Modules) CJS(CommonJS Modules) があります。

それぞれで動作する環境が違います。

import(ESM)

ES6(es2015)で決められたモジュール読み込み仕様になります。
IEを除く、モダンブラウザで使用可能になっています。

モジュール側

挨拶をするクラスを作成してみます。

greeting.js
export class Greeting {
  name = ''
  constructor(name) {
    this.name = name
  }
  greeting() {
    console.log(`hello ${this.#name}!!`)
  }
}

読み込み側

モジュールを読み込んで挨拶してみましょう。

index.js
import { Greeting } from './greeting.js'
const instance = new Greeting('iwt')
instance.greeting()
<!doctype html>
<html lang="ja">
<head>
  <meta charset="UTF-8">
  <meta name="viewport"
        content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>module-test</title>
</head>
<body>
<script src="index.js" type="module"></script>
</body>
</html>

ブラウザを立ち上げると、以下のコンソールが出現しました。

hello iwt!!

ちなみに、node.jsで実行しようとすると、

node index.js
# Cannot use import statement outside a module

と怒られます。

require(CJS)

Node.js環境で動作する書き方になります。
つまりサーバーサイドで動作するということです。

ブラウザ側では動作しません。

モジュール側

先程のクラスをCJS仕様に置き換えます。

greeting.js
class Greeting {
  name = ''
  constructor(name) {
    this.name = name
  }
  greeting() {
    console.log(`hello ${this.name}!!`)
  }
}

module.exports = Greeting

読み込み側

index.js
const { Greeting } = require('./greeting.js')

const instance = new Greeting('iwt')
instance.greeting()

実行

node.jsで実行してみます。

node index.js

# hello iwt!!

無事、メッセージが表示されました。

これも、ブラウザ側で実行しようとすると、

Uncaught ReferenceError: require is not defined

と怒られます。ブラウザ側にrequire関数がないんですね。

環境に依存しない方法

import文とrequire文では動作する環境が違うことがわかりました。
もし、両方利用したい場合はどうすれば良いか。

webpack

を使用します。

webpackを使用することで以下のメリットがあります。

  • importrequire文を解析し、どちらの環境でも使用できるようにしてくれる
  • 外部ファイル(モジュール)と取り込み、一つのファイルとしてまとめてくれる

詳細は省きますが、設定によって使用するモジュールの形態やデッドコードを除く(Tree Shaking)といった便利な機能があります。

結論

  • importはブラウザ側で動作する(IE除く)
  • requireはNode.js側で動作する
  • どちらも安定して使用するならばwebpackを使用してコードをまとめる

思考停止、だめ、ぜったい。

運営について

Natural Tearoomはシステム開発会社フロントエンドエンジニアがんちゃんが運営するメディアです。
フロントエンド技術を中心に発信しています。

· プライバシーポリシー

SNS

© 2021 天然珈琲店