학습내용
다음 그림의 키워드를 참고하여, 하나하나 뿌시도록 해야겠다.
바닐라 JS가 아닌 React를 사용하는 이유
React는 facebook에서 개발하였으며, 공식문서에 가보면 "사용자 인터페이스를 만들기 위한 Javascript 라이브러리"라고 한다.
- 선언형
바닐라 js로 구현할 경우 거쳐야할 단계를 전부 작성해야한다.
반면, React를 활용한다면 목표로 하는 UI만 정의만 하면 React가 알아서 단계를 수행한다.
또한, 뷰만 설계하여 코드의 가독성과 유지보수성을 향상 시킨다.
리액트 - 선언형
바닐라js - 명령형
- 컴포넌트 기반 아키텍쳐
코드의 모듈성과 재사용성 향상
- 가상 DOM 활용
브라우저의 리플로우, 리페인트 과정을 최소화 할 수 있다!
실시간으로 다수의 사용자가 이용하고 즉각 업데이트 해야하는 트위터나 증권앱을 예시로 들 수 있겠다.
cf. 리액트를 사용해야 하는이유
라이브러리 vs 프레임워크
- 라이브러리
특정 기능을 수행하는 도구 모음
제어의 흐름이 전적으로 개발자에게 있다. 능동적으로 라이브러리를 호출하여 사용가능하다.
- 프레임워크
더 큰 구조적 패턴을 제공한다.
제어의 역전 개념이 적용되어 프레임워크에 제어 흐름을 넘기고 틀 안에서 수동적으로 동작한다.
cf. 리액트를 프레임워크라 분류하는 사람들도 있던데??
=> 위에서 공식문서에 리액트는 라이브러리라고 나왔다고 했다.
하지만 프레임워크라 칭하는 사람들도 있어서 항상 궁금했던 차에 알아본 결과,
리액트 자체는 UI 를 만드는데 집중된 라이브러리이나, 여러가지 툴들과 결합하여 프레임워크처럼 활용할 수 있는 확장 가능성 때문에 때로는 경계가 모호하여 그런 것 같다.
JSX
jsx는 javascript에 XML을 추가하여 확장한 문법으로 공식적인 자바스크립트 문법은 아니라고 한다.
jsx를 사용하는 이유?
=> 자바스크립트 코드 안에서 UI 작업을 하면 더 간결하고 가독성 면에서도 좋다.
import './App.css';
import React from 'react';
function App() {
return (
<div>Hello World</div>
);
}
export default App;
다른방식으로는
createElement를 사용하는 방식이 있는데 확실이 가독성 면에서 좋지는 않은 것 같다.
import './App.css';
import React from 'react';
function App() {
return (
React.createElement('div', null, 'Hello World')
);
}
export default App;
Vite
jsx 문법 브라우저에서 사용 불가
⇒ 따라서 해당 문법을 브라우저에서 실행 가능한 코드로 변환해야함.
⇒ + 코드를 최적화 시키고(변수함수 이름 줄이고, 공백)
⇒ Vite와 같은 별도 도구를 사용하는 이유이다.
요즘 Vite가 많이 활용하는 핵심적인 이유??
번들링 과정 없이 ES 모듈을 직접 브라우저로 보내서 빠른 개발 환경 지원(이를 위해 HMR을 지원)
프로덕션 빌드에서는 Rollup이라는 번들러를 사용해서 빌드생성함. 즉, 빌드 도구의 역할도 수행
Webpack
Webpack은 여러 개의 모듈(html, css, js, image 등)을 하나의 javascript 파일로 묶어주는 모듈 번들러이다.
=> CRA(create-react-app)을 사용하면 내부적으로 웹팩을 사용하기 때문에 자동으로 구성이 된다.
Props
key와 value로 이루어진 객체형태이다.
리액트에서는 컴포넌트에 커스텀 속성을 props라는 이름으로 추가하게 해준다.
상위 컴포넌트에서 하위 컴포넌트를 호출할 때
import Post from "./Post";
const PostList = () => {
return <Post name='bae' />;
};
이렇게 하위 컴포넌트로 props를 전달할 수 있다. (React 특성 - 단방향 데이터 흐름)
하지만, 이렇게만 끝내버리면 리액트 입장에서는 name 속성을 어디에 뿌려야할지 알 수가 없다. 리액트에게 해당 속성을 어떻게 처리할지도 알려줘야 한다.
즉, 호출되는 대상 컴포넌트(자식컴포넌트)에도 Props 인자를 설정해야한다.
const Post = (props) => {
return (
<li className={classes.post}>
<p className={classes.author}>{props.author}</p>
<p className={classes.text}>{props.body}</p>
</li>
);
};
핵심
- 부모컴포넌트에서 자식컴포넌트로만 props 전달이 가능
- 자식컴포넌트는 props 인자를 활용하여 부모컴포넌트에 접근
- 자식 컴포넌트는 props를 직접 수정할 수 없으며, 오로지 읽기만 가능
CSS 모듈
CRA나 vite로 생성한 프로젝트에서 제공되는 기능이다.
html, jsx에서 활용하는 클래스 이름이 자동으로 고유한 클래스 이름으로 변환됨. => 이름 충돌이 나지 않는 장점이 있다!
import시에 .module을 붙이면 CSS모듈을 활용하겠다고 vite나 cra에 알리는 것임. (아래 import문 참고)
import classes from ‘./Post.module.css';
⇒ 이렇게하면 나중에 css 클래스 이름이 고유한 이름으로 변환된다.
classes라는 것은 객체가 되고, 해당 css파일에 정의해둔 클래스들은 이 객체의 프로퍼티 네임이 된다.
useState
컴포넌트 내에서 변수 값을 변경해도, 리액트는 변경사실을 감지하지 못한다.
왜???
=> 일반 변수는 React 상태관리 시스템 외부에 있다. 따라서 컴포넌트의 한 렌더링 사이클 내에서만 존재한다.
★ 리액트의 상태관리와 렌더링 프로세스
- 초기 렌더링
처음 마운트 시, JSX 코드를 실행하여 UI 렌더링한다.
- 상태 변경
useState()에서 반환된 setter함수가 호출되면 상태가 업데이트 된다.
=> 리액트가 이를 감지한다.
- 컴포넌트 리렌더링
상태가 변경되면 해당 컴포넌트의 렌더링 함수가 다시 실행되어 새로운 UI가 생성된다.
- 화면 업데이트
기존 UI와 비교하여 실제 DOM을 최소한으로 업데이트한다. => 성능면에서 중요
상태 올리기
=> 이부분이 조금 어려웠던 부분인 것 같아서 내일 다시 추가로 학습을 해봐야겠다.
해당 폼을 모달창으로 만들기
다음 두가지 방법중 모달 컴포넌트로 구현하는 것을 실습해봤다.
- CSS 구현
NewPost 컴포넌트에 적용된 폼스타일을 모달처럼 보이도록 변경
- 모달 컴포넌트를 별도로 구현
안에 있는 여러 콘텐츠를 오버레이 스타일로 만들기.
=> 복잡한 형태의 웹사이트에서 이 방법이 좋다고 한다.
전달받은 props를 통해 속성에 접근할 때,
const Post = (props) => {
return (
<li className={classes.post}>
<p className={classes.author}>{props.author}</p>
<p className={classes.text}>{props.body}</p>
</li>
);
};
=> 이렇게 사용할 수도 있지만, ‘props.’ 를 굳이 사용할 필요없이
const Modal = ({ children }) => {
return (
<>
<div className={classes.backdrop} />
<dialog open className={classes.modal}>
{children}
</dialog>
</>
);
};
_객체구조분해_를 사용해 특정 속성에 바로 접근이 가능하다.
children 프로퍼티가 참조하는것은
사용자 정의 컴포넌트의 본문 태그안에 담겨 전달되는 콘텐츠이다!
cf. dialog 태그와 open속성.
open속성의 기본값은 true이고, 이게 있어야 다이얼로그 요소가 자동으로 화면에 표시된다.
children 속성을 사용하는 이유
다른 컴포넌트를 래핑할 수 있는 래퍼 컴포넌트를 만들어 사용할수있다.
멘토링
Q) React에서 컴포넌트를 스타일링 하는 여러가지 방법들에는
CSS모듈, styled-components, emotion, 기타 프레임워크(부트스트랩, tailwind, sass)등이 있다고 알고 있습니다.
각각의 장단점이 있겠지만, 유지보수나 클린코드 면에서 멘토님의 취향을 반영한 의견이 궁금합니다!
A) CSS를 작업할때는 개인적으로 조금 내려놓는 편이긴 하다.
HTML이나, 컴포넌트 작성에 조금더 유지보수면에서 신경을 쓰는편이고,
그래도 emotion이 여러가지 타협점을 찾거나 하기에는 좋았던 것 같다.라고 하셨던 것 같다.
아마 emotion이 컴포넌트의 재사용성을 높이면서도 스타일링의 유연성을 유지할 수 있다는 말씀이신 건가 싶다?!