HoC 를 통해 더 편리한 활용
방금 우리가 Container 를 만들 때 사용했던 로직을, 쉽게 재사용 할 수 있도록 HoC 를 사용한다면, 매우 편리해질 수 있습니다. useSample 이라는 함수를 만들고, 내보내주세요.
src/contexts/sample.js
import React, { Component, createContext } from 'react';
const Context = createContext(); // Context 를 만듭니다.
// Context 안에는 Provider 와 Consumer 라는게 존재합니다.
// 이 둘은, Context 를 이용하기 위해 필요한 컴포넌트들입니다.
// Consumer 는 나중에 내보내줄 때 편하도록 SampleConsumer 라고 부르도록 설정했습니다.
const { Provider, Consumer: SampleConsumer } = Context;
// Provider 에서 state 를 사용하기 위해서 컴포넌트를 새로 만들어줍니다.
class SampleProvider extends Component {
state = {
value: '기본값입니다'
}
// 여기서 actions 라는 객체는 우리가 임의로 설정하는 객체입니다.
// 나중에 변화를 일으키는 함수들을 전달해줄때, 함수 하나하나 일일히 전달하는 것이 아니라,
// 객체 하나로 한꺼번에 전달하기 위함입니다.
actions = {
setValue: (value) => {
this.setState({value});
}
}
render() {
const { state, actions } = this;
// Provider 내에서 사용할 값은, "value" 라고 부릅니다.
// 현재 컴포넌트의 state 와 actions 객체를 넣은 객체를 만들어서,
// Provider 의 value 값으로 사용하겠습니다.
const value = { state, actions };
return (
<Provider value={value}>
{this.props.children}
</Provider>
)
}
}
// :: HoC 를 사용
function useSample(WrappedComponent) {
return function UseSample(props) {
return (
<SampleConsumer>
{
({ state, actions }) => (
<WrappedComponent
value={state.value}
setValue={actions.setValue}
/>
)
}
</SampleConsumer>
)
}
}
// 내보내줍니다.
export {
SampleProvider,
SampleConsumer,
useSample
};
자, 그러면 이제 Sends 컴포넌트는 다음과 같이 작성 할 수 있습니다.
src/components/Sends.js
import React, { Component } from 'react';
import { useSample } from '../contexts/sample';
class Sends extends Component {
state = {
input: ''
}
componentDidMount() {
// 초기 값 설정
this.setState({
input: this.props.value,
})
}
handleChange = (e) => {
this.setState({ input: e.target.value });
}
handleSubmit = (e) => {
e.preventDefault();
// props로 받은 setValue 호출
this.props.setValue(this.state.input);
}
render() {
return (
<form onSubmit={this.handleSubmit}>
<input value={this.state.input} onChange={this.handleChange}/>
<button type="submit">설정</button>
</form>
);
}
}
// useSample 사용
export default useSample(Sends);
그리고, Receives 는 다음과 같이 재작성 할 수 있겠죠.
src/components/Receives.js
import React from 'react';
import { useSample } from '../contexts/sample';
const Receives = ({ value }) => {
return (
<div>
현재 설정된 값: { value }
</div>
);
};
export default useSample(Receives);
너무 간단해졌죠~?