
JSX는 JavaScript 파일에서 HTML과 유사한 마크업을 작성할 수 있게 해주는 JavaScript용 확장 문법이다. 컴포넌트를 작성하는 다른 방법이 있지만 대부분의 React 개발자는 JSX의 간결함을 선호하고 대부분의 코드베이스에서 이를 사용한다.


웹은 HTML, CSS와 JavaScript로 만들어졌다. 수년 동안 웹 개발자는 컨텐츠를 HTML, 디자인을 CSS, 로직은 JavaScript로 벼로 별도의 파일에 보관했다. 컨텐츠는 HTML 내부에 마크업되었지만 페이지의 로직은 JavaScript에서 별도로 존재했다.
하지만 웹이 점점 더 interactive해지고 로직이 점점 더 컨텐츠를 결정했다. JavaScript가 HTML을 담당했다. 이것이 리액트에서 렌더링 로직과 마크업이 같은 위치, 즉 컴포넌트에 함께 존재하는 이유이다.

버튼의 렌더링 로직과 마크업을 함께 유지하면 수정할 때마다 서로 동기화가 잘 유지된다. 반대로 버튼의 마크업과 사이드 바의 마크업과 같이 관련되지 않은 세부 정보는 서로 격리되어 있어 둘 중 하나를 스스로 변경하는 것이 더 안전하다.
각 리액트 컴포넌트는 리액트가 브라우저에 렌더링하는 일부 마크업을 포함할 수 있는 JavaScript함수이다. 리액트 컴포넌트는 JSX라는 구문 확장을 사용하여 해당 마크업을 나타낸다. JSX는 HTML과 비슷해 보이지만 조금 더 엄격하고 동적 정보를 나열할 수 있다. 이를 이해하는 가장 좋은 방법은 일부 HTML 마크업을 JSX 마크업으로 변환하는 것이다.
💡 NoteJSX와 리액트는 변개의 두가지 이다. 함께 사용되는 경우가 많지만 서로 독립적으로 사용할 수 있다.
JSX는 구문 확장이고 리액트는 JavaScript 라이브러리이다.
(완전히 유효한) HTML이 있다고 가정한다.
<h1>Hedy Lamarr's Todos</h1>
<img
src="https://i.imgur.com/yXOvdOSs.jpg"
alt="Hedy Lamarr"
class="photo"
>
<ul>
<li>Invent new traffic lights
<li>Rehearse a movie scene
<li>Improve the spectrum technology
</ul>
그리고 컴포넌트에 넣고 싶어한다.
export default function TodoList() {
return (
// ???
)
}
그대로 복사하여 붙여넣으면 작동하지 않는다.
export default function TodoList() {
return (
// This doesn't quite work!
<h1>Hedy Lamarr's Todos</h1>
<img
src="https://i.imgur.com/yXOvdOSs.jpg"
alt="Hedy Lamarr"
class="photo"
>
<ul>
<li>Invent new traffic lights
<li>Rehearse a movie scene
<li>Improve the spectrum technology
</ul>
);
}

JSX과 HTML보다 더 엄격하고 규칙이 몇 가지 더 많기 때문이다. 위의 오류 메시지를 읽으면 마크업을 수정하도록 안내하거나 아래 안내를 따를 수 있다.
💡 Note대부분의 경우 리액트의 화면 오류 메시지는 문제가 있는 위치를 찾는데 도움이 된다. 막히면 읽어봐라
컴포넌트에서 여러 요소를 반환하려면 하나의 부모 태그로 감싸라
예를 들어 <div>를 사용할 수 있다.
<div>
<h1>Hedy Lamarr's Todos</h1>
<img
src="https://i.imgur.com/yXOvdOSs.jpg"
alt="Hedy Lamarr"
class="photo"
>
<ul>
...
</ul>
</div>
<div> 대신에 <> 와 </> 를 사용할 수도 있다.
Fragment라고 하며, Fragment를 사용하면 브라우저 HTML 트리에 흔적을 남기지 않고 항목을 그룹화 할 수 있다.
💡 Deep Dive여러 JSX 태그를 묶는 이유
JSX는 HTML처럼 보이지만 내부적으로 일반 JavaScript 객체로 변환된다. 배열로 묶지않고는 함수에서 두 객체를 반환할 수 없다. 이는 두 개의 JSX태그를 다른 태그나 Fragment로 묶지 않고 반환할 수 없는 이유를 설명한다.
JSX에서는 태그가 명시적으로 닫혀있어야 한다. <img> 와 같은 자동 닫힘 태그는 <img /> 가 되어야 하고 <li>orange 는 <li>orange</li> 로 작성되어야 한다.
Hedy Lamarr의 이미지와 목록 항목이 닫힌 모습이다.
<>
<img
src="https://i.imgur.com/yXOvdOSs.jpg"
alt="Hedy Lamarr"
class="photo"
/>
<ul>
<li>Invent new traffic lights</li>
<li>Rehearse a movie scene</li>
<li>Improve the spectrum technology</li>
</ul>
</>
JSX는 JavaScript로 바뀌고 JSX로 작성된 속성은 JavaScript 객체의 키가 된다. 컴포넌트에서 이러한 속성을 변수로 읽어들이고 싶을때가 많다. 그러나 JavaScript에는 변수 이름에 제한이 있다. 예를 들어 이름에 dash를 포함하거나 class와 같은 예약어를 사용할 수 없다.
리액트에서 많은 HTML과 SVG 속성이 camelCase로 작성되는 이유이다. 예를 들어 stroke-width 대신 strokeWidth 를 사용한다. class는 예약어이므로 리액트에서는 해당 DOM 속성의 이름을 따라 className을 대신 작성한다.
<img
src="https://i.imgur.com/yXOvdOSs.jpg"
alt="Hedy Lamarr"
className="photo"
/>
💡 Pitfall
역사적인 이유로 aria-* 및 data-* 속성은 dash가 있는 HTML로 작성된다.
기존 마크업에서 이러한 모든 속성을 변환하는 것은 지루할 수 있다. 기존 HTML 및 SVG를 JSX로 변환하는 변환기를 사용하는 것이 좋다. 변환기는 실제로 매우 유용하지만 JSX를 편안하게 직접 작성할 수 있도록 진행 상황을 이해하는 것은 여전히 가치가 있다.
export default function TodoList() {
return (
<>
<h1>Hedy Lamarr's Todos</h1>
<img
src="https://i.imgur.com/yXOvdOSs.jpg"
alt="Hedy Lamarr"
className="photo"
/>
<ul>
<li>Invent new traffic lights</li>
<li>Rehearse a movie scene</li>
<li>Improve the spectrum technology</li>
</ul>
</>
);
}
이제 JSX가 존재하는 이유와 구성 요소에서 JSX를 사용하는 방법을 알았다.
글 잘 봤습니다.