단순 컴파일 혹은, 번들러에 컴파일러를 연결할 때, 어떤 컴파일러를 사용할지 고민이 있던 적이 있을 것입니다.
타입스크립트 프로젝트의 관점에서만 tsc, babel, esbuild 중 어떤 컴파일러를 도입하는 것이 좋을 지 생각해보겠습니다.
용어 정리가 필요할 것 같아서, babel을 예시로 babel과 babel-loader가 뭐가 다른지만 살짝 짚고 넘어가겠습니다. babel과 babel-loader는 다른 것이 아닙니다. loader는 webpack 같은 번들러를 사용할 때 해당 번들러와 컴파일러를 연결하는 역할을 할 뿐입니다.즉, 이 글에서는 babel과 babel-loader를 같은 의미로 사용하겠습니다.
(1번과 2번은 하나의 파일을 사용할 뿐 상관 관계는 전혀없습니다.)
tsc 의 경우는 tsc --build tsconfig.json 을 통해 특정 옵션 파일을 지정할 수 있지만,
tsserver의 경우는 무조건 tsconfig.json의 옵션을 따르게 됩니다.
compilerOption은 tsc의 옵션일뿐, babal, ts-loader, es-loader의 옵션은 아닙니다.
tsconfig.json의 관점에서 해석하면 차이점을 인지하기가 보다 쉬운데,
tsconfig.json는 tsc 명령어로 컴파일할때 컴파일에 대한 옵션을 제공하며, vsc의 내장 타입 체커인 tsserver도 이 tsconfig의 옵션을 확인하여 타입체크를 진행합니다.
tsc 명령어로 트랜스파일링을 진행할때 직접 tsconfig 파일을 지정하지 않으면 프로젝트 디렉토리를 순회하면서 tsconfig.json 파일을 찾고 컴파일 옵션에 따라 트랜스파일을 진행합니다.
( 직접 지정할 수 있다는 것은 tsconfig 파일이 경우에 따라 여러개 일 수 있다는 뜻)
( tsc와 함께 옵션을 직접 지정할 수 있는데, 이때 직접 커맨드에 지정한 옵션이 우선시 됨)
(* tsc index.ts 처럼 파일을 직접 지정할 경우, tsconfig.json의 옵션은 무시되고 기본 옵션으로 적용됨)
이때 'declaration' 옵션을 활성화 시키면,
컴파일된 파일들이 다른 타입스크립트 프로젝트에서도 타입추론이 가능하도록 해주는 d.ts 파일을 제공할 수 있는데,
이는 tsc 명령어로 트랜스파일링할 경우에만 가능합니다.
또한 tsc 명령어는 컴파일 과정에서 타입체크를 기본적으로 진행합니다.
babel로 트랜스파일할 경우 babel은 tsconfig.json의 옵션을 확인하지 않고 대신 babel-prest-typescipt의 기본 옵션을 사용합니다.
(babel로 빌드할 때 tsconfig.json에 컴파일 옵션을 아무리 적어도 의미가 없음)
tsc의 트랜스파일과정과는 다르기때문에, 타입체크를 진행하지도 않고, declaration 옵션으로 d.ts 파일을 생성할 수 없습니다.
단 이 점 덕분에, tsc의 트랜스파일링보다는 훨씬 빠르게 작동합니다.
esbuild는 다른 컴파일러보다 go 언어, 병렬처리, 타입체크X 등의 이유로 더 빨리 동작하는데, esbuild는 babel과 다르게 tsc 명령어와 관련이 없지만 tsconfig의 옵션을 참고합니다. tsconfig를 기반으로 트랜스파일을 진행하는 것은 아니고, jsxFactory, jsxFragmentFactory, useDefundeForClassFields, importsNotUsedAsValues 의 옵션만 부분적으로 확인하고 적용합니다.
다른 컴파일 옵션은 esbuild의 옵션을 따르기 때문에 declatation 옵션을 사용할 수 없고, esbuild의 경우도 d.ts 파일을 생성할 수 없습니다.
(babel, esbuild 로 컴파일 하며, d.ts 를 제공하고싶은 경우 tsc --emitDeclarationOnly 같은 커맨드를 포함시켜야함)