1️⃣ script
<script src="./module1.js"></script>
<script src="./module2.js"></script>
<script src="./module3.js"></script>
초기에는 프로그램의 규모가 작았기 때문에 약간의 상호작용만 제공하면 됐기에 다른 파일을 불러올 때 script를 사용하여 전체 다 가져옴
문제점
자바스크립트는 파일마다 독립적인 스코프를 가지지 않고 전체 파일이 하나의 전역 객체를 공유하여 사용
⇒ 전역변수가 중복되는 문제가 발생할 수 있음 (위 같이 여러 개의 파일로 분리해도 1, 2, 3이 같은 스코프를 공유하기 때문에 모듈화가 아님)
문제 해결
- 모듈: 재사용 가능한 코드 조각으로 애플리케이션을 구성하는 개별 요소
파일을 모듈로 나누어 내보내고 불러옴 ⇒ Node.js는 Common JS를 채택
2️⃣ Common JS
module.exports = { ... } // 모듈 내보낼 때
const utils = require('utils'); // 모듈 가져올 때
module.exports
로 모듈을 내보내고 require()
로 접근
Bundler 사용 이유
requier()
은 Node.js에만 있고 브라우저에서 지원하지 않기에 브라우저가 이해하게 하려면 번들러가 필요함
번들러는 빌드하면서 require()
를 지우고 모듈을 통채로 가져와서 적용해줌
⇒ 이 때문에 Browerify / webpack 같은 툴이 탄생하고 발전함
// a.js
module.exports = "Hi"
// b.js
var a = require("./a")
console.log(a) // = hi
// a.js와 b.js를 bundle하면
var b = "Hi"
console.log(b);
문제점
번들러가 모듈 내의 메소드 전체를 가져오다보니 크기가 커짐
⇒ 일부만 가져오며 정적으로 분석할 수 있게끔 하는 방식 사용 : ES Module
// user.js
module.exports = {
name: 'Eunjae',
address: '...',
phone: '..'
}
// app.js
var user = require('./user')
console.log(user. name)
// 번들러로 가져올 때
var user = { // name만 사용하지만 전체 다 가져옴
name: 'Eunjae',
address: '...',
phone: '..'
}
console.log(user. name)
3️⃣ ES Modules
export.default =()=> { ... }; // 모듈 내보낼 때
import utils from 'utils'; // 모듈 가져올 때
export
로 내보내고 import
로 접근
번들 과정
요즘 모던 브라우저는 거의 import를 지원하지만 그렇지 않은 브라우저가 간혹 있으니 번들러를 사용해야함
CJS에 비해 가져올 모듈의 일부를 명시적으로 지정할 수 있기에 효율적임
// user.js
export const name = 'Eunjae'
export const address = '..'
export const phone = '..'
// app.js
import { name } from './user'
console.log(name)
// 번들 하면
// index.js
const name = 'Eunjae' // 이렇게 모듈 중 일부만 가져옴
console.log(name)
번들러는 require / import 상관없이 같은 방식으로 번들함
이렇게 만든 파일은 전통적인 방식으로 HTML에 포함되어 배포됨
<script src="./index.dif98w.js"></script>
지원되는 브라우저는...
<script>
태그에 type="module"
을 넣으면 안에서 import 구문을 사용할 수 있음
<script type="module">
import { name } from './user.js'
console.log(name)
</script>
📌 번들러를 버릴 수 없는 이유
require / import를 브라우저에서 사용하기 위해 탄생했지만 이 밖의 기능도 많이 해서 의존도가 높아짐 (sass 파일을 css로 변환)
현재는 자바스크립트 & 브라우저 API & webpack or Next.js의 설정 등의 경계가 흐려지고 섞인 상황
이를 명확하게 이해하고 정리하기는 어렵고 대강 타임라인만 이해하면 될 듯!
참고
모듈과 CommonJS vs ES modules
Common JS, ES Modules, Bundler, ...
'Programming > Client' 카테고리의 다른 글
body 스크롤 확실하게 막기 (0) | 2024.06.07 |
---|---|
여러 번 호출 가능한 abortController 만들기 (feat. useRef) (0) | 2024.06.07 |
[MSW] 브라우저, Node.js 환경에서 API 모킹하기 (0) | 2023.05.22 |
Javascript / React에서 Fetch 올바르게 사용하기 (with Node.js 테스트 환경) (0) | 2023.05.21 |
[Next.js] 웹 사이트 방문자 데이터 수집 (with GA: 구글 애널리틱스 ) (0) | 2023.05.08 |