Kapan saya harus menggunakan kurung kurawal untuk impor ES6?

766

Tampaknya sudah jelas, tapi saya agak bingung tentang kapan harus menggunakan kurung kurawal untuk mengimpor satu modul di ES6. Misalnya, dalam proyek React-Native yang saya kerjakan, saya memiliki file berikut dan isinya:

initialState.js
var initialState = {
    todo: {
        todos: [
            {id: 1, task: 'Finish Coding', completed: false},
            {id: 2, task: 'Do Laundry', completed: false},
            {id: 2, task: 'Shopping Groceries', completed: false},
        ]
    }
};

export default initialState;

Di TodoReducer.js, saya harus mengimpornya tanpa kurung kurawal:

import initialState from './todoInitialState';

Jika saya melampirkan initialStatekurung kurawal, saya mendapatkan kesalahan berikut untuk baris kode berikut:

Tidak dapat membaca todo properti dari undefined

TodoReducer.js:
export default function todos(state = initialState.todo, action) {
// ...
}

Kesalahan serupa juga terjadi pada komponen saya dengan kurung kurawal. Saya bertanya-tanya kapan saya harus menggunakan kurung kurawal untuk impor tunggal, karena jelas, ketika mengimpor beberapa komponen / modul, Anda harus melampirkannya dalam kurung kurawal, yang saya tahu.

Edit:

Posting SO di sini tidak menjawab pertanyaan saya, sebaliknya saya bertanya kapan saya harus atau tidak harus menggunakan kurung kurawal untuk mengimpor satu modul, atau saya tidak boleh menggunakan kurung kurawal untuk mengimpor satu modul di ES6 (ini rupanya bukan case, karena saya telah melihat impor tunggal dengan kawat gigi keriting diperlukan)

TonyGW
sumber
1
tidak, ini berbeda. terima kasih
TonyGW

Jawaban:

2268

Ini adalah impor default :

// B.js
import A from './A'

Ini hanya berfungsi jika Amemiliki ekspor default :

// A.js
export default 42

Dalam hal ini, apa pun nama yang Anda tetapkan saat mengimpor:

// B.js
import A from './A'
import MyA from './A'
import Something from './A'

Karena akan selalu menyelesaikan apa pun adalah ekspor bawaan dari A.


Ini adalah impor bernama bernamaA :

import { A } from './A'

Ini hanya berfungsi jika Aberisi ekspor bernama bernamaA :

export const A = 42

Dalam hal ini nama penting karena Anda mengimpor hal tertentu dengan nama ekspornya :

// B.js
import { A } from './A'
import { myA } from './A' // Doesn't work!
import { Something } from './A' // Doesn't work!

Untuk membuatnya bekerja, Anda akan menambahkan ekspor bernama yang sesuai ke A:

// A.js
export const A = 42
export const myA = 43
export const Something = 44

Modul hanya dapat memiliki satu ekspor standar , tetapi sebanyak yang disebut ekspor yang Anda inginkan (nol, satu, dua, atau banyak). Anda dapat mengimpor semuanya bersama-sama:

// B.js
import A, { myA, Something } from './A'

Di sini, kami mengimpor ekspor default sebagai A, dan masing-masing bernama ekspor yang disebut myAdan Something.

// A.js
export default 42
export const myA = 43
export const Something = 44

Kami juga dapat menetapkan mereka semua nama yang berbeda saat mengimpor:

// B.js
import X, { myA as myX, Something as XSomething } from './A'

Ekspor standar cenderung digunakan untuk apa pun yang biasanya Anda harapkan dari modul. Ekspor yang disebutkan cenderung digunakan untuk utilitas yang mungkin berguna, tetapi tidak selalu diperlukan. Namun terserah Anda untuk memilih cara mengekspor barang: misalnya, modul mungkin tidak memiliki ekspor default sama sekali.

Ini adalah panduan yang bagus untuk modul ES, menjelaskan perbedaan antara ekspor standar dan bernama.

Dan Abramov
sumber
4
Apakah ada kejatuhan memiliki modul yang memiliki ekspor individual export const myA = 43; export const Something = 44;dan juga export default { myA, Something }? Jadi ketika Anda mengimpor, Anda dapat melakukan import A from './A';semuanya di dalam modul, atau import { Something } from './A';Anda hanya akan mendapatkan sebagian dari modul
Michael
12
Ini baik-baik saja, tapi sudah ada sintaks untuk meraih semua ekspor bernama menjadi satu objek: import * as AllTheThings.
Dan Abramov
82
Jelas dijelaskan! Saya berharap saya dapat menggandakan suara jawaban ini.
Willa
7
bagaimana dengan ini- import 'firebase/storage';atau import 'rxjs/add/operator/map';. Apa yang sebenarnya dilakukan?
kyw
9
@kyw: Ini mengeksekusi modul tetapi mengabaikan nilai yang diekspor. Berguna untuk efek samping.
Dan Abramov
84

