LoginSignup
2
1

More than 3 years have passed since last update.

【JavaScript】ESModulesの使い方 import・export

Posted at

はじめに

VueCLIを勉強中しているのですが、モジュールの使い方について、しっかりとした理解が必要だと気づいたので、今回はESModeulsの使い方についてまとめておきます。

大前提としてモジュール管理とは何かという話ですが、
「ソースコードを分割して、メンテナンスをし易くするための仕組み」のことです。

1つのファイルに全ての処理を記述すると、当然ですがコードは肥大化してきますし、メンテナンスも大変です。

その為、機能ごとに別ファイル(モジュール)に分割して必要に応じて読み込むことで、より効率なコードになるわけです。

ESModulesとは、ECMAScriptの規格に基づいたモジュール管理の仕組みで、主にブラウザ上で動作します。importexportというキーワードを使って、モジュールの読み込みや出力を行います。

他にもNode.jsで動作する、Common.jsというモジュール管理の仕組みもあります。
こちらはrequireやexportsというキーワードを使い、モジュールの読み込みを行います。(しっかりと試せていませんが)

モジュール管理する方法は、実行環境などによって異なる種類があるということですね。

ESModulesを試す

では、実際にESModulesのモジュール管理のやり方を試していきましょう。
まず、moduleAとmoduleBという名前のjsファイルと、ブラウザで結果を確認するのでhtmlを用意します。

moduleB.js
let num = 10;

function methodA(){
    console.log("This number : " + num);
}

//num変数と、methodAメソッドをエクスポート。
export {num,methodA};
moduleA.js

//インポート
import {num ,methodA} from "./moduleB.js";

console.log(num); // 10

methodA(); // This number : 10
index.html
<body>
    //typeをmoduleと指定する。
    <script type="module" src="moduleA.js"></script>
</body>

まず最初に、モジュール管理を行う場合、スクリプト読み込み時にtype="module"を指定する必要があります。この指定が無いとESmodulesは使えません。

moduleBでは、オブジェクトリテラルにexportしたい変数や関数を指定します。

moduleAでは、importの後に、moduleBでの指定と同じ様に{num ,methodA}とします。ここで、export時と異なる命名にすると、エラーになるので注意しましょう。

そして、fromの後に、どのファイルからのimportをするかを指定します。ちなみにファイル指定では、../などパス指定をする必要があります。 from 'moduleB.js'のように、ファイル名だけではエラーとなります。また、拡張子の.jsも省略できないのでご注意を

こうすることで、moduleAでmoduleBの変数や関数を扱うことができるようになりました!

またexportとimportのモジュール名は同名にする必要があると言いましたが、asを使うことで別名の変数や、関数に変更することも可能です。

moduleA.js
//asで名前変更
import {num as n ,methodA as A} from "./moduleB.js";

console.log(n); // 10

A(); // This number : 10

モジュール管理の基本的な流れは、こんな感じですが、

実はexportの方法は2種類あります。上のやり方は名前付きexportとなります。

次は、もう1つのexport defaultのやり方を見ていきましょう。

export default

moduleB.js
class Person{
    constructor(val){
        this.val = val;
    }

    print(){
        console.log(this.val * 2);
    }
}

//デフォルトエクスポート
export default Person;
moduleA.js
import Person from "./moduleB.js";

const person = new Person(10);

console.log(person.val); //10

person.print(); // 20

今回はmoduleBでクラスを作り、それをmoduleAでimportします。

名前付きexportとの違いは、出力できるモジュールの数です。

名前付きexportでは、先ほどの例の様に、変数や関数など複数のモジュールをエクスポートできますが、

export defaultの場合、エクスポートできるモジュールの数は1つとなります。

なので例えば、下記の様に複数のクラスをexport defaultすることはできません。

moduleB.js
class Person{
    constructor(val){
        this.val = val;
    }
    print(){
        console.log(this.val * 2);
    }
}

class Child{
    constructor(val){
        this.val = val;
    }
    print(){
        console.log(this.val * 2);
    }
}
//複数エクスポートはできない。エラー
export default {Person,Child}; //SyntaxError:

また、defaultを使った場合、importのモジュール名はasを使うことなく変更することができます。

moduleA.js
//例えばモジュール名をPに変更
import P from "./moduleB.js";

//Pでインスタンス化
const person = new P(10);

console.log(person.val);

person.print();

ちなみに、defaultは1つのスクリプトファイルに対して、1つという決まりがありますが、

名前付きexportは複数記述が可能です。

なので、例えば以下の様に複数に分けてexportをすることもできます。

moduleB.js
class Person{
    constructor(val){
        this.val = val;
    }
    print(){
        console.log(this.val * 2);
    }
}

let num = 300;

function methodA(){
    console.log("This number : " + num);
}

function methodB(){
    console.log("Hello World");
}

export default Person;
//exportを複数回使用
export  {num,methodA};
export  {methodB};

importでも、分割して読み込むことができます。
まとめて読み込みたい場合は、下の様にまとめて読み込むことも可能です。

moduleA.js
//分けることもできる。必要に応じて読み込み。
import P from "./moduleB.js";
import {num} from "./moduleB.js";
import {methodA} from "./moduleB.js";
import {methodB} from "./moduleB.js";


//まとめてimportもできる。
import P,{num, methodA,methodB} from "./moduleB.js";

以上、ESmodulesでのモジュール管理についてでした。ありがとうございました。

参考

https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Statements/export
https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Statements/import

2
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
1