섹션 16. Mini Projects
1강. (실습) 미니 블로그 기획, 프로젝트 생성 및 필요한 패키지 설치
소스코드 모음
https://github.com/soaple/mini-blog
GitHub - soaple/mini-blog: 소플의 처음 만난 리액트 실습 프로젝트
소플의 처음 만난 리액트 실습 프로젝트. Contribute to soaple/mini-blog development by creating an account on GitHub.
github.com
프로젝트 : 미니 블로그 기획하기
개발을 시작하기 전에 정해야 할 것들
- 항상 어떤 제품을 개발하기 전에는 기획과 필요한 기능, 전체 디자인에 대해서 간단하게나마 정리 필요
미니 블로그에 필요한 기능
- 글 목록 보기 기능(리스트 형태)
- 글 보기 기능
- 댓글 보기 기능
- 글 작성 기능
- 댓글 작성 기능
1. (실습) 프로젝트 생성하기
2. (실습) 필요한 패키지 설치
<이번 프로젝트에서 사용할 패키지>
- react-router-dom v6
- 리액트 앱에서 페이지 전환을 위해 사용하는 패키지
- 거의 모든 리액트 앱에 들어가는 필수이기 때문에 잘 기억할 것 - styled-components v5
- 스타일링을 위한 라이브러리
- --save : 지금 설치하는 패키지들을 package.json 파일이 관리하는 의존성 목록에 저장하겠다는 의미
- 한 번에 두 개의 패키지를 동시에 설치하는 명령어임
따로따로 설치하고 싶으면 하나씩 입력해서 하면 됨
- -> npm install --save react-router-dom
- -> npm install --save styled-components
설치를 확인하려면 package.json 파일에 들어가서 확인하면 됨
dependencies에 두 개가 설치된 것을 확인할 수 있음
- dependencies : 이 애플리케이션에 필요한 패키지들, 의존성 목록을 나타냄
- 의존성을 추가하면 나중에 다른 사람이 이 프로젝트를 실행하려고 할 때 어떤 패키지들이 필요한지 일일이 확인할 필요 없이 npm install만 하면 됨. --save 옵션을 적극적으로 활용할 것
2강. (실습) 주요 컴포넌트 및 폴더 구성하기
컴포넌트는 재사용이 가능한 형태로 최대한 작게 쪼개서 개발하는 것이 중요
그래야 컴포넌트를 재사용해서 다른 컴포넌트를 빠르게 개발할 수 있기 때문
필요한 컴포넌트가 정해지면 각 컴포넌트에 이름을 지어줘야 한다. 이를 위해 각 요소에 대해 영어 이름이 필요
글 : post
댓글 : comment
각 기능에 필요한 Component
- 글 보기 기능(리스트 형태)
- PostList, PostListItem - 글 보기 기능
- Post - 댓글 보기 기능
- CommentList, CommentListItem - 글 작성 기능
- PostWrite - 댓글 작성 기능
- CommentWrite
1. (실습) 폴더 구성하기
폴더를 구성하는 이유는 각 컴포넌트들을 적당한 폴더에 모아서 관리함으로써 개발의 편의와 향후 유지 보수가 용이하게 하기 위함
다른 개발자와의 협업을 생각하면 보편적으로 많이 쓰이는 방식으로 구성하는 것이 좋다.
React 컴포넌트가 재사용 가능할 경우 종류별로 모아놓거나 각 페이지에서만 사용하고 딱히 재사용될 일이 없는 경우에는 각 페이지별로 폴더를 만들고 그 안에 모아놓음
3강. (실습) UI 컴포넌트 및 List 컴포넌트 구현하기
UI컴포넌트 : 버튼, 텍스트 입력 등 사용자가 직접 입력을 할 수 있게 해주는 컴포넌트를 말함
- 프로젝트 설계 : 탑다운 방식으로 큰 그림을 먼저 그리고, 이후에 작은 부분을 구체화
- 프로젝트 구현 : 바텀업 방식으로 작은 부분부터 구현한 이후에 작은 부분을 모아 큰 부분을 완성
그래서 큰 컴포넌트를 개발하기 전에 먼저 작은 UI 컴포넌트부터 구현하는 것
필요한 UI Component
- 버튼
- 텍스트 input
1. (실습) Button 컴포넌트 만들기
- 버튼은 따로 만들 필요 없이 그냥 HTML에서 제공하는 버튼 태그를 사용해도 됨
- 별도의 리액트 컴포넌트로 만드는 이유는, 버튼의 스타일을 변경하고 버튼에 들어갈 텍스트도 props로 받아서 좀 더 쉽게 사용할 수 있게 하기 위함
- 부가적인 기능도 추가 가능
UI 폴더에 Button.jsx 파일을 만들고 버튼 함수 컴포넌트 생성
- styled component를 사용해서 버튼 태그에 스타일을 입힌 StyledButton 컴포넌트 만듦
- 버튼 컴포넌트에서 props로 받은 title이 버튼 목록에 표시되도록 해줌
- props로 받은 onClick은 StyledButton의 onClick에 넣어줌으로써 클릭 이벤트를 상위 컴포넌트에서 받을 수 있게 함
2. (실습) TextInput 컴포넌트 만들기
TextInput 컴포넌트는 사용자로부터 텍스트를 입력받을 수 있게 해주는 컴포넌트
보통 입력을 받을 때 input 태그를 사용하지만, 여기에서는 여러 줄에 걸친 텍스트를 입력받아야 하기 때문에 textarea 태그를 사용
UI폴더에 TextInput.jsx 파일을 만들고 컴포넌트 생성
- Button 컴포넌트와 동일하게 Styled 컴포넌트를 사용해서 Textarea 태그에 스타일을 입힌 styled.textarea 컴포넌트 생성
- TextInput 컴포넌트의 props로는 높이 설정을 위한 height, 입력된 값을 표시하기 위한 value, 변경된 값을 상위 컴포넌트로 전달하기 위한 onChange
3. (실습) List 컴포넌트 구현하기
List 컴포넌트들은 앞에서 생성한 폴더 중 List 폴더에 들어가게 됨
1) PostListItem 컴포넌트 만들기
- PostList 컴포넌트가 아닌 PostListItem 컴포넌트를 먼저 구현하는 이유는 PostList 컴포넌트에서 PostListItem 컴포넌트를 필요로 하기 때문임
- 따라서, 작은 컴포넌트들을 먼저 구현하고 이후에 그것을 사용하는 큰 컴포넌트를 구현하는 것
list 폴더에 PostListItem 컴포넌트 생성
- title 텍스트 이용, props로 받은 post 객체에 들어있는 title 문자열 표시
2) PostList 컴포넌트 만들기
맵함수를 사용하여 글의 개수만큼 PostListItem 컴포넌트를 생성한다는 점이 다른 컴포넌트와 좀 다름
- 앞에서 만든 PostListItem 컴포넌트를 사용하기 위해 import
- PostList 컴포넌트의 props로 받은 post라는 배열에는 post 객체들이 들어있음
- 이 post 배열의 맵 함수를 이용하여 각 post 객체에 대해 PostListItem 컴포넌트를 만들어서 렌더링
4. (실습) CommentListItem 컴포넌트 만들기
스타일이 약간 다르다는 걸 제외하고는 PostListItem 컴포넌트와 거의 동일
- props에서 comment 객체 하나만 사용
- comment 객체에는 사용자가 작성한 댓글 내용이 들어 있음
- 이를 styled 컴포넌트를 통해 만든 ContentText라는 컴포넌트를 이용해서 화면에 표시
- 글은 클릭이 가능했지만 댓글은 별도로 클릭하는 기능이 없기 때문에 onClick 이벤트를 처리하지 않아도 됨
5. (실습) CommentList 컴포먼트 만들기
PostList 컴포넌트와 거의 동일
반복적으로 렌더링하는 아이템이 CommentListItem 컴포넌트라는 점을 제외하고는 동일
- CommentList 컴포넌트의 props로는 comments라는 배열이 들어오게 됨
- 이 배열에는 comment 객체들이 들어 있으며 이 배열에 map 함수를 사용해서 각 댓글 객체를 CommentListItem 컴포넌트로 넘겨서 화면에 댓글을 표시함
4강. (실습) 가짜 데이터 만들기
DB와 서버를 구축하는 부분까지 다룰 수 없으니 가짜 데이터 사용
직접 글과 댓글을 남기려면 별도의 DB를 구축하고 서버 API도 개발해야 함
또한, 서버 API와 리액트 애플리케이션을 연동하는 작업도 해야 함
<미리 만들어둔 데이터>
https://github.com/soaple/mini-blog/blob/master/src/data.json
scr 폴더에 data.json 파일을 만들고 github에서 가져온 가짜 데이터를 붙여 넣음
- JSON : JavaScript Object Notation
- 서버와의 통신에서 가장 많이 사용되는 데이터 유형
5강. (실습) Page 컴포넌트 구현 및 각 페이지별 경로 구성하기
UI컴포넌트, List 컴포넌트, Data까지 모두 준비 완료
컴포넌트들과 데이터를 모아서 Page 컴포넌트를 구현해 보는 것이 목적
1. (실습) MainPage 만들기
지금 만들 미니 블로그에 사용자가 처음 접속했을 때 보게 될 페이지
리액트에서는 페이지 또한 하나의 컴포넌트 (MainPage 컴포넌트 라는 말을 쓸 것임)
- MainPage 컴포넌트에서는 글 작성 버튼과 글 목록을 보여주어야 함
- 버튼 컴포넌트를 이용해서 글 작성하기 페이지로 이동할 수 있음
- PostList 컴포넌트를 이용하여 글 목록을 표시
- 페이지 이동을 위해 react-router-dom에 useNavigate 훅을 사용
메인 페이지는 컴포넌트를 모아놓은 수준으로 굉장히 단순한데, 이것이 컴포넌트 기반으로 개발하는 리액트의 장점
2. (실습) PostWritePage 만들기
글 작성을 위한 페이지를 PostWritePage 컴포넌트로 구현
MainPage 컴포넌트와 마찬가지로 이미 만들어둔 컴포넌트들을 조립해서 제작
- PostWritePage 컴포넌트는 두 개의 state를 가지고 있음
- 1) 글의 제목을 위한 state
- 2) 글의 내용을 위한 state
- 두 개의 state 모두 useState 훅을 이용하여 선언 - 실제 화면에 나타나는 부분은 TextInput 컴포넌트를 사용해서 글의 제목과 내용을 각각 입력받을 수 있도록 구성
- 화면 하단에는 버튼 컴포넌트를 사용하여 글 작성 버튼 삽입
3. (실습) PostViewPage 만들기
글을 볼 수 있게 해주는 컴포넌트이기 때문에 글과 댓글을 보여주어야 하며, 댓글 작성 기능도 있어야 함
- PostViewPage 컴포넌트에서는 먼저 props로 전달받은 글의 아이디를 이용해서 전체 데이터에서 해당되는 글을 찾음
- 찾은 글의 제목, 내용, 댓글을 화면에 렌더링하고 그 아래에는 TextInput 컴포넌트와 버튼 컴포넌트를 이용해 댓글을 작성할 수 있도록 UI를 제공
100% 에러나겠군
4. (실습) 각 페이지별 경로 구성하기
모든 페이지 컴포넌트 구현 완료
페이지 컴포넌트들을 실제 웹브라우저에서 보이도록 각 경로에 매핑해 주는 작업이 필요
우리가 어떤 사이트를 탐색할 때, 주소 입력란을 보면 사이트의 각 페이지를 이동함에 따라 경로가 바뀜
- 메인 도메인 : facebook.com
- 패스 : /games, /places
- 리액트에서는 react-router-dom이라는 패키지를 이용해서 각 경로에 따라 다른 컴포넌트를 보여주도록 만듦
react-router-dom v6
- React를 위한 라우팅 라이브러리
- route : 노선, 경로
- routing, 라우팅 : 사용자가 원하는 경로로 보내는 과정
- 이러한 라우팅을 쉽게 구현할 수 있도록 React 컴포넌트 형태로 제공해 주는 라이브러리
react-route-dom을 이용해 라우팅을 구성하기 위해서 사용하는 기본적인 컴포넌트는 브라우저 라우터, 라우츠, 라우트로 총 3가지(Router, Routes, Route)
- BrowserRouter 컴포넌트 : 웹브라우저에서 React 라우터를 사용하여 라우팅을 사용할 수 있도록 해주는 컴포넌트
- 웹브라우저의 히스토리는 사용자가 탐색한 페이지들의 방문 기록이 저장
- 뒤로 가기 버튼은 이 히스토리를 이용해서 이전 페이지가 어디인지 찾아서 해당 페이지로 이동하는 것
- 히스토리를 이용해서 경로를 탐색할 수 있게 해주는 컴포넌트
- Routes, Route 컴포넌트 : 실제로 라우팅 경로를 구성할 수 있게 해주는 컴포넌트
- Routes
- 여러 개의 Route를 children으로 가진다. - Route
- Routes 컴포넌트의 하위 컴포넌트로서 패스와 엘리먼트라는 props를 갖고 있다.
- 패스 : 경로
- 엘리먼트 : 경로가 일치할 경우 렌더링 할 리액트 엘리먼트
- 사용자가 주소창에 새로운 경로를 입력하거나 웹사이트 내에서 경로 이동이 일어나게 되면 routes 컴포넌트는 하위 children으로 갖고 있는 route 컴포넌트 중에서 현재 경로와 가장 일치하는 경로를 찾아 해당되는 엘리먼트를 반환하게 됨 그러면 사용자에게 보이는 화면이 바뀌게 됨
- 경로값이 없이 사이트 메인으로 접속하게 되면 index라는 prop를 가진 route로 routing 됨
- 메인 페이지 컴포넌트가 렌더링 되어 보이게 됨
/places로 접속하면 place page 컴포넌트가
/games로 접속하면 games page 컴포넌트가 렌더링 되어 나오게 됨
useNavigate()
페이지 간 이동하게 하는 훅
useNavigate 훅의 호출 결과로 나오는 navigate 함수의 파라미터로 이동할 패스를 넣어주면 된다.
<참고. react-route-dome 자세한 내용>
Home v6.21.1 | React Router
I'm on v5 The migration guide will help you migrate incrementally and keep shipping along the way. Or, do it all in one yolo commit! Either way, we've got you covered to start using the new features right away.
reactrouter.com
<느낀 점>
일단 뭔가 많이 만들어 놓긴 했는데 100% 에러가 나고, 어떻게 잡아야 할지 엄두가 안 난다. 무서운 느낌이다.
어? 금지!
'JavaScript' 카테고리의 다른 글
0029. JavaScript 공부하기4 - 함수(Function), 배열(Array), 객체(Object) (1) | 2024.01.03 |
---|---|
0028. JavaScript 공부하기3 - 반복문(while, for, break, continue) (1) | 2024.01.03 |
0027. JavaScript 공부하기2 - 연산자, 부정, 부등호, 조건문, Boolean (Feat. 잘못된 코딩 공부순서) (1) | 2024.01.02 |
0026. JavaScript 공부하기 1 - 크롬 개발자 도구, 콘솔, 숫자와 문자, 변수 (Feat. 생활코딩) (2) | 2024.01.02 |
0026. Front-end 공부하기17 - Project 실습(2), 코드 에러잡기 전쟁 (0) | 2024.01.02 |