https://jframework.tistory.com/23
이어서..
리액트 앱을 만들다 보면 컴포넌트 간의 값을 전달해야 하는 상황이 발생한다.
리액트에서는 부모가 자식 컴포넌트에 단일 객체 형태로 값을 전달할 수 있다.
이 객체를 리액트에서는 Props(Properties) 라고 커뮤니케이션 용어로 사용한다.
예제로 변수 name에 값을 전달해보도록 하자
여기서 한 가지 주의할 부분은 Props는 부모가 자식에게만 전달 할 수 있다.
자식이 부모에게 값을 전달하는 것은 불가능하다는 뜻이다.
위 예시로 보면 Body 컴포넌트에 Porps를 전달하려면 부모인 App 컴포넌트에서만 전달이 가능하다.
App.js를 수정해보자
// src/App.js
import './App.css';
import Header from './components/Header';
import Body from './components/Body';
import Footer from './components/Footer';
function App() {
const name = "리액트앱";
return (
<div className="App">
<Header />
{/* //Header 렌더링 추가 */}
<Body name={name}/>
<Footer />
</div>
);
}
export default App;
// src/components/Body.js
import './Body.css';
const Body = (props) => {
const numA = 1;
const numB = 2;
const strA = 'Hello';
const strB = 'World';
const boolA = true;
const boolB = false;
const objA = { a: 1, b: 2, c: 3 };
console.log('프로퍼티: ', props);
return (
<div className="body">
<h1>Body props => {props.name}</h1>
<h2>{numA} + {numB} = {numA + numB}</h2>
<h2>{strA} + {strB} = {strA + strB}</h2>
<h2>{ (boolA || boolB) ? '참입니다.' : '거짓입니다.'}</h2>
<h2> {objA.a} :: {JSON.stringify(objA)} </h2>
</div>
);
}
export default Body;
값이 잘 전달되는 모습을 볼 수 있다.
전달되는 객체는 props 가 default 값인 부분도 확인 할 수 있다.
그럼 Props에 여러 개의 값을 전달해보자
// src/App.js
import './App.css';
import Header from './components/Header';
import Body from './components/Body';
import Footer from './components/Footer';
function App() {
const name = "리액트앱";
return (
<div className="App">
<Header />
{/* //Header 렌더링 추가 */}
<Body name={name} addr={"평택"}/>
<Footer />
</div>
);
}
export default App;
// src/components/Body.js
import './Body.css';
const Body = (props) => {
const numA = 1;
const numB = 2;
const strA = 'Hello';
const strB = 'World';
const boolA = true;
const boolB = false;
const objA = { a: 1, b: 2, c: 3 };
console.log('프로퍼티: ', props);
return (
<div className="body">
<h1>Body props => {props.name} {props.addr}</h1>
<h2>{numA} + {numB} = {numA + numB}</h2>
<h2>{strA} + {strB} = {strA + strB}</h2>
<h2>{ (boolA || boolB) ? '참입니다.' : '거짓입니다.'}</h2>
<h2> {objA.a} :: {JSON.stringify(objA)} </h2>
</div>
);
}
export default Body;
스프레드 연산자로 여러 개의 값 전달하기
부모 컴포넌트에서 Props로 전달할 값이 많아지면, 값을 모두 태그에 명시해야하는 불편함이 생기며,
가독성도 좋아지지 않는다.
어떻게하면 해결할 수 있을까?
이때 자바스크립트에서 제공하는 스프레드 연산자를 활용하여 전달 가능하다.
아래 예시를 살펴보자
// src/App.js
import './App.css';
import Header from './components/Header';
import Body from './components/Body';
import Footer from './components/Footer';
function App() {
const name = "리액트앱";
const addr = "평택";
const arrayNum = [1, 2, 3, 4, 5];
const BodyPorps = {
name: name,
addr: addr,
arr : arrayNum
}
return (
<div className="App">
<Header />
{/* //Header 렌더링 추가 */}
<Body {...BodyPorps}/>
<Footer />
</div>
);
}
export default App;
App 컴포넌트에서 Body 컴포넌트로 Props를 전달할 값을 객체 BodyPorps로 생성하고, 이를 스프레드 연산자를 통하여 Body 속성으로 Props를 전달하였다.
아래와 같이 새로운 BodyProps 를 선언 후 객체안에 여러 obj 타입을 넣어서 자식 컴포넌트에게 객체를 전달되는지를 확인하자
// src/App.js
import './App.css';
import Header from './components/Header';
import Body from './components/Body';
import Footer from './components/Footer';
function App() {
const name = "리액트앱";
const addr = "평택";
const arrayNum = [1, 2, 3, 4, 5];
const BodyProps = {
name: name,
addr: addr,
arr : arrayNum,
favorList: [
{ id: 1, name: '사과', price: 1000 },
{ id: 2, name: '바나나', price: 2000 },
{ id: 3, name: '포도', price: 3000 },
{ id: 4, name: '귤', price: 4000 },
{ id: 5, name: '배', price: 5000 },
]
}
return (
<div className="App">
<Header />
{/* //Header 렌더링 추가 */}
<Body {...BodyProps}/>
<Footer />
</div>
);
}
export default App;
// src/components/Body.js
import './Body.css';
// const Body = (props) => {
const Body = ({name, addr, arr, favorList}) => {
const numA = 1;
const numB = 2;
const strA = 'Hello';
const strB = 'World';
const boolA = true;
const boolB = false;
const objA = { a: 1, b: 2, c: 3 };
return (
<div className="body">
<h1>Body props</h1>
<h5>{numA} + {numB} = {numA + numB}</h5>
<h5>{strA} + {strB} = {strA + strB}</h5>
<h5>{ (boolA || boolB) ? '참입니다.' : '거짓입니다.'}</h5>
<h5> {objA.a} :: {JSON.stringify(objA)} </h5>
<h5> {name} :: {addr} :: {arr} :: {arr.length}</h5>
<h5>{favorList.length} :: {favorList.map(i => i.name + ', ')}</h5>
</div>
);
}
Body.defaultProps = {
arr: [],
favorList:[{id:'1', name:'사과', price:'1000'},]
}
export default Body;
위와 같이 구조분해 할당을 이용하여 {name, addr, arr, favorList} 를 변수로 받아서 값을 가져왔다.
혹시 App 컴포넌트에서 Props 값 중 값이 null 이거나 전달되지 않으면 어떻게 될까?
당연히 properties 속성에 해당 변수가 없다고 뜰 것이다.
이런 경우에 대비하여 defaultProps를 사용한다.
defaultProps를 통하여 디폴트 값을 설정할 수 있기 때문에 방어코드를 통한 오류를 방지할 수 있을 뿐만 아니라
좀 더 유연한 코드를 작성할 수도 있다.
//자식 컴포넌트가 데이터를 전달받지 못하였을 때를 대비한 defaultProps
Body.defaultProps = {
arr: [],
favorList:[{id:'1', name:'사과', price:'1000'},]
}
여기까지 하다보면 따라오다보면 데이터 만의 값 전달이 아닌 컴포넌트 전달할 수 있으면 얼마나 좋을까?
라는 생각을 하는 사람도 있을 것이다.
물론 가능하다.
지금까지는 컴포넌트 간에 문자나 숫자, object 등의 값을 전달해보았지만 리액트는 컴포넌트를 전달할 수도 있다.
'프로그래밍 > react' 카테고리의 다른 글
1-9) [리액트 기초] useEffect 사용법 (0) | 2024.01.30 |
---|---|
1-8) [리액트 기초] Ref 사용방법 (0) | 2024.01.29 |
1-7) [리액트 기초] 여러 개의 입력 상태 관리하기 (1) | 2024.01.29 |
1-6) [리액트 기초] 컴포넌트 이벤트 호출 (1) | 2024.01.24 |
1-4) [리액트 기초] JSX란? JSX 문법 (1) | 2024.01.24 |
1-3) [리액트 기초] 기본 기능 다루기 - 함수 컴포넌트 생성 (0) | 2024.01.24 |
1-2) [리액트 기초] 기본 기능 다루기 (0) | 2024.01.23 |
1-1) [리액트 기초] 리액트 앱 최초 만들기 (0) | 2024.01.23 |
댓글