Saya akan mengatakan ada juga notasi berbintang untuk importkata kunci ES6 yang layak disebutkan.

masukkan deskripsi gambar di sini

Jika Anda mencoba konsol Mix log:

import * as Mix from "./A";
console.log(Mix);

Kamu akan mendapatkan:

masukkan deskripsi gambar di sini

Kapan saya harus menggunakan kurung kurawal untuk impor ES6?

Tanda kurung berwarna emas ketika Anda hanya membutuhkan komponen tertentu dari modul, yang membuat jejak kaki yang lebih kecil untuk bundler seperti paket web.

prosti
sumber
4
Gambar Anda adalah lembar contekan yang sempurna untuk jawaban khusus ini.
Rodrirokr
1
Apakah import * as Mix from "./A";dan import A as Mix from "./A";sama?
Shafizadeh
40

Dan Abramov menjawab di atas menjelaskan tentang ekspor default dan ekspor bernama .

Yang mana untuk digunakan?

Mengutip David Herman : ECMAScript 6 mendukung gaya ekspor tunggal / standar, dan memberikan sintaksis paling manis untuk mengimpor default. Impor yang disebut ekspor dapat dan bahkan harus sedikit kurang ringkas.

Namun dalam TypeScript bernama ekspor disukai karena refactoring. Contoh, jika Anda mengekspor kelas secara default dan menamainya, nama kelas hanya akan berubah di file itu dan tidak di referensi lain, dengan nama kelas ekspor bernama akan diganti namanya di semua referensi. Ekspor yang dinamai juga lebih disukai untuk utilitas.

Keseluruhan gunakan apapun yang Anda inginkan.

Tambahan

Ekspor default sebenarnya adalah ekspor bernama dengan nama default, jadi ekspor default dapat diimpor sebagai:

import {default as Sample} from '../Sample.js';
Deepak Sharma
sumber
2
The Additionalline adalah informasi yang baik. import A from './A'tidak masuk akal jika Anda mengekspor tanpa mendefinisikan nama seperti export default 42.
PGT
8
Harap pastikan untuk tidak salah menafsirkan kutipan David Herman. Ini tidak berarti " Sangat disukai untuk selalu menggunakan ekspor tunggal / standar dalam ES6 ", tetapi " Karena ekspor tunggal sangat umum, ES6 mendukung standar terbaik dan kami memberikan mereka sintaks yang paling manis ".
Bergi
15

Jika Anda berpikir importhanya sebagai sintaksis gula untuk modul node, objek, dan perusakan, saya menemukan itu cukup intuitif.

// bar.js
module = {};

module.exports = { 
  functionA: () => {},
  functionB: ()=> {}
};

 // really all that is is this:
 var module = { 
   exports: {
      functionA, functionB
   }
  };

// then, over in foo.js

// the whole exported object: 
var fump = require('./bar.js'); //= { functionA, functionB }
// or
import fump from './bar' // same thing, object functionA and functionB props


// just one prop of the object
var fump = require('./bar.js').functionA;

// same as this, right?
var fump = { functionA, functionB }.functionA;

// and if we use es6 destructuring: 
var { functionA } =  { functionA, functionB };
// we get same result

// so, in import syntax:
import { functionA } from './bar';
Brandon
sumber
9

Untuk memahami penggunaan kurung kurawal dalam importpernyataan, pertama, Anda harus memahami konsep destruksi yang diperkenalkan dalam ES6

  1. Destrukturisasi objek

    var bodyBuilder = {
      firstname: 'Kai',
      lastname: 'Greene',
      nickname: 'The Predator'
    };
    
    var {firstname, lastname} = bodyBuilder;
    console.log(firstname, lastname); //Kai Greene
    
    firstname = 'Morgan';
    lastname = 'Aste';
    
    console.log(firstname, lastname); // Morgan Aste
  2. Perusakan susunan

    var [firstGame] = ['Gran Turismo', 'Burnout', 'GTA'];
    
    console.log(firstGame); // Gran Turismo

    Menggunakan daftar yang cocok

      var [,secondGame] = ['Gran Turismo', 'Burnout', 'GTA'];
      console.log(secondGame); // Burnout

    Menggunakan operator spread

    var [firstGame, ...rest] = ['Gran Turismo', 'Burnout', 'GTA'];
    console.log(firstGame);// Gran Turismo
    console.log(rest);// ['Burnout', 'GTA'];

