처음 만난 리액트 문서


5.2 Props에 대해 알아보기

5.2.1 Props의 개념

이제 리액트 컴포넌트의 입력으로 들어가는 props에 대해서 자세히 배워보도록 하겠습니다. 먼저 propsprop 뒤에 복수형을 나타내는 알파벳 s를 붙여서 prop이 여러개인 것을 의미합니다. 그럼 prop은 무엇일까요? propproperty라는 영어단어를 줄여서 쓴 것입니다. property는 '재산'이라는 뜻도 있지만, '속성', '특성'이라는 뜻도 갖고 있습니다. 리액트에서는 속성이라는 뜻으로 사용된다고 볼 수 있습니다. 그렇다면 무엇의 속성일까요? 바로 리액트 컴포넌트의 속성입니다. 앞에서 봤던 붕어빵 그림을 다시 한 번 보도록 하겠습니다.

컴포넌트와 Element

앞에서 리액트 컴포넌트는 이 그림에서 붕어빵틀에 해당된다고 했었는데, 그렇다면 여기에서 props가 나타내는 것은 뭘까요? props는 붕어빵에 들어가는 재료를 의미한다고 볼 수 있습니다. 같은 붕어빵이라도 어떤 재료를 넣느냐에 따라서 다른 맛이 나죠. 아래 그림을 하나 더 살펴보도록 하겠습니다.

컴포넌트와 Props

이 그림에서는 총 세 개의 각기 다른 붕어빵이 등장합니다. 옛날에는 붕어빵 안에 무조건 팥이 들어갔지만, 요즘은 전혀 그렇지 않습니다. 붕어빵이라고 다 같은 붕어빵이 아니죠. 팥을 넣으면 팥 붕어빵이 되고, 슈크림을 넣으면 슈크림 붕어빵이 되고, 고구마를 넣으면 고구마 붕어빵이 됩니다. 여기서 붕어빵에 들어가는 재료가 바로 props입니다. 같은 붕어빵 틀에서 구워져서 나온 것이기 때문에 모양은 붕어 모양으로 같지만, 속을 뜯어보면 안에 들어있는 재료가 다르고 색깔도 각기 다릅니다. 이처럼 props는 같은 리액트 컴포넌트에서 눈에 보이는 글자나 색깔 등의 속성을 바꾸고 싶을 때 사용하는 컴포넌트의 속재료라고 생각하면 됩니다.

페이스북 그룹의 컴포넌트

컴포넌트와 props가 실제로 사용되는 예시를 설명하기 위해서 앞에 나왔던 에어비앤비 첫 화면을 다시 한 번 보겠습니다. 여기서 위에 빨간색으로 표시되어 있는 부분에서는 여행할 지역들을 나타내고 있습니다. 자세히 보면 모두 모서리가 둥근 사각형 모양에 상단에는 그림이 배경으로 들어가 있고, 하단에는 색깔로 된 배경과 글자가 들어가 있는 형태라는 것을 알 수 있습니다. 모양만 놓고 보면 모두 동일한 모양을 갖고 있는 것이죠. 하지만 안에 들어있는 그림과 색상, 글자, 거리들은 모두 다릅니다.

각기 다른 Elements

이번엔 해당 부분만 떼어와서 조금 더 자세히 살펴보도록 하겠습니다. 총 네 개의 여행지가 존재하는데, 우리가 살펴봤던대로 모두 같은 모양인 것을 볼 수 있습니다. 그리고 배경 이미지와 하단 영역의 색상과 글자는 다 다릅니다. 이것을 리액트 컴포넌트의 관점에서 보면, 네 가지 모두 다 같은 컴포넌트에서 생성된 element라고 할 수 있습니다. 하지만 각기 다른 이미지와 텍스트를 갖고 있는 것은 어떻게 설명할 수 있을까요? 여기서 나오는 것이 바로 props입니다.

첫 번째 '서울' 여행지에는 서울.jpg라는 이름의 이미지가 배경으로 들어갔고, 하단 영역의 배경색으로는 #de3151이라는 컴퓨터에서 색을 나타내는 HEX값이 들어갔습니다. 그리고 가운데 제목으로는 서울, 거리로는 2km가 들어갔습니다. 마찬가지로 두 번째 여행지 아이템인 '인천'에는 인천.jpg라는 이미지가 배경으로, 하단 배경색으로는 #cc2d4a, 제목으로는 인천, 그리고 거리는 29km가 들어갔습니다. 당연히 세 번째, 네 번째 여행지 아이템도 마찬가지 형태로 되어 있습니다.

