자바스크립트 상태관리 라이브러리
Node.js 모듈에서 출발
Provider : react-redux라이브러리 안에 있는 컴포넌트입니다.
- 리액트 앱에 스토어를 쉽게 연결하기 위한 컴포넌트 입니다.
combineReducer : redux모듈이 제공하는 함수이다.
- 만든 모든 리듀서들을 통합하여 하나의 리듀서로 쓰기 위한 함수이다
useSelector : redux의 state조회 (즉, 스토어에 있는 데이터들 조회)
useDispatch : 생성한 action 실행
구현 과정
1) 왼쪽은 연락처 등록하는 폼, 오른쪽은 연락처 리스트와 검색창
2) 리스트에 유저 이름과 전화번호를 추가 기능
3) 정보 저장은 배열로 저장
4) 사용자가 유저를 이름검색으로 찾을 수 있다.
import {사용하는 기능} from 'react-bootstrap';
import 'bootstrap/dist/css/bootstrap.min.css';
UI설정을 위한 코드
4. App.js 작성
import './App.css';
import {Container, Row, Col} from 'react-bootstrap';
import ContactForm from './components/ContactForm';
import ContactList from './components/ContactList';
import 'bootstrap/dist/css/bootstrap.min.css';
function App() {
return (
<div className="App">
<h1 className="title">연락처</h1>
<Container>
<Row>
<Col>
<ContactForm></ContactForm>
</Col>
<Col>
<ContactList></ContactList>
</Col>
</Row>
</Container>
</div>
);
}
export default App;
.title{
text-align: center;
}
import React from 'react';
import {Form, Button} from 'react-bootstrap';
const ContactForm = () => {
return(
<Form>
<Form.Group className="mb-3" controlId="formName">
<Form.Label>이름</Form.Label>
<Form.Control type="text" placeholder="이름을 입력해주세요."/>
</Form.Group>
<Form.Group className="mb-3" controlId="formContact">
<Form.Label>전화번호</Form.Label>
<Form.Control type="number" placeholder="전화번호를 입력해주세요."/>
</Form.Group>
<Button variant="primary" type="submit">
추가
</Button>
</Form>
);
};
export default ContactForm;
import React from 'react';
import SearchBox from './SearchBox';
import ContactItem from './ContactItem';
const ContactList = () =>{
return(
<div>
<SearchBox></SearchBox>
<ContactItem></ContactItem>
</div>
);
};
export default ContactList;
import React from "react";
import { Form, Button, Col, Row } from "react-bootstrap";
const SearchBox = () =>{
return(
<Row>
<Col lg={10}>
<Form.Control type="text" placeholder="이름을 입력해주세요." />
</Col>
<Col lg={2}>
<Button>찾기</Button>
</Col>
</Row>
);
}
export default SearchBox;
import React from 'react';
import {Row, Col} from 'react-bootstrap';
const ContactItem = () =>{
return(
<Row>
<Col lg={1}>
<img width={50} src="https://upload.wikimedia.org/wikipedia/commons/thumb/b/bc/Unknown_person.jpg/925px-Unknown_person.jpg" alt="" />
</Col>
<Col lg={11}>
<div></div>
<div></div>
</Col>
</Row>
);
};
export default ContactItem;

기능 추가를 위한 코드
10. store.js
import {createStore} from 'redux';
import reducer from './reducer/reducer';
let store = createStore(reducer);
export default store;
// 배열 만들기
let initialState = {
contactList: [],
};
//reducer는 state 와 action으로 이루어 진다.
function reducer(state = initialState, action){
// 변수 type, payload에 따라 action이 수행
const {type, payload} = action;
switch(type){
case 'ADD_CONTACT':
return{
...state,
contactList:[
...state.contactList,
{
name: action.payload.name,
phoneNumber: action.payload.phoneNumber,
},
],
};
default :
return {...state};
}
}
export default reducer;
import store from './store';
import { Provider } from 'react-redux';
root.render(
<Provider store={store}>
<App />
</Provider>
);
import React from 'react';
import {Form, Button} from 'react-bootstrap';
import { useState } from 'react';
import { useDispatch } from 'react-redux';
const ContactForm = () => {
const [name, setName] = useState('');
const [phoneNumber, setPhoneNumber] = useState(0);
// action 실행을 위한 dispatch
const dispatch = useDispatch();
const addContact = (event) => {
event.preventDefault();
dispatch({
type: 'ADD_CONTACT',
payload: { name, phoneNumber },
});
};
return(
<Form onSubmit={addContact}>
<Form.Group className="mb-3" controlId="formName">
<Form.Label>이름</Form.Label>
<Form.Control type="text" placeholder="이름을 입력해주세요."
onChange={(event) => setName(event.target.value)} />
</Form.Group>
<Form.Group className="mb-3" controlId="formContact">
<Form.Label>전화번호</Form.Label>
<Form.Control type="number" placeholder="전화번호를 입력해주세요."
onChange={(event) => setPhoneNumber(event.target.value)} />
</Form.Group>
<Button variant="primary" type="submit">
추가
</Button>
</Form>
);
};
export default ContactForm;
import React from 'react';
import SearchBox from './SearchBox';
import ContactItem from './ContactItem';
import { useSelector } from 'react-redux';
const ContactList = () =>{
//redux의 state 조회
const contactList = useSelector((state) => state.contactList);
return(
<div>
<SearchBox></SearchBox>
{contactList.map((item) => (
<ContactItem item={item}></ContactItem>
))}
</div>
);
};
export default ContactList;
15.ContactItem.js 수정
import React from 'react';
import {Row, Col} from 'react-bootstrap';
const ContactItem = ({ item }) =>{
return(
<Row>
<Col lg={1}>
<img width={50} src="https://upload.wikimedia.org/wikipedia/commons/thumb/b/bc/Unknown_person.jpg/925px-Unknown_person.jpg" alt="" />
</Col>
<Col lg={11}>
<div>{item.name}</div>
<div>{item.phoneNumber}</div>
</Col>
</Row>
);
};
export default ContactItem;
최종 실행

이름과 전화번호 작성하고 추가버튼을 누르면

여러 개를 추가하며도 잘 나오는 것을 확인 가능

오타와 대,소문자의 틀림으로 인해 많은 오류가 발생했었다. 톡히 이름이 비슷한 변수, 컴포넌트들을 사용하는 과정에서 오타가 많이 발생했고, 컴포넌트 호출하는 과정에서 대문자를 소문자를 적는 실수가 많았다. 코드를 작성할 때 다시 한번 점검하는 습관이 필요하다.
또한, 오늘 주소록을 만들면서 구현 과정을 설계하는 것이 중요하다고 느꼈다. 천천히 하나씩 진행하면서 오류도 잡기 편했고, 단계가 있기에 진행하는 부분에도 도움이 되었다. 어떤 프로젝트를 하던 설계 과정을 잘 하도록 노력하자