Sekarang kita sudah berhasil, masuk ES6 Anda dapat mengekspor beberapa modul. Anda kemudian dapat menggunakan objek perusakan seperti di bawah ini

Mari kita asumsikan Anda memiliki modul yang disebut module.js

    export const printFirstname(firstname) => console.log(firstname);
    export const printLastname(lastname) => console.log(lastname);

Anda ingin mengimpor fungsi yang diekspor ke index.js;

    import {printFirstname, printLastname} from './module.js'

    printFirstname('Taylor');
    printLastname('Swift');

Anda juga dapat menggunakan nama variabel yang berbeda seperti itu

    import {printFirstname as pFname, printLastname as pLname} from './module.js'

    pFname('Taylor');
    pLanme('Swift');
theTypan
sumber
Karena Anda menunjukkan perbandingan pada destrukturisasi, saya akan menambahkan perbandingan destruksi yang setara dengan komentar terakhir Anda: import {printFirstname as pFname, printLastname as pLname} from './module.js'sama dengan:var foo = {printFirstname: 'p_f_n', printLastname: 'p_l_n'}; var { printFirstname:pFname, printLastname: pLname } = foo; pFname('Taylor'); pLname('Swift');
Adam Moisa
penggemar binaraga?
Tushar Pandey
@TusharPandey Saya seorang pembangun tubuh
theTypan
1
Saya pikir dalam penjelasan tentang mengimpor dan kapan menggunakan keriting vs tidak menggunakannya, jika Anda tidak menyebutkan penghancuran objek, Anda benar-benar tidak memberikan penjelasan terbaik. Setelah saya belajar tentang penataan, saya tidak pernah memikirkan mengapa saya menggunakan keriting itu lagi, itu hanya secara intuitif masuk akal.
Eric Bishard
6

ES6Modul ringkasan :

ekspor:

Anda memiliki 2 jenis ekspor:

  1. Ekspor bernama
  2. Ekspor default, Maks 1 per modul

Sintaksis:

// Module A
export const importantData_1 = 1;
export const importantData_2 = 2;
export default function foo () {}

Impor:

The jenis ekspor (yaitu bernama atau ekspor default) mempengaruhi bagaimana impor sesuatu:

  1. Untuk ekspor bernama kita harus menggunakan kurung kurawal dan nama yang tepat sebagai deklarasi (yaitu variabel, fungsi, atau kelas) yang diekspor.
  2. Untuk ekspor standar, kita dapat memilih nama.

Sintaksis:

// Module B, imports from module A which is located in the same directory

import { importantData_1 , importantData_2  } from './A';  // for our named imports

// syntax single named import: 
// import { importantData_1 } 

// for our default export (foo), the name choice is arbitrary
import ourFunction from './A';   

Hal-hal menarik:

  1. Gunakan daftar yang dipisahkan koma dalam kurung kurawal dengan nama yang cocok dari ekspor untuk ekspor yang disebutkan.
  2. Gunakan nama yang Anda pilih tanpa kurung kurawal untuk ekspor default.

Alias:

Setiap kali Anda ingin mengganti nama impor bernama ini dimungkinkan melalui alias . Sintaks untuk ini adalah sebagai berikut:

import { importantData_1 as myData } from './A';

Sekarang kami telah mengimpor importantData_1 tetapi pengenalnya myDatabukan importantData_1.

Willem van der Veen
sumber
5

biasanya ketika Anda mengekspor fungsi Anda perlu menggunakan {}

if you have export const x 

Kau gunakan import {x} from ''

if you use export default const x 

Anda perlu menggunakan import X from '' sini Anda dapat mengubah X ke variabel apa pun yang Anda inginkan

jadlmir
sumber
4

Kurung kurawal ({}) digunakan untuk mengimpor bindings bernama dan konsep di balik itu adalah penugasan merusak

Demonstrasi sederhana tentang cara kerja pernyataan impor dengan contoh dapat ditemukan dalam jawaban saya sendiri untuk pertanyaan serupa di Kapan kita menggunakan '{}' dalam impor javascript?

samuelj90
sumber
1
Anda pasti mendapatkan suara saya untuk jawaban singkat terbaik!
Eric Bishard 6-19
0

Kurung kurawal hanya digunakan untuk impor saat ekspor disebutkan. Jika ekspor default maka kurung kurawal tidak digunakan untuk impor.

Abhishek Kumar
sumber
0

Untuk ekspor default, kami tidak menggunakan {} ketika kami mengimpor.

misalnya

player.js

export default vx;

index.js

import vx from './player';

index.js masukkan deskripsi gambar di sini

player.js masukkan deskripsi gambar di sini

Jika kami ingin mengimpor semua yang kami ekspor maka kami menggunakan * masukkan deskripsi gambar di sini

pengguna260778
sumber