여기서 이러한 컴포넌트의 모습과 속성을 결정하는 것이 바로 props입니다. props컴포넌트에 전달할 다양한 정보들을 담고있는 자바스크립트 객체입니다. 우리가 컴포넌트에 어떤 데이터를 전달하고 전달된 데이터에 따라 다른 모습의 element를 화면에 렌더링하고 싶을 때, 해당 데이터를 props에 넣어 전달하는 것이죠. 이 그림을 앞에서 살펴봤던 세 가지 맛의 붕어빵 그림과 비교해서 본다면 더 쉽게 이해가 될 것입니다. 여기서 props의 개념에 대해서 확실히 이해하고 다음으로 넘어가도록 합시다.

5.2.2 Props의 특징

이번에는 props의 중요한 특징에 대해서 알아보도록 하겠습니다. props의 중요한 특징은 읽기 전용(Read-Only) 이라는 것입니다. 읽을 수만 있다는 것은 값을 변경할 수 없다는 말이기도 하죠. props의 값들은 리액트 컴포넌트가 element를 생성하기 위해서 사용하는 값들입니다. 그런데 이 값들이 element를 생성하는 도중에 갑자기 바뀌어 버리면 제대로 된 element가 생성될 수 없겠죠. 마치 붕어빵을 굽는 중간이나 다 구워진 이후에 속재료를 바꿀 수 없는 것과 마찬가지입니다. 다 구워진 이후에 속재료를 바꾸려면 붕어빵의 배를 갈라야 하는데 그렇게 하면 제대로된 상품으로 판매할 수가 없겠죠.

그렇다면 다른 props의 값으로 element를 생성하려면 어떻게 해야 할까요? 새로운 값을 컴포넌트에 전달하여 새로 element를 생성하면 됩니다. 이 과정에서 element가 다시 렌더링이 되는 것이죠. 여기서 잠시 자바스크립트 함수의 속성에 대해서 짚고 넘어가보도록 하겠습니다. 아래 그림을 먼저 보도록 하죠.

Pure function

여기에 sum()이라는 이름을 가진 함수가 하나 있습니다. 이 함수는 ab라는 두 개의 파라미터를 받아서 그 둘의 합을 리턴하는 함수입니다. 이 함수에서는 ab라는 파라미터의 값을 변경하지 않고 있습니다. 그리고 ab라는 파라미터 집합의 값이 같은 경우에는 항상 같은 값을 리턴 할 것입니다. 우리는 이러한 함수를 'Pure하다'라고 합니다. 말 그대로 함수가 순수하다는 뜻인데, 이 말은 입력값을 변경하지 않으며, 같은 입력값에 대해서는 항상 같은 출력값을 낸다는 의미입니다. 그렇다면 함수가 순수하지 않은 경우도 한 번 살펴볼까요?

Impure function

여기에 withdraw라는 함수가 있습니다. 이 함수는 accountamount라는 파라미터를 받아서 accounttotal이라는 값에서 amount를 빼는 함수입니다. 한글로 쉽게 이야기 하면 계좌에서 출금을 하는 함수인데, 은행계좌 정보와 총액을 파라미터로 받아서 계좌의 현재 총 잔액을 나타내는 total에서 출금할 금액인 amount를 빼는 것입니다. 자, 여기서 이 함수는 입력으로 받은 파라미터 account의 값을 변경했습니다. 이런 경우 우리는 'Impure하다'라고 합니다. 순수하지 않다는 뜻이죠.

props에 대해서 설명하다가 갑자기 왜 Pure함수와 Impure함수에 대해서 설명을 하는지 의아했을 겁니다. 이것은 리액트 컴포넌트의 정의와 관련이 되어 있기 때문입니다. 아래 문장은 리액트 공식 문서에 나오는 컴포넌트의 특징을 설명한 문장입니다.

All React components must act like pure functions with respect to their props.

이 문장을 한글로 해석해보면 아래와 같습니다.

모든 리액트 컴포넌트는 그들의 props에 관해서는 Pure 함수 같은 역할을 해야한다.

이렇게 써놓아도 아직 이해하기가 어렵죠? 이해하기 쉽게 풀어서 쓰면 아래와 같습니다.

모든 리액트 컴포넌트는 props를 직접 바꿀 수 없고, 같은 props에 대해서는 항상 같은 결과를 보여줄것!

앞에서 리액트 컴포넌트가 자바스크립트의 함수와 같은 개념이라고 설명했었죠? 그렇기 때문에 리액트 컴포넌트에 입력으로 들어오는 props는 자바스크립트 함수의 파라미터와 같습니다. 함수가 Pure하다는 것은 함수의 입력값인 파라미터를 바꿀 수 없다는 의미를 포함하고 있기 때문에, 리액트 컴포넌트에서는 props를 바꿀 수 없다는 의미가 됩니다. 그리고 Pure함수는 같은 입력값에 대해서는 항상 같은 결과를 보여줘야 하기 때문에, 리액트 컴포넌트 관점에서는 같은 props에 대해서는 항상 같은 결과를 보여줘야 한다는 의미가 됩니다. 여기서의 결과는 리액트 element가 되겠죠.

