대충 영어로는 이런 에러고"Cannot write file ... because it would overwrite input file."
한글로는 아래처럼 "... 파일은 입력 파일을 덮어쓰므로 쓸 수 없습니다."
라는 문구의 에러를 만났다 😬
일단, 문제가 발생한 파트는 메인 API 쪽은 아니고, Database에 특정 정보를 third party(kakao place, google spreadsheet)부터 가져와서 데이터를 전처리하고 prisma를 통해 db로 push해주는 코드를 짜는 일종의 모듈/패키지 개발 쪽이다.
대충 패키지 구조는
gym-collector/
modules/
grade-collecotor.js -> 문제의 파일
retryCatch.ts
index.ts
type.d.ts
...
사실 타입스크립트로 작성했으면 참 좋았겠지만 Google SpreadSheet API를 이용해 정보를 긁어오는 Node.js 버전 코드를 거의 그대로 옮겨왔는데, 타입스크립트로 변형해주기 너무 귀찮아서(ㅎㅎ) allowJS를 해주고 사용하기로 했다. 마침 예제코드에 이미 JSDoc type hints가 모두 적혀져있기도 했기 때문에...!
아무튼 allowJS를 true로 설정해준 후, include에 modules/ 폴더를 넣어주었는데 위와같은 에러가 발생했다. 아니 일단 번역체부터가 이해가 안된다. 대체 무슨 소리일까...?하고 구글링 해봤는데 한글로 하면 안나오더라.(영어 설정으로 사용해야하는 EU..)
그래서 추측해서 영어로 구글링을 다시 해봤는데 내 케이스에 맞는 적절한 답변과 원인에 대한 설명을 얻을 수 있었다.
https://stackoverflow.com/questions/42609768/typescript-error-cannot-write-file-because-it-would-overwrite-input-file
정확히 allowJS:true일때 발생하는 문제로, outDir를 만약 지정하지 않았다면 include해준 javascript 파일도 같이 컴파일 되므로 javascript 원본 파일이 overwrite 되기 때문에 이를 알려주기 위한 에러라는 것이다.
결론적으로 해당 에러는 outDir를 지정해주거나, noEmit으로 js 파일을 내보내지 않겠다고 선언하면 사라진다. 해당 패키지는 다른 package에서 import할 목적으로 만든 내용은 아니고 npm script를 통해 ts-node로 실행
하는 것이 목적이기에 굳이 js 파일을 내보낼 필요는 없어서 outDir
대신 noEmit을 true로 설정해주었다.
{
"compilerOptions": {
/* Visit https://aka.ms/tsconfig.json to read more about this file */
/* Basic Options */
"target": "esnext" /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019', 'ES2020', 'ES2021', or 'ESNEXT'. */,
"module": "ESNext" /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', 'es2020', or 'ESNext'. */,
"allowJs": true /* Allow javascript files to be compiled. */,
"noEmit": true /* Do not emit outputs. */,
"composite": true /* Enable project compilation */,
/* Strict Type-Checking Options */
"strict": true /* Enable all strict type-checking options. */,
/* Module Resolution Options */
"resolveJsonModule": true,
"moduleResolution": "node" /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */,
"baseUrl": "." /* Base directory to resolve non-absolute module names. */,
/* Type declaration files to be included in compilation. */
"allowSyntheticDefaultImports": true /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */,
"esModuleInterop": true /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */,
/* Advanced Options */
"skipLibCheck": true /* Skip type checking of declaration files. */,
"forceConsistentCasingInFileNames": true /* Disallow inconsistently-cased references to the same file. */
},
"ts-node": {
"esm": true,
"files": true,
"transpileOnly": true,
"experimentalResolver": true,
"experimentalSpecifierResolution": "node",
"compilerOptions": {
"module": "commonjs"
}
},
"include": ["index.ts", "./type.d.ts", "*.json", "modules"]
}