타입스크립트 디버깅 기법
소스맵과 브라우저·VS Code 중단점, 구조화된 로그, 컴파일러 오류를 활용해 프론트·서버 문제의 원인을 추적합니다.
이전 절들에서는 Jest를 사용한 단위 테스트와 Cypress를 사용한 E2E 테스트를 통해 코드의 정확성을 검증하는 방법을 알아보았습니다.
하지만 아무리 철저하게 테스트를 작성하더라도, 애플리케이션 개발 과정에서는 예상치 못한 버그나 로직 오류가 발생하기 마련입니다.
이때 필요한 것이 바로 디버깅(Debugging)입니다.
디버깅은 소프트웨어의 오류(버그)를 찾아내고 수정하는 과정입니다.
타입스크립트는 컴파일 시점에 강력한 타입 검사를 제공하여 많은 오류를 미리 잡아주지만, 런타임에 발생하는 논리적 오류나 외부 시스템과의 연동 문제는 여전히 디버깅을 통해 해결해야 합니다.
이 절에서는 타입스크립트 프로젝트에서 효과적으로 디버깅을 수행하기 위한 다양한 기법과 도구들을 소개합니다.
테스트는 회귀를 막지만, 실패 순간의 런타임 값과 호출 순서를 대신 보여주지는 않습니다. 타입스크립트 디버깅은 소스맵으로 원본 위치를 되찾고, 중단점과 로그로 타입 이후의 실제 값을 추적하는 과정입니다.
- 1브라우저 개발자 도구를 이용한 디버깅
프론트엔드 애플리케이션을 개발할 때는 웹 브라우저가 제공하는 개발자 도구로 DOM, 네트워크 요청, 콘솔 오류, 중단점을 함께 확인합니다. 디버깅(Debugging)
- 2VS Code를 이용한 디버깅 (Node.js/React)
VS Code launch 설정을 쓰면 Node.js 프로세스와 React 개발 서버에 중단점을 연결할 수 있습니다. 디버깅
- 3로깅(Logging)을 이용한 디버깅
그는 특정 지점의 입력, 분기, 반환값을 남겨 재현이 어려운 흐름을 좁히지만, 민감 정보와 과도한 출력은 배포 전에 제거해야 합니다. 원본 소스 코드 매핑 (Source Maps)
- 4타입스크립트 디버깅 기법 기준
정확성 브라우저 디버깅은 Source Maps를 켜고 DevTools Sources 탭에서 TypeScript 원본 기준으로 중단점을 확인합니다. 비용 Node.js 디버깅은 --inspect나 VS Code launch 설정으로 서버 프로세스에 붙어 비동기 스택과 런타임 값을 추적합니다. 확장성 원본 소스 코드 매핑 (Source Maps): 타입스크립트 코드는 브라우저에서 실행될 때 자바스크립트로 변환됩니다. 예외 디버깅을 원활하게 하려면 tsconfig의 sourceMap을 켜고 실행 도구가 .map 파일을 읽도록 맞춥니다.
- 5정확성 브라우저 디버깅
Source Maps를 켜고 DevTools Sources 탭에서 TypeScript 원본 기준으로 중단점을 확인합니다.
- 6비용 Node.js 디버깅
--inspect나 VS Code launch 설정으로 서버 프로세스에 붙어 비동기 스택과 런타임 값을 추적합니다.
- 7확장성 원본 소스 코드 매핑 (Source Maps)
타입스크립트 코드는 브라우저에서 실행될 때 자바스크립트로 변환됩니다.
- 8예외 디버깅
원활하게 하려면 tsconfig의 sourceMap을 켜고 실행 도구가 .map 파일을 읽도록 맞춥니다.
타입 검사부터 소스맵 기반 중단점 디버깅, 실행 제어와 상태 관찰까지 이어지는 핵심 루프를 먼저 한 장으로 정리합니다.
브라우저 개발자 도구를 이용한 디버깅
프론트엔드 애플리케이션을 개발할 때는 웹 브라우저가 제공하는 개발자 도구가 가장 강력한 디버깅 도구입니다.
크롬, 파이어폭스, 엣지 등 대부분의 최신 브라우저는 유사한 기능을 제공합니다.
Sources 탭 활용
Sources 탭은 자바스크립트(타입스크립트) 코드를 실행 중에 디버깅하는 핵심 공간입니다.
- 원본 소스 코드 매핑 (Source Maps): 타입스크립트 코드는 브라우저에서 실행될 때 자바스크립트로 변환됩니다. 디버깅을 원활하게 하려면, 컴파일된 자바스크립트 코드와 원본 타입스크립트 코드를 연결해주는 소스 맵(Source Map)이 필수적입니다.
tsconfig.json파일에서sourceMap옵션을true로 설정해야 합니다.tsconfig.json { "compilerOptions": { // ... "sourceMap": true, // 이 옵션을 true로 설정 // ... } }- 대부분의 프론트엔드 빌드 도구(Webpack, Vite 등)는 기본적으로 소스 맵을 생성하도록 설정되어 있습니다.
- 중단점 (Breakpoints): 코드의 특정 라인에서 실행을 일시 중지시키는 지점입니다. 중단점이 활성화되면, 해당 라인에서 실행이 멈추고 현재 스코프의 변수 값, 호출 스택 등을 검사할 수 있습니다.
Sources탭에서 코드 라인 번호를 클릭하여 설정/해제할 수 있습니다.- 조건부 중단점 (Conditional Breakpoints): 특정 조건이 만족할 때만 실행이 중지되도록 설정할 수 있습니다. (우클릭 ->
Add conditional breakpoint) - 로그 포인트 (Logpoints): 실행을 멈추지 않고 특정 라인의 변수 값이나 메시지를 콘솔에 출력합니다.
console.log를 코드를 수정하지 않고 사용할 때 유용합니다. (우클릭 ->Add logpoint)
-
실행 제어
- Continue (F8): 다음 중단점까지 실행을 계속합니다.
- Step Over (F10): 현재 라인을 실행하고 다음 라인으로 이동합니다. 함수 호출이 있으면 함수 내부로 들어가지 않고 함수 전체를 실행합니다.
- Step Into (F11): 현재 라인을 실행하고 다음 라인으로 이동합니다. 함수 호출이 있으면 함수 내부로 들어갑니다.
- Step Out (Shift + F11): 현재 함수 실행을 완료하고, 해당 함수를 호출했던 위치의 다음 라인으로 이동합니다.
- 스코프(Scope) 및 변수 검사: 중단점에서 멈췄을 때,
Scope패널에서 현재 스코프 내의 모든 변수와 그 값을 확인할 수 있습니다.Watch패널에 특정 변수를 추가하여 지속적으로 감시할 수도 있습니다. -
콘솔(Console) 활용
- 디버깅 중 콘솔에서 현재 스코프의 변수 값을 직접 변경하거나, 함수를 실행해볼 수 있습니다.
console.log(),console.warn(),console.error(),console.table()등을 활용하여 코드 실행 흐름과 변수 값을 출력할 수 있습니다.
VS Code를 이용한 디버깅 (Node.js/React)
브레이크포인트는 실행을 멈추고 sourcemap은 컴파일된 JavaScript 위치를 원본 TypeScript 줄과 맞춘다.
- 의심되는 TypeScript 줄에 중단점 설정
breakpoint 의심되는 TypeScript 줄에 중단점 설정 실행을 멈출 위치를 고른다.
- Node.js 또는 브라우저 실행
runtime Node.js 또는 브라우저 실행 컴파일 결과가 실제로 돈다.
- 원본 줄 매핑
sourcemap 원본 줄 매핑 디버거 위치와 TS 파일을 연결한다.
- 콜스택과 지역 변수 확인
inspect 콜스택과 지역 변수 확인 타입 오류가 아니라 실행 순간의 값을 본다.
| 구분 | 의미 | 판단 |
|---|---|---|
| 줄 위치 불일치 | sourcemap 확인 | 빌드 결과와 원본 파일 매핑 문제 |
| 상태 확인 | variables, call stack | 실제 값과 호출 경로 추적 |
| 재개 | step/continue | 다음 상태 변화 지점으로 이동 |
VS Code는 Node.js 애플리케이션 및 React 애플리케이션을 위한 강력한 디버깅 환경을 내장하고 있습니다.
타입스크립트 코드도 직접 디버깅할 수 있어 매우 효율적입니다.
Node.js 애플리케이션 디버깅
launch.json 파일을 설정하여 Node.js 애플리케이션을 디버깅할 수 있습니다.
VS Code 좌측의 Run and Debug 탭(벌레 아이콘)을 클릭합니다.
create a launch.json file 링크를 클릭하고, Node.js 환경을 선택합니다.
자동 생성된 launch.json 파일의 configurations 배열을 수정합니다.
{
"version": "0.2.0",
"configurations": [
{
"type": "node",
"request": "launch",
"name": "Launch Program (TypeScript)",
"skipFiles": ["<node_internals>/**"],
"runtimeArgs": ["-r", "ts-node/register"], // ts-node를 사용하여 TypeScript 파일 직접 실행
"args": ["${workspaceFolder}/src/index.ts"], // 실행할 엔트리 포인트 파일
"cwd": "${workspaceFolder}", // 작업 디렉토리
"console": "integratedTerminal", // 디버그 콘솔
"sourceMaps": true // 소스 맵 사용
}
]
}runtimeArgs: ["-r", "ts-node/register"]:ts-node를 사용하여 컴파일 없이 타입스크립트 파일을 직접 실행합니다.args: ["${workspaceFolder}/src/index.ts"]: 애플리케이션의 진입점 파일입니다.sourceMaps: true: 타입스크립트 소스 맵을 사용하여 원본.ts파일에서 디버깅할 수 있게 합니다.
코드에 중단점을 설정하고 (.ts 파일의 라인 번호 옆 클릭), Run and Debug 탭에서 Launch Program (TypeScript)를 선택하고 실행 버튼(녹색 삼각형)을 클릭합니다.
React (Vite) 애플리케이션 디버깅
Vite로 생성된 프로젝트는 기본적으로 소스 맵을 포함하며, VS Code와 잘 통합됩니다.
Debugger for Chrome (또는 Edge) 확장 프로그램 설치: VS Code Extensions 탭에서 Debugger for Chrome 또는 Debugger for Edge를 검색하여 설치합니다.
launch.json 파일 설정
{
"version": "0.2.0",
"configurations": [
{
"name": "Launch Chrome against localhost",
"type": "pwa-chrome", // 또는 pwa-msedge
"request": "launch",
"url": "http://localhost:3000", // React 앱이 실행되는 URL
"webRoot": "${workspaceFolder}/src",
"sourceMapPathOverrides": {
"webpack:///./src/*": "${webRoot}/*" // 번들러 소스 맵 경로 오버라이드 (필요 시)
}
}
]
}React 개발 서버를 시작합니다 (npm start).
VS Code에서 디버깅을 시작하면 브라우저가 열리고, .tsx 파일에 설정한 중단점에서 코드가 멈추는 것을 확인할 수 있습니다.
로깅(Logging)을 이용한 디버깅
가장 기본적인 디버깅 기법은 console.log()와 같은 로깅 명령어를 사용하여 프로그램의 상태나 변수 값을 출력해보는 것입니다.
- 간단하고 빠름: 즉시 적용하여 결과를 볼 수 있습니다.
- 비침습적: 실행 흐름을 멈추지 않고 정보를 얻을 수 있습니다.
console.log가 너무 많아지면 코드의 가독성을 해치고, 프로덕션 환경에 배포될 경우 성능 저하나 보안 문제를 야기할 수 있습니다.- 복잡한 객체를 출력할 때는
console.dir()이나console.table()을 사용하여 더 구조화된 출력을 얻을 수 있습니다.
function processData(data: string[]): number {
console.log('--- Debugging processData ---'); // 함수 진입 시 로깅
let sum = 0;
for (const item of data) {
const num = parseInt(item, 10);
console.log(`Processing item: ${item}, parsed as: ${num}`); // 각 항목 처리 로깅
if (isNaN(num)) {
console.warn(`Warning: Invalid number encountered: ${item}`); // 경고 로깅
continue;
}
sum += num;
}
console.log('Final sum:', sum); // 최종 결과 로깅
console.log('--- End of processData ---');
return sum;
}타입 오류, 로그, 중단점, 네트워크 기록을 같은 흐름에 놓으면 런타임 문제를 더 차분하게 추적할 수 있습니다.
- 1재현
어떤 입력과 화면 상태에서 문제가 반복되는지 고정합니다.
- 2관찰
그, Network 탭, Scope 패널로 실제 값을 확인합니다.
- 3가설
타입 계약과 런타임 값이 어긋나는 지점을 후보로 좁힙니다.
- 4검증
수정 후 테스트와 같은 재현 절차로 회귀 여부를 확인합니다.
타입스크립트 컴파일러 에러 활용
타입스크립트의 가장 큰 장점은 강력한 정적 타입 검사입니다.
컴파일 시점에 발생하는 에러 메시지를 이해하고 해결하는 것이 가장 효율적인 디버깅의 시작입니다.
- 명확한 에러 메시지: 타입스크립트 컴파일러(
tsc)는 타입 불일치, 오타, 누락된 속성 등에 대해 매우 상세한 에러 메시지를 제공합니다. - IDE의 실시간 피드백: VS Code와 같은 IDE는 타입스크립트 컴파일러와 통합되어 코드를 작성하는 즉시 에러를 표시하고 수정 가이드를 제공합니다.
strict모드 활용:tsconfig.json에서strict: true를 설정하면 더 엄격한 타입 검사를 통해 잠재적인 런타임 오류를 미리 방지할 수 있습니다. (예:null또는undefined에 대한 엄격한 검사)
// 예시: 타입 오류를 통한 디버깅
interface Product {
id: number;
name: string;
price: number;
}
function getProductName(product: Product): string {
// return product.Name; // Error: Property 'Name' does not exist on type 'Product'. Did you mean 'name'?
return product.name;
}
const myProduct = { id: 1, name: 'Laptop', cost: 1200 };
// getProductName(myProduct); // Error: Argument of type '{ id: number; name: string; cost: number; }' is not assignable to parameter of type 'Product'.
// Object literal may only specify known properties, and 'cost' does not exist in type 'Product'.이러한 에러 메시지는 런타임에 발생할 수 있는 undefined 접근 오류나 논리적 실수를 사전에 방지해줍니다.
고급 디버깅 기법
- 조건부 로깅/디버깅: 특정 조건에서만 로깅을 활성화하거나 디버거를 실행하도록 설정합니다. (예:
if (DEBUG_MODE) { console.log(...) }) - 네트워크 탭 (브라우저 개발자 도구): API 요청/응답의 상태 코드, 페이로드, 시간 등을 확인하여 백엔드 통신 문제를 디버깅합니다.
- 성능 탭 (브라우저 개발자 도구): 애플리케이션의 렌더링 성능, 자바스크립트 실행 시간 등을 프로파일링하여 성능 병목 현상을 찾습니다.
- Source Maps in Production: 프로덕션 환경에서도 소스 맵을 사용하여 사용자가 겪는 오류를 추적하고 디버깅할 수 있습니다. 다만, 보안상의 이유로 일반 사용자에게는 노출되지 않도록 설정하는 것이 중요합니다. (예: 특정 서버에서만 소스 맵 제공)
디버깅 요약
디버깅은 개발 과정에서 피할 수 없는 부분이며, 효율적인 디버깅 능력은 개발자의 생산성에 큰 영향을 미칩니다.
타입스크립트는 정적 타입 검사를 통해 많은 오류를 사전에 방지하지만, 런타임 버그는 여전히 발생할 수 있습니다.
브라우저 개발자 도구의 Sources 탭, VS Code의 통합 디버거, 그리고 전략적인 로깅은 타입스크립트 애플리케이션을 디버깅하는 데 가장 강력한 도구들입니다.
이러한 도구들을 능숙하게 활용하고, 타입스크립트 컴파일러의 경고와 에러 메시지를 적극적으로 활용하여 코드의 견고성을 높이는 것이 중요합니다.
디버깅은 버그 수정뿐 아니라 코드의 실행 흐름과 잠재적인 문제를 확인하는 과정입니다.
재현 조건, 관찰 지표, 수정 결과를 함께 기록해야 효과를 확인할 수 있습니다.
아래 다이어그램은 오류가 발생했을 때 타입 검사, 소스맵, 중단점, 네트워크/성능 탭 중 어떤 단서를 먼저 볼지 정리한 진단표입니다.
타입 에러, 런타임 예외, 느린 화면, 실패한 요청은 서로 다른 단서를 남기므로 진단 출발점도 달라집니다.
- 컴파일 오류
타입 추론, 제네릭 제약, nullable 경로를 확인합니다.
- 런타임 예외
소스맵으로 원본 위치를 찾고 중단점에서 값 변화를 따라갑니다.
- API 실패
요청 payload, 응답 status, CORS, 인증 헤더를 먼저 비교합니다.
- 느린 화면
렌더링, 스크립트 실행, 네트워크 대기 시간을 분리해서 봅니다.
- 반복 루프
입력, 계정, 브라우저 상태를 고정합니다.
아래 다이어그램은 재현 조건을 고정한 뒤 타입 오류, 소스맵, 런타임 상태 중 어떤 증거를 먼저 확인할지 정리한 선택표입니다.
먼저 재현 조건을 고정한 뒤 컴파일러, 소스맵, 브라우저 패널 중 가장 가까운 증거를 선택합니다.
- type
컴파일러 오류부터 읽기 · 속성명, null 가능성, 제네릭 추론 오류는 런타임 전에 고칠 수 있는 신호입니다.
- source
소스맵으로 원본 위치 추적 · 빌드된 JS가 아니라 `.ts`와 `.tsx` 줄에서 중단점을 걸어 상태를 확인합니다.
- runtime
실행 중 값과 요청 비교 · Scope, Watch, Network 탭으로 화면 상태와 API 응답이 언제 어긋나는지 봅니다.
아래 다이어그램은 타입스크립트 디버깅 기법에서 브라우저 개발자 도구를 이용한 디버깅과 Sources 탭 활용을 검증 신호와 재현 절차 기준으로 연결합니다.
런타임은 emit된 JavaScript를 실행한다. debugger는 JS 위치와 map을 결합해 TypeScript 원본 줄을 보여 줄 뿐이며, 외부 입력의 형태나 타입 선언의 진실성까지 검증하지 않는다.
- CHECKTypeScript source
CHECK TypeScript source tsc --noEmit 로 정적 계약을 검사한다.
- EMITJavaScript
EMIT JavaScript 실제로 실행되는 코드. outDir 와 module 형식을 고정한다.
- MAP.js.map
MAP .js.map 생성 위치를 원본 위치와 연결한다. inlineSources 는 TS 내용도 담는다.
- VIEWdebugger / stack
VIEW debugger / stack 도구가 map을 읽을 때 TS 파일과 줄 번호로 되돌려 표시한다.
타입스크립트 디버깅은 타입 오류, 소스맵, 중단점, 네트워크 로그를 한 번에 열어두는 일이 아니라 재현 조건에 맞는 증거를 좁히는 과정입니다.
수정 뒤에는 같은 조건에서 실패가 사라졌는지 기록해 회귀 확인 기준으로 남깁니다.