조금 어려운 내용이 나와서 당황하셨을 수도 있겠습니다. 정리하면, 리액트 컴포넌트의 props는 바꿀 수 없고, 같은 props가 들어오면 항상 같은 element를 리턴해야 한다고 기억하면 됩니다.

5.2.3 Props 사용법

props는 어떻게 사용할까요? 앞에서 props가 컴포넌트에 전달할 다양한 정보를 담고 있는 자바스크립트 객체라고 설명했습니다. 그렇다면 컴포넌트에 props라는 객체를 전달하기 위해서는 어떻게 해야 하는지 살펴보도록 하겠습니다.

먼저 JSX를 사용하는 경우에는 아래 코드와 같이 키와 값으로 이루어진 키-값 쌍의 형태로 컴포넌트에 props를 넣을 수 있습니다.

function App(props) {
    return (
        <Profile
            name="소플"
            introduction="안녕하세요, 소플입니다."
            viewCount={1500}
        />
    );
}

이 코드에는 App컴포넌트가 나오고, 그 안에서 Profile컴포넌트를 사용하고 있습니다. 여기서 Profile컴포넌트에 name, introduction, viewCount라는 세 가지 속성들을 넣어주었습니다. 이렇게 하면 이 속성의 값들이 모두 Profile컴포넌트에 props로 전달되며, props는 아래와 같은 형태의 자바스크립트 객체가 됩니다.

{
    name: "소플",
    introduction: "안녕하세요, 소플입니다.",
    viewCount: 1500
}

여기서 한 가지 눈여겨 봐야 할 부분은 각 속성에 값을 넣을 때 중괄호를 사용한 것과 사용하지 않은 것의 차이입니다. nameintroduction에 들어간 문자열은 중괄호를 사용하지 않았고, viewCount에 들어간 정수는 중괄호를 사용했습니다.

우리가 앞에서 JSX에 대해서 배울 때 '중괄호를 사용하면 무조건 자바스크립트 코드가 들어간다' 라고 배웠습니다. 그래서 마찬가지로 props에 값을 넣을 때에도 문자열 이외에 정수, 변수, 그리고 다른 컴포넌트 등이 들어갈 경우에는 중괄호를 사용해서 감싸주어야 합니다. 물론 문자열도 중괄호로 감싸도 상관은 없습니다. 그래서 중괄호를 사용하게 되면 아래와 같이 props의 값으로 컴포넌트도 넣을 수 있습니다.

function App(props) {
    return (
        <Layout
            width={2560}
            height={1440}
            header={
                <Header title="소플의 블로그입니다." />
            }
            footer={
                <Footer />
            }
        />
    );
}

이렇게 하면 Layout컴포넌트의 props로는 정수값을 가진 width, height와 리액트 엘리먼트로 header, footer가 들어오게 됩니다. 이처럼 JSX를 사용하는 경우에는 간단하게 컴포넌트에 props를 넣을 수 있습니다.

그렇다면 JSX를 사용하지 않는 경우에는 어떻게 props를 넣어줘야 할까요? 우리가 앞에서 리액트 엘리먼트에 대해서 배울 때 리액트의 createElement()함수에 대해서 배웠습니다. createElement()함수는 아래와 같은 형태로 사용했습니다.

React.createElement(
    type,
    [props],
    [...children]
)

여기서 두 번째 파라미터가 바로 props입니다. 여기에 자바스크립트 객체를 넣으면 그게 곧 해당 컴포넌트의 props가 됩니다. 위에 나왔던 Profile컴포넌트를 JSX를 사용하지 않고 코드를 작성하면 아래와 같이 될 것입니다.

React.createElement(
    Profile,
    {
        name: "소플",
        introduction: "안녕하세요, 소플입니다.",
        viewCount: 1500
    },
    null
);

타입은 컴포넌트의 이름인 Profile이 들어가고, props로 자바스크립트 객체가 들어갔습니다. 그리고 마지막으로 하위 컴포넌트가 없기 때문에 children에는 null이 들어갔습니다. 앞에서 리액트로 개발을 할 때는 무조건 JSX를 사용하는 것이 좋다고 설명했습니다. 그렇기 때문에 이 코드는 참고만 하고, 실제로 props를 사용할 때는 위에 나왔던 JSX를 사용하는 형태로 사용하기 바랍니다.


마지막 업데이트: 2025년 08월 26일 02시 47분

이 문서의 저작권은 이인제(소플)에 있습니다. 무단 전재와 무단 복제를 금합니다.

On this page