컴포넌트 간 통신

김지윤·2022년 7월 4일
0

React

목록 보기
6/6

1. 하위컴포넌트 변경

  • A 의 button 를 클릭하여 E 를 변경하려면
    A -> E 까지 모두 Props로 내려서 처리해야함
import {useState} from "react";

const A = () => {
    const [value, setValue] = useState("아직 안바뀜");

    const handleOnClick = (e) => {
        setValue("E의 값을 변경");
    };

    return (
        <div>
            <B value={value}/>
            <button onClick={handleOnClick}>E의 값을 바꾸기</button>
        </div>
    );
};

const B = ({value}) => {
    return (
      <div>
          <p>여긴 B</p>
          <C value={value}/>
      </div>
    );
}

const C = ({value}) => {
    return (
        <div>
            <p>여긴 C</p>
            <D value={value}/>
        </div>
    );
}

const D = ({value}) => {
    return (
        <div>
            <p>여긴 D</p>
            <E value={value}/>
        </div>
    );

}

const E = ({value}) => {
    return (
        <div>
            <p>여긴 E</p>
            <h3>{value}</h3>
        </div>
    );
}

export default A;

2. 상위 컴포넌트를 변경하기

  • E 의 button 를 클릭하여 A 의 p 를 변경하려면
import {useState} from "react";

const A = () => {
    const [value, setValue] = useState("아직 안바뀜");
    return(
        <div>
            <p>{value}</p>
            <B setValue={setValue}/>
        </div>
    );
};

const B = ({setValue}) => {
    return(
        <div>
            <p>여긴 B</p>
            <C setValue={setValue} />
        </div>
    )
}

const C = ({setValue}) => {
    return(
        <div>
            <p>여긴 C</p>
            <D setValue={setValue}/>
        </div>
    )
}

const D = ({setValue}) => {
    return(
        <div>
            <p>여긴 D</p>
            <E setValue={setValue}/>
        </div>
    )
}

const E = ({setValue}) => {
    const handleOnClick = () => {
        setValue("A 의 값을 변경");
    }
    return(
        <div>
            <p>여긴 E</p>
            <button onClick={handleOnClick}>클릭</button>
        </div>
    )
}

export default A;
  • 실제 프로젝트에서 해당 부분들을 전달하는 방식으로 구현은 너무 힘들다.
    위와 같은 문제점을 해결하고자 아래 사항들이 나오게됨.
  1. Context
  • 하위 컴포넌트 전체에 데이터를 공유하는 법
    • 데이터를 Set 하는 놈
      • 가장 상위 컴포넌트 => 프로바이더 데이터를 Get 하는 놈
    • 모든 하위 컴포넌트에서 접근 가능
      • 컨슈머로 하는 방법
      • 클래스 컴포넌트의 this.context 로 하는 방법
      • 펑셔널 컴포넌트의 useContext 로 하는 방법
  • 데이터를 Set 하기
    • 일단 컨텍스트를 생성한다.
    • 컨텍스트, 프로바이더를 사용한다.
    • value를 사용
// context를 생성한다.
import {createContext} from "react";
const PersonContext = createContext();
export default PersonContext;

index.js

import React from 'react';
import ReactDOM from 'react-dom/client';
import './index.css';
import App from './App';
import reportWebVitals from './reportWebVitals';
import PersonContext from "./contexts/PersonContext";

const root = ReactDOM.createRoot(document.getElementById('root'));

// 최상위 컴포넌트를 Context로 쌓아서 넣어준다.
const persons = [
    {id: 0, name: "Mark", age: 30},
    {id: 1, name: "Hanna", age: 28}
];

// value를 해당 객체를 너헝준다.
root.render(
  <React.StrictMode>
      <PersonContext.Provider value={persons}>
          <App />
      </PersonContext.Provider>
  </React.StrictMode>
);

// If you want to start measuring performance in your app, pass a function
// to log results (for example: reportWebVitals(console.log))
// or send to an analytics endpoint. Learn more: https://bit.ly/CRA-vitals
reportWebVitals();
  • 데이터를 Get 하기 (1) - Consumer
    • 컨텍스트를 가져온다.
    • 컨텍스트 컨슈머를 사용한다.
    • value를 사용
// 컨텍스트를 가져온다
import PersonContext from "../contexts/PersonContext";

const Example1 = () => {
  // 컨텍스트 컨슈머를 사용한다.
    return(
        <PersonContext.Consumer>
      // value를 사용
            {(persons) => (<ul>
                {persons.map((person, idx) => (
                    <li key={idx}>{person.name}</li>
                ))}
            </ul>)}
        </PersonContext.Consumer>
    );
}

export default Example1;
  • 데이터를 Get 하기 (2) - class
    • static contextType에 컨텍스트를 설정한다.
    • this.context => value 이다.
import React from "react";
import PersonContext from "../contexts/PersonContext";

export default class Example2 extends React.Component{
    // 여러개를 지정할 수 없음
  	// static contextType 컨텍스트를 설정
    //static contextType = PersonContext;

    render() {
      // 사용한다.
        const persons = this.context;
        return(
            <ul>
                {persons.map((person, idx) => (
                    <li key={idx}>{person.name}</li>
                ))}
            </ul>
        );
    }
}

Example2.contextType = PersonContext;
  • 데이터를 Get 하기 (3) - functional
    • useContext로 컨텍스트를 인자로 호출한다.
    • useContext의 리턴이 value이다.
import PersonContext from "../contexts/PersonContext";
import {useContext} from "react";

const Example3 = () => {
  // Hook으로 컨텍스트를 가져온다.
    const persons = useContext(PersonContext);
  // 사용한다.
    return(
        <ul>
            {persons.map((person, idx) => (
                <li key={idx}>{person.name}</li>
            ))}
        </ul>
    );
}

export default Example3;
profile
윤의 개발자 블로그

0개의 댓글