일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | 5 | 6 | 7 |
8 | 9 | 10 | 11 | 12 | 13 | 14 |
15 | 16 | 17 | 18 | 19 | 20 | 21 |
22 | 23 | 24 | 25 | 26 | 27 | 28 |
29 | 30 | 31 |
Tags
- Design Patterns
- Spring Boot
- tool
- elasticsearch
- Spring
- MySQL
- java
- php
- AWS
- Gradle
- Spring Batch
- ReactJS
- Git
- JVM
- redis
- devops
- javascript
- it
- 맛집
- ubuntu
- db
- IntelliJ
- Web Server
- laravel
- jsp
- springboot
- jenkins
- linux
- 요리
- Oracle
Archives
- Today
- Total
아무거나
React + Typescript 에서 FC 를 사용하면 안되는 이유 본문
반응형
React + Typescript 에서 FC 를 사용하면 안되는 이유
먼저 React17 이하에서는 아래와 같이 React.FC 사용이 가능하며 React18 이상부터는 없어졌다고 한다.
참고
그러나 FC 를 사용하는건 좋은 방법이 아니며 CRA 에서는 여러가지의 이유로 FC 를 없애야 한다고 이슈가 올라왔었고 반영되었으며 이유는 아래 설명을 참고하자.
- children 을 암시적으로 가지고 있다.
- FC 를 이용한 컴포넌트 props 는 type 이 ReactNode 인 Children 을 암묵적으로 가지게 되며 이는 꼭 타입스크립트에 한정하지 않더라도 안티패턴이라고 한다. 왜냐하면 children 이라는 암묵적이었던 키워드는 자식노드가 필요한지 아닌지의 의도를 명확하게 드러낼 수 없다는, 타입의 관점에서는 꽤 크리티컬한 문제를 갖고 있었다. (타입에 자식 노드가 꼭 필요한 컴포넌트에 자식 노드를 넣지 않았을 경우 혹은 그 반대의 경우를 타입으로 잡아내지 못한다는 단점이 존재
즉, 암묵적으로 선언됐던 children 을 명시적으로 컴포넌트에 맞게 선언을 하자는 취지라고 한다.
) - 예시
- AS-IS (react 를 업데이트하면 하기 주석의 에러가 표시)
const Example: React.FC = ({ children }) => <div>{children}</div>; // "TS2339: Property 'children' does not exist on type '{}'."
- TO-BE (자식 컴포넌트가 꼭 필요하다는 의도를 타입으로 정의)
type Props = { children: React.ReactNode; // children?: React.ReactNode; 자식노드가 옵셔널한경우 }; const Example: React.FC<Props> = ({ children }) => <div>{children}</div>;
- AS-IS (react 를 업데이트하면 하기 주석의 에러가 표시)
- FC 를 이용한 컴포넌트 props 는 type 이 ReactNode 인 Children 을 암묵적으로 가지게 되며 이는 꼭 타입스크립트에 한정하지 않더라도 안티패턴이라고 한다. 왜냐하면 children 이라는 암묵적이었던 키워드는 자식노드가 필요한지 아닌지의 의도를 명확하게 드러낼 수 없다는, 타입의 관점에서는 꽤 크리티컬한 문제를 갖고 있었다. (타입에 자식 노드가 꼭 필요한 컴포넌트에 자식 노드를 넣지 않았을 경우 혹은 그 반대의 경우를 타입으로 잡아내지 못한다는 단점이 존재
- 제네릭을 지원하지 않는다.
- 하기 제네릭 컴포넌트를 작성한 내용을 보자
// 제네릭 컴포넌트 작성 type GenericComponentProps<T> = { prop: T; callback: (t: T) => void; }; const GenericComponent = <T>(props: GenericComponentProps<T>) => { /*...*/ };
// 허용 X (T 를 넘겨줄 방법이 없기 때문에 FC 에서 허용되지 않는다) const GenericComponent: React.FC</* ??? */> = <T>(props: GenericComponentProps<T>) => {/*...*/}
- 하기 제네릭 컴포넌트를 작성한 내용을 보자
- 네임스페이스 패턴을 이용할 때 불편하다.
- 하기 코드와 같이 연관성 있는 컴포넌트에 대해 네임스페이스 패턴을 적용하는 것은 매우 많이 쓰이는 방법이다.
<Select> <Select.Item /> </Select>
- FC 를 사용하고도 상기 패턴을 적용할 수 있지만 많이 불편해진다.
// FC를 사용할 때 const Select: React.FC<SelectProps> & { Item: React.FC<ItemProps> } = ( props ) => { /* ... */ }; Select.Item = (props) => { /*...*/ };
// FC를 사용하지 않을 때 const Select = (props: SelectProps) => { /* ... */ }; Select.Item = (props: ItemProps) => { /*...*/ };
- 하기 코드와 같이 연관성 있는 컴포넌트에 대해 네임스페이스 패턴을 적용하는 것은 매우 많이 쓰이는 방법이다.
- FC 를 사용하면 코드가 더 길어진다.
const C1: React.FC<CProps> = (props) => {}; // FC 사용 O const C2 = (props: CProps) => {}; // FC 사용 X
참고
- https://emewjin.github.io/
- https://blog.shiren.dev/
반응형
'Javascript & HTML & CSS > reactjs' 카테고리의 다른 글
Scroll Down 구현 (0) | 2022.07.29 |
---|---|
Fragments (0) | 2022.07.29 |
useRef 를 사용한 직접 DOM 제어 (0) | 2022.07.29 |
react + typescript 체크박스 컨트롤 예제 (0) | 2020.05.11 |
Fragments 정의 (0) | 2020.05.08 |
Comments