모듈이란? feat. 일반스코프와 모듈의차이
모듈은 대개 클래스 하나, 또는 특정한 목적을 가진 여러개의 함수로 구성된 라이브러리로 구성된다.
자바스크립트가 만들어진지 얼마 안되었을 때에는 자바스크립트로 만든 스크립트의 크기도 작고, 기능도 단순했기 때문에 자바스크립트는 긴 세월 동안 모듈 관련 표준 문법이 필요없었다.
그런데 스크립트의 크기가 점차 커지고, 기능도 복잡해지자 자바스크립트 커뮤니티는 특별한 라이브러리를 만들어서 필요한 모듈을 언제든지 불러올 수 있게 해준다거나 코드를 모듈 단위로 구성해주는 방법을 만드는 등 다양한 시도를 하게된다.
- AMD
가장 오래된 모듈 시스템중 하나로, require.js 라는 라이브러를 통해 처음 개발되었다. - CommonJS
Node.js 서버를 위해 만들어진 모듈 시스템이다. - UMD
AMD와 CommonJS와 같은 다양한 모듈 시스템을 함께 사용하기 위해 만들어졌다.
모듈은 그냥 파일 하나에 불과하고, 스크립트 하나는 모듈 하나이다.
모듈에 특수한 지시자 export, import 으로 모듈을 내보내고 가져올 수 있다.
브라우저에서는 특수한 키워드나 기능과 함께 사용되므로 <script type="module">
과 같은 속성을 설정해서 해당 스크립트가 모듈이라는 것을 브라우저가 알 수 있게 해야한다.
!주의!
모듈은 로컬 파일에서 동작하지 않고, http또는 https프로토콜을 사용해서만 동작한다.
즉, file://가 아닌 localhost같은 live server같은 것을 이용해서 동작시켜야 한다.
일반 스코프와 모듈의 차이
모듈은 항상 엄격모드로 실행된다. 즉 선언되지 않은 변수에 값을 할당하는 코드는 에러를 발생시킨다.
<script type="module">
a = 5; //error
</script>
모듈은 자신만의 스코프를 가지고 있다.
브라우저 환경에서도 script type="module"하면 독립적인 스코프가 만들어진다.
<script type="module">
// user는 해당 모듈 안에서만 접근 가능합니다.
let user = "John";
</script>
<script type="module">
alert(user); // Error: user is not defined
</script>
참고로, 브라우저 환경에서 window 레벨 전역변수가 필요하면 window객체를 명시적으로 사용하면된다.
script type="module" src="..."
는 defer를 붙인것과 똑같이 동작한다.
type="module"
인데 src가 같으면 스크립트가 한번만 실행된다.
빌드툴 관점
브라우저 환경에서 모듈을 단독으로 사용하는 경우는 흔치않고, webpack이 번들링하여 적용합니다.
- HTML의 script type='module'에 넣을 진입점 모듈을 선택 index.js
- 진입점 모듈에 의존하는 모듈들을 가지고와서 의존성 트리를 그림
- 모듈을 한데 모아서 번들링
- 이때 트리셰이킹 등등의 변형 및 최적화 수행
번들링 과정이 끝나면 import, export가 사라져서 type="module"이 더이상 필요없게됨
즉, 웹팩이 번들링되면
<script src="bundle.js"></script>
만 써도됨.
즉, 모듈이 일반 스크립트가 됨!
import는 무조건 최상단에서 쓰여야함!
import()는 동적 import 문법으로 상관없고, type="module"가 아닌 일반스크립트에서도 사용가능!
참고
'개발 > FrontEnd Interview' 카테고리의 다른 글
Shadow DOM이 아니라 Iframe를 사용한 이유 (2) | 2021.07.21 |
---|---|
obj.method를 할때 자바스크립트에서는 어떤일이 발생할까 (0) | 2021.06.29 |
Tagged Template Literals (feat. styled-component) (1) | 2021.06.27 |
prettier와 eslint의 차이가 뭔가요? (0) | 2021.06.27 |
package-lock.json, yarn.lock 너희들은 뭐냐! (0) | 2021.06.27 |