티스토리 뷰

Development

프레그먼트(Fragments)

BELLORI 2024. 1. 25. 01:58

컴포넌트를 만들 때 아래와 같은 에러를 본 적이 있을 것이다.

 

Adjacent JSX elements must be wrapped in an enclosing tag.

Did you want a JSX fragment <>...</>?

 

만약 컴포넌트가 아래와 같이 작성이 되었다고 해보자.

const App = () ⇒ {
 return (
  <div>one</div>
  <div>two</div>;
 );
}

 

이 코드에는 문법 오류 문제가 있다.

JSX 문법으로 작성된 내용이 아래와 같이 해석이 되기 때문이다.

return (
 React.createElement('div', {}, "one")
 React.createElement('div', {}, "two")
)

VSCode 파싱 에러

 

React 컴포넌트는 하나의 최상위 엘리먼트만 렌더링을 할 수 있기 때문에 2개 이상의 엘리먼트가 감싸지지 않고 작성될 경우 에러 문구를 보여준다.

 

컴포넌트가 여러 엘리먼트를 반환하는 것은 흔한 패턴이기 때문에 항상 감싸줘야 한다.

이를 해결하기 위해 가장 일반적인 방법은 div로 묶는 방법인데 단순히 감쌀 목적으로 <div>를 사용하는 것은 적절치 않다.

그래서 이를 해결하기 위해 Fragment를 사용한다.

 

React의 Fragment는 웹 표준에서의 <template>과 같다.

웹 표준에서의 <template>도 실제 렌더링이 되지 않는 것처럼 <fragment>도 렌더링이 되지 않는다.

 

[예제]

<div>one</div>, <div>two</div> 이 두 개 요소를 렌더링 해야한다고 가정해보자.

function App() {
  return (
    <div className="app">
      <div>one</div>
      <div>two</div>
    </div>
  );
}

div 지옥이다.

만약 여기서 fragment를 사용한다면 어떻게 될까?

import { Fragment } from 'react';

function App() {
  return (
    <Fragment>
      <div>one</div>
      <div>two</div>
    </Fragment>
  );
}

 

DOM에 Fragment는 렌더링 되지 않고 JSX 문법을 지키면서 요소들을 그룹화 해서 렌더링 할 수 있다.

 

Fragment는 단축 문법을 지원하는데 위의 에러 메시지처럼 <> … </>이다.

function App() {
  return (
    <>
      <div>one</div>
      <div>two</div>
    </>
  );
}

 

단축 문법을 사용해도 이렇게 같은 결과가 나온다.

 

React에서 Fragment를 사용하는 것은 불필요한 부모 Element를 추가하지 않고 여러 Element들을 그룹화 하는데 사용되며, 공식적으로 권장되는 방법이다.

 

애초에 에러 메시지에서 Did you want a JSX fragment <>...</>? 라고 친절히 Fragment에 대한 힌트를 제공해주고 있다.