From 2d0417b496d06c5f0dc5860fd1c38f55ed0ebebc Mon Sep 17 00:00:00 2001 From: doitchuu Date: Tue, 22 Apr 2025 00:09:34 +0900 Subject: [PATCH 1/5] =?UTF-8?q?[Docs]=206.1=20=EC=A0=95=EB=A6=AC=20?= =?UTF-8?q?=EC=99=84=EB=A3=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../seulgi.md" | 80 ++++++++++++++++++- 1 file changed, 79 insertions(+), 1 deletion(-) diff --git "a/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.1_\354\236\220\353\260\224\354\212\244\355\201\254\353\246\275\355\212\270\354\235\230_\353\237\260\355\203\200\354\236\204\352\263\274_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270\354\235\230_\354\273\264\355\214\214\354\235\274/seulgi.md" "b/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.1_\354\236\220\353\260\224\354\212\244\355\201\254\353\246\275\355\212\270\354\235\230_\353\237\260\355\203\200\354\236\204\352\263\274_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270\354\235\230_\354\273\264\355\214\214\354\235\274/seulgi.md" index 3beced8..e498801 100644 --- "a/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.1_\354\236\220\353\260\224\354\212\244\355\201\254\353\246\275\355\212\270\354\235\230_\353\237\260\355\203\200\354\236\204\352\263\274_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270\354\235\230_\354\273\264\355\214\214\354\235\274/seulgi.md" +++ "b/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.1_\354\236\220\353\260\224\354\212\244\355\201\254\353\246\275\355\212\270\354\235\230_\353\237\260\355\203\200\354\236\204\352\263\274_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270\354\235\230_\354\273\264\355\214\214\354\235\274/seulgi.md" @@ -1 +1,79 @@ - +# 1. 자바스크립트의 런타임과 타입스크립트의 컴파일 + +## 1) 런타임과 컴파일타임 + +프로그래밍 언어는 일반적으로 고수준 언어 / 저수준 언어로 구분할 수 있다. + +
+ +### 고수준 언어? 저수준 언어? + +- 고수준 언어 : 사람이 이해하기 쉬운 형식으로 작성 +- 저수준 언어 : 컴퓨터가 이해하기 쉬운 형식으로 작성 + +자바스크립트는 대표적인 고수준 언어로, 컴파일러나 인터프리터에 의해
+저수준 프로그래밍 언어, 즉 기계가 이해할 수 있는 언어로 번역되어 실행된다. + +### 컴파일 타임? + +소스코드(개발자가 작성)가 컴파일 과정을 거쳐 컴퓨터가 인식할 수 있는
+기계어 코드(바이트 코드)로 변환되어 실행할 수 있는 프로그램이 되는 과정이다. + +### 런타임? + +소스코드의 컴파일이 완료되면 프로그램이 메모리에 적재되어 실행되는데
+이 시간을 런타임이라고 하는데 즉 런타임은 컴파일 과정을 마친 응용 프로그램이
+사용자에 의해 실행되는 과정이다. + +
+
+ +## 2) 자바스크립트 런타임 + +자바스크립트 런타임은 자바스크립트가 실행되는 환경이다. + +자바스크립트 런타임의 주요 구성 요소로
+자바스크립트 엔진, 웹 API, 콜백 큐, 이벤트 루프, 렌더 큐가 있다. + +> 자바스크립트는 대표적인 인터프리터 언어로 별도의 컴파일 과정이 존재하지 않는다고 알려져 있다.
+ +> 하지만 엄밀히 말해 컴파일 단계가 존재하는데 자바스크립트를 해석하고 실행하는 역할을 하는
+> V8 엔진은 때때로 자바스크립트 코드를 최적화하기 위해 컴파일 단계를 거친다.(실행 속도 향상을 위한 목적)
+> 이 과정에서 자바스크립트 코드를 캐싱해 실행 시간을 단축시킨다. + +
+
+ +## 3) 타입스크립트의 컴파일 + +타입스크립트는 **tsc**라고 불리는 컴파일러를 통해 자바스크립트 코드로 변환된다. + +하지만, 타입스크립트는 고수준언어 -> 고수준 언어로 변환되는 것이기 때문에
+컴파일이 아닌 트랜스파일로 불리거나 소스코드 -> 다른 소스코드로 변환하는 것이기에
+소스 대 소스 컴파일러라고 지칭하기도 한다. + +> 타입스크립트 컴파일러는 소스코드를 해석해 AST를 만들고 이후 타입 확인을 거친 다음 결과 코드를 생성한다. + +
+ +### 컴파일러가 소스코드를 컴파일해 프로그램으로 실행되기까지의 과정을 알아보자! + +1. 타입스크립트 소스코드를 타입스크립트 AST로 만든다.(tsc) +2. 타입 검사기가 AST를 확인해 타입을 확인한다.(tsc) +3. 타입스크립트 AST를 자바스크립트 소스로 변환한다.(tsc) +4. 자바스크립트 소스코드를 자바스크립트 AST로 만든다.(런타임) +5. AST가 바이트 코드로 변환된다.(런타임) +6. 런타임에서 바이트 코드가 평가되 프로그램이 실행된다.(런타임) + +### AST(Abstract Syntax Tree)? + +컴파일러가 소스코드를 해석하는 과정에서 생성된 데이터 구조다.
+컴파일러는 어휘적 분석과 구문 분석을 통해 소스코드를 노드 단위의 트리 구조로 구성한다. + +### 타입스크립트 === 정적 검사기? + +타입스크립트를 컴파일타임에 에러를 발견할 수 있는 정적 검사기라고 부르는데 +컴파일타임에 타입을 검사하기 때문이다.(런타임 전 에러 발견 가능) + +
+
From d236a82ba2b54706ec473e48a9853e62e520dc0c Mon Sep 17 00:00:00 2001 From: doitchuu Date: Tue, 22 Apr 2025 01:04:13 +0900 Subject: [PATCH 2/5] =?UTF-8?q?[Docs]=206.2=20=EC=A0=95=EB=A6=AC=20?= =?UTF-8?q?=EC=99=84=EB=A3=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../seulgi.md" | 95 ++++++++++++++++++- 1 file changed, 94 insertions(+), 1 deletion(-) diff --git "a/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.2_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274\353\237\254\354\235\230_\353\217\231\354\236\221/seulgi.md" "b/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.2_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274\353\237\254\354\235\230_\353\217\231\354\236\221/seulgi.md" index 3beced8..46f1cb0 100644 --- "a/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.2_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274\353\237\254\354\235\230_\353\217\231\354\236\221/seulgi.md" +++ "b/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.2_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274\353\237\254\354\235\230_\353\217\231\354\236\221/seulgi.md" @@ -1 +1,94 @@ - +# 2. 타입스크립트 컴파일러의 동작 + +## 1) 코드 검사기로서의 타입스크립트 컴파일러 + +타입스크립트는 컴파일타임에 문법 에러와 타입 관련 에러를 모두 검출한다. + +```js +const developer = { + work() { + console.log("working"); + }, +}; + +developer.work(); +developer.sleep(); // TypeError; +``` + +> 해당 코드를 자바스크립트로 작성하는 시점에는 에러가 발생하지 않으나, 실제 실행 시 에러가 난다. + +```ts +const developer = { + work() { + console.log("working"); + }, +}; + +developer.work(); +developer.sleep(); // Property "sleep" does not exist on type "{work(): void}" +``` + +> 타입스크립트는 코드를 실행 전에 에러를 사전에 발견해 알려준다.
+> 즉, 런타임에 발생할 수 있는 문법 오류 등의 에러뿐 아니라 타입 에러도 잡을 수 있다. + +타입스크립트 컴파일러는 tsc binder를 사용하여 타입 검사를 하며, 컴파일타임에 타입 오류를 발견한다.
+타입 검사를 거쳐 코드를 안전하게 만든 이후에는 타입스크립트 AST를 자바스크립트 코드로 변환한다. + +
+
+ +## 2) 코드 변환가로서의 타입스크립트 컴파일러 + +타입스크립트 코드를 각자의 런타임 환경에서 동작할 수 있도록
+구버전의 자바스크립트로 트랜스파일한다.
+이것이 타입스크립트 컴파일러의 두 번째 역할이다. + +- 타입스크립트 컴파일러의 target 옵션을 사용하여 특정 버전의 자바스크립트 소스코드로 컴파일할 수 있다. +- 타입스크립트 컴파일러는 타입 검사를 수행한 후 코드 변환을 시작한다. +- 이때 타입 오류가 있더라도 일단 컴파일을 진행한다. + +> 타입스크립트 코드가 자바스크립트 코드로 변환되는 과정은
+> 타입 검사와 독립적으로 동작하기 때문이다.
+ +> 타입스크립트 코드 타이핑이 잘못되서 발생하는 에러도 런타임 에러로 처리된다. 자바스크립트 실행 과정에서 런타임 에러로 처리된다. + +### 다만 문제가 있다..! + +타입스크립트 소스코드에 타입 에러가 있더라도 +자바스크립트로 컴파일되어 타입 정보가 모두 제거된 후에는 +타입이 아무런 효력을 발휘하지 못한다. + +```ts +interface Square { + width: number; +} + +interface Rectangle extends Square { + height: number; +} + +type Shape = Square | Rectangle; + +function calculateArea(shape: Shape) { + // 에러! Rectangle이 타입이기 때문에 런타임은 해당 코드를 이해하지 못함 + if (shape instanceof Rectangle) { + return shape.width * shape.height; + } else { + return shape.width * shape.width; + } +} +``` + +> 타입스크립트 코드가 자바스크립트로 컴파일되는 과정에서 모든 인터페이스, 타입, 타입 구문이 제거되어 버리기 때문에 런타임에서는 타입을 사용할 수 없다. + +### 타입스크립트 컴파일러의 역할? + +1. 최신 버전의 타입스크립트 / 자바스크립트 코드를 구버전의 자바스크립트로 트랜스파일한다. +2. 코드의 타입 오류를 검사한다. + +### 바벨 (Babel)? + +ECMAScript 2015 이후의 코드를 현재 또는 오래된 브라우저와 호환되는 버전으로 변환해주는 자바스크립트 컴파일러이다. + +
+
From 407d56bd18bfef349f9a864e865455f3ed85c64d Mon Sep 17 00:00:00 2001 From: doitchuu Date: Tue, 22 Apr 2025 20:38:44 +0900 Subject: [PATCH 3/5] =?UTF-8?q?[Add]=206.2=20=EC=9D=B4=EB=AF=B8=EC=A7=80?= =?UTF-8?q?=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- assets/CH06/kind_of_symbol.png | Bin 0 -> 61034 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 assets/CH06/kind_of_symbol.png diff --git a/assets/CH06/kind_of_symbol.png b/assets/CH06/kind_of_symbol.png new file mode 100644 index 0000000000000000000000000000000000000000..e124044cd93864ccec7951732f9be5e03a25b8ad GIT binary patch literal 61034 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 z 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 z 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 T)9~UK(Cw{^l5~ya`{4fps8~w@ literal 0 HcmV?d00001 From 00551cf86d330a0e7d7dd0feac79ac4fa33e037d Mon Sep 17 00:00:00 2001 From: doitchuu Date: Tue, 22 Apr 2025 20:39:00 +0900 Subject: [PATCH 4/5] =?UTF-8?q?[Docs]=206.3=20=EC=A0=95=EB=A6=AC=20?= =?UTF-8?q?=EC=99=84=EB=A3=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../seulgi.md" | 185 +++++++++++++++++- 1 file changed, 184 insertions(+), 1 deletion(-) diff --git "a/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.3_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274\353\237\254\354\235\230_\352\265\254\354\241\260/seulgi.md" "b/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.3_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274\353\237\254\354\235\230_\352\265\254\354\241\260/seulgi.md" index 3beced8..b91a80a 100644 --- "a/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.3_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274\353\237\254\354\235\230_\352\265\254\354\241\260/seulgi.md" +++ "b/CH06_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274/6.3_\355\203\200\354\236\205\354\212\244\355\201\254\353\246\275\355\212\270_\354\273\264\355\214\214\354\235\274\353\237\254\354\235\230_\352\265\254\354\241\260/seulgi.md" @@ -1 +1,184 @@ - +# 3. 타입스크립트 컴파일러의 구조 + +타입스크립트 컴파일러가 동작하는 데 중요한 몇 가지 중요한 구성 요소가 있다. +타입스크립트 컴파일러의 구체적인 동작을 살펴보자. + +| 순서 | 단계 | 설명 | +| ---- | ------ | ----------------------------- | +| 1 | 스캐너 | .ts 토큰화 | +| 2 | 파서 | 토큰 기반 AST 생성 | +| 3 | 바인더 | AST 노드 기반 심볼 생성 | +| 4 | 체커 | AST + 심볼 기반 타입 검사 | +| 5 | 이미터 | AST + 코드 생성 기반 .js 생성 | + +> 위의 5단계를 거쳐 타입 검사와 자바스크립트 소스 변환을 진행한다. + +
+
+ +## 1) 프로그램(Program) + +타입스크립트 컴파일러는 tsc명령어로 실행된다.
+컴파일러는 tsconfig.json에 명시된 컴파일 옵션을 기반으로 컴파일을 수행한다. + +전체적인 컴파일 과정을 관리하는 프로그램 객체(인스턴스)가 생성되고,
+객체 내 컴파일할 타입스크립트 소스 파일과 소스 파일 내 임포트된 파일을 불러오는데
+가장 최초 불러온 파일을 기준으로 컴파일 과정이 시작된다. + +
+
+ +## 2) 스캐너(Scanner) + +스캐너는 타입스크립트 소스 파일을 어휘적으로 분석하여 토큰을 생성하는 역할을 한다.
+소스코드를 작은 단위로 나누어 의미 있는 토큰으로 변환하는 작업을 수행한다. + +```ts +// 코드는 스캐너에 의해 다음과 같은 토큰으로 분석된다. +const woowa = "bros"; +``` + +- ConstKeyword: const +- WhitespaceTrivia: (공백) +- Identifier: woowa +- WhitespaceTrivia: (공백) +- EqualsToken: = +- WhitespaceTrivia: (공백) +- StringLiteral: "bros" +- SemicolonToken: ; + +
+
+ +## 3) 파서(Parser) + +스캐너가 소스 파일을 토큰으로 나눠주면, 파서는 그 토큰 정보를 이용하여 AST를 생성한다. + +파서는 생성된 토큰 목록을 활용하여 구문적 분석을 수행한다. + +코드의 실질적인 구조를 노드 단위의 트리 형태로 표현하고,
+각각의 노드는 코드상의 위치, 구문 종류, 코드 내용과 같은 정보를 담는다. + +### AST? + +컴파일러가 동작하는 데 핵심 기반이 되는 자료 구조로,
+소스코드의 구조를 트리 형태로 표현한다. + +AST의 최상위 노드는 타입스크립트 소스 파일이며,
+최하위 노드는 파일의 끝 지점으로 구성된다. + +
+
+ +## 4) 바인더(Binder) + +체커 단계에서 타입 검사를 할 수 있도록 기반을 마련하는 역할은 한다.
+바인더는 타입 검사를 위해 심볼이라는 데이터 구조를 생성한다. + +심볼은 이전 단계의 AST에서 선언된 타입의 노드 정보를 저장한다. + +```ts +export interface Symbol { + flags: SymbolFlags; // Symbol flags + escapedName: string; // Name of Symbol + declarations?: Declaration[]; + // ... +} + +// src/compiler/types.ts +export const enum SymbolFlags { + NONE = 0, + FunctionScopedVariable = 1 << 0, // Variable (var) or parameter + BloackScopedVariable = 1 << 1, // A block-scoped variable (let or const) + Property = 1 << 2, // Property or enum member + EnumMember = 1 << 3, // Enum member + Function = 1 << 4, // Function + Class = 1 << 5, // Class + Interface = 1 << 6, // Interface + ... + .. + . +} +``` + +- flags 필드는 AST에서 선언된 타입의 노드 정보를 저장하는 식별자이다. +- 심볼 인터페이스의 declarations 필드는 AST 노드의 배열 형태를 보인다. + +> 바인더는 심볼을 생성하고 해당 심볼과 그에 대응하는 AST 노드를 연결하는 역할을 한다. + +```ts +type SomeType = string | number; +interface SomeInterface { + name: string; + age?: number; +} + +let foo: string = "LET"; +const obj = { + name: "이름", + age: 10, +}; + +class MyClass { + name; + age; + + constructor(name: string, age?: number) { + this.name = name; + this.age = age ?? 0; + } +} + +const arrowFunction = () => {}; +function func() {} + +arrowFunction(); +func(); + +const colin = new Class("colin"); +``` + + + +
+
+ +## 5) 체커(Checker)와 이미터(Emitter) + +### 체커? + +체커는 파서가 생성한 AST와 바인더가 생성한 심볼을 활용해 타입 검사를 수행한다. + +체커의 주요 역할은 AST의 노드를 탐색하면서
+심볼 정보를 불러와 주어진 소스 파일에 대해 타입 검사를 진행하는 것이다.
+체커의 타입 검사는 다음 컴파일 단계인 이미터에서 실행된다. + +checker.ts의 getDiagnostics() 함수를 사용해 타입을 검증하고
+타입 에러에 대한 정보를 보여줄 에러 메시지를 저장한다. + +### 이미터? + +타입스크립트 소스 파일을 변환하는 역할을 한다.
+즉, 타입스크립트 소스를 자바스크립트 파일(.js)과 타입 선언 파일(d.ts)로 생성한다. + +타입스크립트 소스 파일을 변환하는 과정에서
+개발자가 설정한 타입스크립트 설정파일을 읽어오고,
+체커를 통해 코드에 대한 타입 검증 정보를 가져온다. + +emitter.ts 소스 파일 내부의 emitFiles() 함수를 사용해
+타입스크립트 소스 변환을 진행한다. + +
+
+ +## 6) 타입스크립트의 컴파일 과정 + +1. tsc 명령어를 실행해 프로그램 객체가 컴파일 과정을 시작한다. +2. 스캐너는 소스 파일을 토큰 단위로 분리한다. +3. 파서는 토큰을 이용해 AST를 생성한다. +4. 바인더는 AST의 각 노드에 대응하는 심볼을 생성한다. 심볼은 선언된 타입의 노드 정보를 담고 있다. +5. 체커는 AST를 탐색하며 심볼 정보를 활용해 타입 검사를 수행한다. +6. 타입 검사 결과 에러가 없다면 이미터를 사용해서 자바스크립트 소스 파일로 변환한다. + +
+
From 227268bb153ce6502e2fab6fb5c51ff23c96379e Mon Sep 17 00:00:00 2001 From: doitchuu Date: Tue, 22 Apr 2025 21:43:18 +0900 Subject: [PATCH 5/5] =?UTF-8?q?[Docs]=207.1=20=EC=A0=95=EB=A6=AC=20?= =?UTF-8?q?=EC=99=84=EB=A3=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../seulgi.md" | 366 +++++++++++++++++- 1 file changed, 365 insertions(+), 1 deletion(-) diff --git "a/CH07_\353\271\204\353\217\231\352\270\260_\355\230\270\354\266\234/7.1_API_\354\232\224\354\262\255/seulgi.md" "b/CH07_\353\271\204\353\217\231\352\270\260_\355\230\270\354\266\234/7.1_API_\354\232\224\354\262\255/seulgi.md" index 3beced8..c697d7a 100644 --- "a/CH07_\353\271\204\353\217\231\352\270\260_\355\230\270\354\266\234/7.1_API_\354\232\224\354\262\255/seulgi.md" +++ "b/CH07_\353\271\204\353\217\231\352\270\260_\355\230\270\354\266\234/7.1_API_\354\232\224\354\262\255/seulgi.md" @@ -1 +1,365 @@ - +# 1. API 요청 + +## 1) fetch로 API 요청하기 + +장바구니 조회 기능을 만들기 위해 외부 데이터베이스에 접근해 +사용자가 장바구니에 추가한 정보를 호출하는 코드를 작성한다고 해보자. + +아래는 fetch 함수를 이용해 사용자가 담은 장바구니 물품 개수를 배지로 만든 예시이다. + +```tsx +const CartBadge = () => { + const [cartCount, setCartCount] = useState(0); + + useEffect(() => { + fetch("").then.((response) => response.json()).then(({cartItem} => { + setCartCount(cartItem.length); + })) + },[]); + + return ( + // 렌더링 로직 + ); +} +``` + +위의 경우처럼 구현해 다른 컴포넌트에서도 사용할 경우에
+ +백엔드에서 기능 변경을 해야해 API URL을 수정해야 한다면,
+이미 컴포넌트 내부 깊숙이 자리 잡은 비동기 호출 코드는 이런 변경 요구에 취약하다.
+
+그 외에도 커스텀 헤더, 타임아웃 설정과 같은 정책이 추가될 때마다 수정의 번거로움이 생긴다. + +
+
+ +## 2) 서비스 레이어로 분리하기 + +여러 API 변경으로 코드가 변경될 수 있다는 걸 감안해,
+비동기 호출 코드는 컴포넌트 영역에서 분리되 서비스 레이어에서 처리되어야 한다. + +단순히, fetch 함수 호출 부분을 서비스 레이어로,
+컴포넌트는 서비스 레이어 비동기 함수를 호출해 그 결과를 받아
+렌더링하는 흐름만으로는 API 요청 정책이 추가되는 것을 해결하기 어렵다. + +예를 들어, fetch함수에서 타임아웃을 설정하기 위해서는 다음 같이 구현해야 한다. + +```tsx +async function fetchCart() { + const controller = new AbortController(); + + const timeoutId = setTimeout(() => controller.abort(), 5000); + + const response = await fetch("url", { + signal: controller.signal, + }); + + clearTimeout(timeoutId); + + return response; +} +``` + +
+
+ +## 3) Axios 활용하기 + +fetch는 내장 라이브러리라 설치 필요는 없지만, 많은 기능을 사용하려면 직접 구현해야 한다. +이런 번거로움 때문에 fetch 함수를 직접 쓰는 대신 Axios 라이브러리를 사용한다. + +```tsx +const apiRequester: AxiosInstance = axios.create({ + baseURL: "url", + timeout: 5000, +}); + +const fetchCart = (): AxiosPromise => + apiRequester.get("cart"); + +const postCart = ( + postCartRequest: PostCartRequest +): AxiosPromise => + apiRequester.post("cart", postCartRequest); +``` + +### API Entry가 2개 이상일 경우 + +```tsx +const apiRequester: AxiosInstance = axios.create(defaultConfig); + +const orderApiRequester: AxiosInstance = axios.create({ + baseURL: "url", + ...defaultConfig, +}); +const orderCartApiRequester: AxiosInstance = axios.create({ + baseURL: "url", + ...defaultConfig, +}); +``` + +각 서버의 기본 URL을 호출하도록 orderApiRequester, orderCartApiRequester 같이
+2개 이상의 API 요청을 처리하는 인스턴스를 따로 구성해야 한다. + +이후, 다른 URL로 서비스 코드를 호출할 때는 각각의 apiRequester를 사용하면 된다. + +
+
+ +## 4) Axios 인터셉터 사용하기 + +서로 다른 역할을 담당하는 다른 서버이기 때문에 +requester별로 다른 헤더를 설정해줘야 하는 로직이 필요할 수 있다. + +이때, 인터셉터 기능을 사용하여 requester에 따라 비동기 호출 내용을 추가해서 처리할 수 있다.
+또한 API 에러를 처리할 때 하나의 에러 객체로 묶어서 처리할 수도 있다. + +이와 달리 요청 옵션에 따라 다른 인터셉터를 만들기 위해 빌더 패턴을 추가하여 +APIBuilder 같은 클래스 형태로 구성하기도 한다. + +> **빌더 패턴(Builder Pattern)?**
+> 객체 생성을 더 편리하고 가독성 있게 만들기 위한 디자인 패턴 중 하나다.
+> 주로 복잡한 객체의 생성을 단순화하고, 객체 생성 과정을 분리하여 객체를 조립하는 방법을 제공한다. + +다만, 이런 APIBuilder 클래스는 보일러플레이트 코드가 많다는 단점을 갖고 있기 때문에
+옵션이 다양한 경우 인터셉터를 설정값에 따라 적용하고,
+필요 없는 인터셉터를 선택적으로 사용할 수 있다는 장점도 갖고 있다. + +
+
+ +## 5) API 응답 타입 지정하기 + +API 응답 값은 하나의 Response 타입으로 묶일 수 있다. + +```ts +interface Response { + data: T; + status: string; + serverDataTime: string; + errorCord?: string; + errorMessage?: string; +} + +const fetchCart = (): AxiosPromise => + apiRequester.get < Response < FetchCartResponse >> "cart"; + +const postCart = ( + postCartRequest: PostCartRequest +): AxiosPromise => + apiRequester.post>("cart", postCartRequest); +``` + +이와 같이 서버에서 오는 응답을 통일할 때 주의할 점은
+Response 타입을 apiRequester 내에서 처리한다면
+UPDATE, CREATE 같이 응답이 없을 수 있는 API 처리가 까다로워질 수 있다. + +따라서, Response 타입은 apiRequester가 모르게 관리되어야 하고,
+해당 값에 어떤 응답이 들어있는지 알 수 없거나 값의 형식이 달라지더라도
+로직에 영향을 주지 않는 경우에는 unknown 타입을 사용하여 알 수 없는 값임을 표현한다. + +```ts +interface response { + data: { + cartItems: CartItem[]; + forPass: unknown; + }; +} +``` + +다만, 이미 설계된 프로덕트에서 쓰고 있는 값이라면 +프로트 로직에서 써야 하는 값에 대해서만 타입을 선언한 다음에 사용하는 것이 좋다. + +```ts +type ForPass = { + type: "A" | "B" | "C"; +}; + +const isTargetValue = () => (data.forPass as ForPass).type === "A"; +``` + +
+
+ +## 6) 뷰 모델 사용하기 + +새로운 프로젝트는 서버 스펙이 자주 바뀌기 때문에 +뷰 모델을 사용하여 API 변경에 따른 범위를 한정해줘야 한다. + +```tsx +interface ListResponse { + items: ListItem[]; +} + +const fetchList = async (filter?: ListFetchFilter): Promise => { + const { data } = await api + .params({ filter }) + .get("/api/get-list") + .call>(); + + return { data }; +}; + +const ListPage = () => { + const [itemCount, setItemCount] = useState(0); + const [items, setItems] = useState([]); + + useEffect(() => { + fetchList(filter).then(({items}) => { + setItemCount(items.length); + setItems(items); + }) + },[]); + + return ( + // 렌더링 로직 + ); +}; +``` + +흔히 좋은 컴포넌트는 변경될 이유가 하나뿐인 컴퍼넌트라 한다. + +API응답의 items 인자를 좀 더 정확한 개념으로 나타내기 위해
+각 역할에 맞는 컴포넌트명으로 바꾼다면 해당 컴포넌트도 수정해야 하는데
+같은 API를 사용하는 기존 컴포넌트들 모두 수정해야하는 문제가 생긴다. + +이 문제를 해결하기 위한 방법으로 뷰 모델을 도입할 수 있다. + +API 응답에는 없는 ItemCount와 같은 도메인 개념을 넣을 때도
+백엔드나 UI에서 로직을 추가하여 처리할 필요 없이 간편하게 새로운 필드를 뷰 모델에 추가할 수 있다. + +### 뷰 모델에도 문제는 있다?! + +추상화 레이어 추가는 결국 코드를 복잡하게 만들며 레이어를 관리하고 개발하는 비용이 든다. + +```tsx +interface JobListResponse { + jobItems: JobListItemResponse[]; +} + +class JobListItem { + constructor(item: JobListItemResponse) { + // JobListItemResponse => JobListItem 객체로 변환 + } +} + +class JobList { + readonly itemCount: number; + readonly items: JobListItemResponse[]; + + constructor({ jobItems }: JobListResponse) { + this.itemCount = jobItem.length; + this.items = jobItems.map((item) => new JobListItem(item)); + } +} + +const fetchJobList = async ( + filter?: ListFetchFilter +): Promise => { + const { data } = await api + .params({ filter }) + .get("/api/get-list") + .call>(); + + return new JobList(data); +}; +``` + +### 도메인의 일관성 + 코드 수정 비용의 절충안을 찾자! + +1. 필요한 곳에만 뷰 모델을 부분적으로 만들어서 사용하기 +2. 백엔드와 클라이언트 개발자가 충분히 소통 후에 개발해 API 응답 변화 줄이기 +3. 뷰 모델에 필드를 추가하기 대신에 getter 등 함수를 추가해 실제 어떤 값이 뷰 모델에 추가한 값인지 알기 쉽게 하기 + +### AI로 찾아본 각 예시들 + +1. 필요한 곳에만 뷰 모델(ViewModel)을 부분적으로 만들어서 사용하기 + +- 전체 도메인 객체를 뷰에 억지로 끼워 맞추기보다는, 필요한 정보만 추려서 가볍게 사용하자. + +```ts +// 전체 도메인 모델 +interface User { + id: number; + name: string; + email: string; + birthday: string; + createdAt: string; + updatedAt: string; +} + +// 뷰 모델 (뷰에서 필요한 정보만 선택) +interface UserProfileViewModel { + name: string; + birthday: string; +} + +// 사용처에서 가볍게 매핑 +const toUserProfileViewModel = (user: User): UserProfileViewModel => ({ + name: user.name, + birthday: user.birthday, +}); +``` + +
+ +2. API 응답 스펙의 변경을 줄이기 위해 백엔드/프론트 간 소통 강화 + +- 프론트와 백엔드가 협의해서 “이건 프론트에서 계산할게요” 또는 “백엔드가 계산해서 내려줄게요” 협의한다고 가정하자. + +```ts +{ +"price": 1000, +"discount": 100 +} + +// 클라이언트에서 totalPrice 계산 +const totalPrice = price - discount; +``` + +- 백엔드에서 계산 요청하고 응답 스펙을 바꾸지 않음 (기존 유지) +- 프론트에서는 필요한 값을 뷰 모델에서 따로 계산 + +
+ +3. 뷰 모델에 필드를 직접 추가하지 말고 함수(getter)를 통해 표현 + +- 어떤 값이 기존 도메인에서 온 값인지, 아니면 UI용 가공값인지 명확히 하자. + +```ts +interface Product { + name: string; + price: number; + discount: number; +} + +// 뷰 모델 형태로 가공 +class ProductViewModel { + constructor(private product: Product) {} + + get name() { + return this.product.name; + } + + get price() { + return this.product.price; + } + + get finalPrice() { + return this.product.price - this.product.discount; + } + + // UI에서만 사용하는 값 + get isOnSale() { + return this.product.discount > 0; + } +} +``` + +- 이 방식은 실제 데이터는 그대로 두고, 추가된 값들이 어떤 용도인지 명확하게 드러나고, +- finalPrice, isOnSale은 UI 전용이라는 게 getter로 구분되어 이해하기 쉽다. + +> 다만, 타입스크립트는 정적 검사 도구라 런타임에 API 응답의 타입 오류를 방지하려면 Superstruct, zod같은 라이브러리를 사용하면 된다. + +
+