폴더 구조에 관한 고민
본격적인 프로젝트 진행을 앞두고 여러가지 고민에 빠졌는데, 그 중 하나는 어떻게 폴더 구조(디렉토리 구조)를 설계할 것인가에 대한 고민이다.
우선 현재까지 팀원들과 이야기하면서 사용할 기술 스택에 대한 고민은 어느 정도 해소된 상태이다.
- 타입 스크립트를 사용하자.
- 필자가 싸피코피 프로젝트를 진행하며 타입스크립트를 프로젝트에 처음 적용해봤는데, 오류와 안정성 측면에서 도움을 많이 받아 TS 도입을 강하게 주장했다.
- Tailwind를 사용하자.
- 역시 이전 프로젝트를 진행하며 Tailwind를 사용했는데 module.css 파일이 아닌 방식을 사용하니 CSS코드 작성 간에 Context Switching 문제에서 벗어날 수 있었고, 주요 클래스만 암기해두면 굉장히 빠른 속도로 작업을 할 수 있었다.
- 또한, 프론트 팀원 중 이전 전공으로 디자인을 했던 팀원이 있어, Figma를 사용함에 있어서 플러그인이나 dev 툴 등을 이용해 코드를 뽑아냈을 때 Tailwind로 바로 사용 가능하다는 점에서 Tailwind를 도입하기로 하였다.
- Zustand를 사용하자.
- 쉬운 사용 방법과 트렌트로 인해 선택하였다. 대부분의 팀들이 Zustand 또는 Recoil 사용을 계획 중인 것으로 알고 있는데, 마침 Zustand를 학습해보고 싶은 시점이었는데 팀원들과 생각이 일치했다.
- 다만 전역 상태는 꼭 필요한 경우에만 사용하고, middleware에 대한 부분도 어느 정도 학습을 해야한다고 생각한다.
기술 스택에 대한 고민은 대충 정리되었고, 본격적으로 프로젝트 시작을 하기 전에 초기 설정을 진행하는 중에 디렉토리 구조를 어떻게 설정할지에 대한 고민이 생겼다.
사실 최근에 Next.js의 Page Router나 App Router 방식에 자주 사용하다보니 React-router-dom 의 사용법이 갑자기 낯설게 느껴지기도 했다(…)
어쨌든, 내가 기존에 사용하던 폴더 구조는 src/pages 폴더에 각 페이지 view 컴포넌트를 정의해두고, 각 페이지에서 사용하는 컴포넌트는 src/components/pages 폴더에서 각 페이지 폴더를 만들어서 사용하곤 했다.
(사실 Vue를 배웠을 때 사용하던 구조를 그대로 사용하고 있었다.)
├── src/
│ │
│ ├── components/
│ │ ├── common/ // 공통 컴포넌트
│ │ ├── home/ // home 페이지에서 사용하는 컴포넌트
│ │ └── about/ // about 페이지에서 사용하는 컴포넌트
│ ├── pages/
│ │ ├── Home.js
│ │ └── About.js
│ ├── App.js
│ └── ...
혼자 개발할 때는 사실 나만 알아볼 수 있으면 되니까, 폴더 구조 같은건 크게 신경쓰지 않지만 팀 단위 프로젝트의 경우 아무리 기능별, 도메인별 등으로 분업해서 작업한다고 하더라도, 어느 정도의 형식화 된 구조를 갖출 필요성이 있다.
나는 우선 위에서 언급했던 방식을 사용한 경험을 떠올리며 login, about 페이지 등이 view와 components로 분리되어 있으니 페이지 자체와 페이지 내에서 사용하는 컴포넌트의 구분을 명확히 할 수 있다고 이야기했다.
팀원들과 소통을 해본 결과, 다들 나와 비슷한 방법을 주로 사용하긴 했지만 이번엔 도메인 또는 기능별로 디렉토리를 구성하고 해당 도메인 디렉토리 내에 page와 components, test 등을 구성하기로 했다.
관심사를 도메인별로 나누고, 특정 도메인 디렉토리 내에선 해당 도메인과 관련된 모든 폴더와 코드를 확인할 수 있도록 한 것이다.
요즘 대규모 프로젝트에서 유행하는 FSD 구조 등에 대해서도 이야기 했는데, 우선 리액트 프로젝트에 익숙하지 않은 팀원이 있고, FSD구조 처럼 복잡한 구조를 가질 만큼의 기능이 많지 않을 것이라 판단했다.
(개인적으론 FSD 구조에서 feature 를 유지하는 이유를 아직 잘 모르겠다. 굳이..? 라는 생각..)
아무튼 팀원들과 이야기 해본 결과 도메인 혹은 기능별 디렉토리를 구성하게 될 것 같고(상세하겐 더 상의해봐야 할 것 같다), 이를 위해 대략적인 디렉토리 구조를 작성해봤다.
아직은 설계 단계라 명확하게 폴더별 역할이 지정되어 있지는 않지만, 대략적인 의도는 아래와 같다.
- apis
- 백엔드 API와의 통신을 담당하는 코드가 위치한다.
- common
- UI 컴포넌트와 같이 공통으로 사용되는 컴포넌트가 위치한다.
- 일부 페이지들에서만 사용되는 컴포넌트를 공통으로 뺄 것인가에 대한 고민이 남아있다.
- routes
- 다들 vue-router의 구조에 익숙하기에 최대한 비슷하게 설정해봤다.
- routes/index.tsx는 아래와 같다. 단순히 라우팅 처리를 하는 말 그대로 index 파일이다.
import React from 'react'; import { BrowserRouter, Route, Routes } from 'react-router-dom'; import App from '../App'; const Router: React.FC = () => { return ( <BrowserRouter> <Routes> <Route path="/" element={<App />} /> </Routes> </BrowserRouter> ); } export default Router;
- utils
- 특정 포맷팅 함수나 로직을 담당하는 코드가 위치한다.
- 현재는 auth 폴더 밑에 로그인 관련 로직을 분리해뒀는데, 이 코드들은 apis 폴더의 로그인 관련 API와 연동될 것이며, 해당 함수들을 이용해 로그인 로직을 구현할 것이다.
- view
- 사실상 pages 폴더이다.
- 프로젝트의 로그인 페이지가 STAFF 전용 로그인과 일반 유저 로그인으로 나눠져 구성되므로 우선 분리해두었다.
- zustand
- store 로 명명하는 것이 일반적으로 알고 있지만, 폴더 구조에서 최대한 아래에 위치시키기 위해 사전순으로 뒤에 있는 철자로 시작하는 zustand 로 명명하였다.
- 내부 코드는 일반 store 와 동일하게 작성될 예정이다.
현재까지 이야기 된 상황은 위와 같고, layout 폴더를 따로 빼서 레이아웃을 좀 간편하게 구성해야하나.. 하는 고민을 하고 있는데 Next에서 사용하던 layout 파일 패턴이 좀 편하게 느껴지긴 했던 것 같다.
다만 이 방식을 사용하려면 특히나 리액트에 익숙하지 않은 팀원에게 children과 합성에 대한 설명을 충분하게 해줘야 할 것 같다.
'Project' 카테고리의 다른 글
[Project] Axios Instance를 만들어보자 (0) | 2024.07.21 |
---|---|
[Project] 프론트엔드 협업을 위한 가이드 작성 (0) | 2024.07.19 |
싸피코피(SSAFY COFFY) 프로젝트 회고 (3) | 2024.07.11 |