팀원들의 프로젝트 이해도를 향상시키기 위해, 오피스너 웹 버전의 기술스택에 대해 각각 간단히 설명을 해보고 학습 방향을 정해보겠습니다.
[Core] Next.js (App Router)
Next.js를 사용하는 주된 이유는 SSR을 구현하기 위함 입니다. 오피스너 웹 버전에서는 건물명을 검색했을 때 사용자들이 유입될 수 있어야 합니다. 이를 위해서는 SEO 최적화가 필요하므로 Next.js 사용이 보다 유리합니다.
- React 기반의 프레임워크로, 서버 사이드 렌더링(SSR)과 정적 사이트 생성(SSG)을 쉽게 처리할 수 있어서 검색 엔진 최적화(SEO)에 유리합니다.
- 초기 페이지 로딩에 대해서는 SSR, SSG 방식으로 동작시킬 수가 있고, 이후의 요청에 대해서는 기본적으로 CSR 방식으로 동작하기 때문에 SSR 방식의 장점인 SEO에 유리하면서도 CSR의 장점을 활용할 수 있습니다.
[Styling] TailwindCSS
TailwindCSS는 스타일링을 쉽게 하기 위한 CSS 프레임워크입니다.
- 유틸리티 기반 CSS 프레임워크로, 제공되는 CSS 클래스들을 이용해서 빠르게 웹 페이지의 스타일을 지정할 수 있습니다.
- 쉽게 말하자면, 디자인의 기본 재료들을 제공하는 도구라고 할 수 있습니다.
- 페이지의 레이아웃이나 텍스트, 색상, 여백 등을 세밀하게 조정해야할 때 사용합니다. 예를 들어, 버튼의 크기, 색깔, 배경색 등을 조정할 수 있습니다.
- 다만 클래스를 남용하면 코드가 복잡해 보일 수 있어서, 일관된 구조로 작성하는 것이 좋습니다.
[Styling] Radix UI
Radix UI는 Headless UI 라이브러리로, 쉽게 말하자면 디자인 없이 기능만 제공하는 UI 라이브러리입니다. 사용자가 원하는 스타일로 쉽게 커스터마이징 할 수 있습니다.
- Radix UI 공식 문서를 살펴보면, "Core building blocks for your design system”이라는 문구를 확인할 수 있습니다. 해석해보면, “나만의 디자인 시스템을 만들기 위한 핵심 빌딩 블록”이라는 의미겠네요.
- Radix UI는 기본적인 UI 구성 요소를 제공하면서도 스타일링과 디자인은 제공하지 않습니다. 즉, UI 요소의 구조와 동작은 제공하지만, 스타일링은 개발자가 직접 지정할 수 있습니다.
- 따라서 반응형에 의해 디자인이 달라지거나, 기능 변경이나 추가가 많이 발생한다면 Headless가 유지보수에 더 유리하겠네요.
- 웹 접근성을 보장하는 UI 라이브러리라서, 디자인 시스템을 별도로 사용하면서도 접근성을 보장할 수 있다는 장점이 있습니다.
왜 Headless UI 라이브러리가 필요할까?
- Material UI나 Bootstrap과 같은 UI 라이브러리들은 각자만의 스타일이 입혀져 있기 때문에 회사에서 설계한 디자인과 다른 경우들이 많습니다. 오피스너의 경우에도 오피스너만의 디자인이 설계되어 있죠.
- 이러한 UI 라이브러리의 테마를 커스터마이징해서 문제를 해결할 수 있지만, 완벽하게 원하는 디자인으로 만드는 작업이 다소 번거로울 수 있습니다.
- 그렇다고 개발자가 처음부터 다 만들기엔 웹 접근성을 준수하며 개발하기가 어렵습니다.
- 그래서 이런 니즈들로 인해, 접근성을 보장하면서 기능을 제공하는 Headless UI 라이브러리가 등장하게 됐습니다.
[Styling] shadcn/ui
기능(Radix UI)과 디자인(TailwindCSS)이 잘 결합된 코드 모음(컴포넌트)이라고 생각하면 됩니다.
- 다시 한번 말하자면, Radix UI에 TailwindCSS의 스타일링을 곁들여, 가공된 컴포넌트로 제공하는 UI 모음집(Component Collection)입니다.
- 라이브러리가 아니기 때문에, npm 패키지 형태가 아닌, 컴포넌트를 복사 붙여넣기 하는 제공 방식을 택하고 있습니다. (패키지 매니저 사용이 아닌 npx 명령어 사용)
- 왜 복붙 방식을 하느냐면, 커스터마이징 자유도를 높이기 위해서라고 생각하면 될 것 같습니다. 또한 의존성을 주입시키지 않음으로써 불필요한 번들 크기 증가를 막을 수 있습니다.
[State Management] React Query
서버 상태 관리에 사용되는 라이브러리로, 비동기 데이터(fetching)를 쉽게 관리 할 수 있도록 도와줍니다. 즉, 서버에서 가져오는 데이터를 효율적으로 관리하기 위해 사용합니다.
- 서버에서 데이터를 가져오고(API 요청 결과), 캐싱하고, 재요청(동기화)하는 작업들을 쉽게 처리할 수 있습니다.
- 데이터를 불필요하게 너무 자주 요청하지 않도록 설정하고, 캐싱이 필요한 시점에만 적절히 캐싱을 사용해 성능을 최적화하는 것이 중요합니다.
[State Management] Zustand
클라이언트 상태 관리를 위해 사용되는 가벼운 전역 상태 관리 라이브러리입니다.
- 테마(라이트/블랙 모드)나 로그인 상태, 사용자 정보와 같은 데이터를 여러 컴포넌트에서 공유해야 할 때 사용합니다.
- 상태 관리가 너무 복잡해지지 않도록 하는 것이 중요하고, 컴포넌트가 필요 이상으로 상태를 구독하지 않도록 신경써야합니다.
🔥 학습 방향
- next-auth를 사용하여 로그인 기능 구현을 할 예정이므로 이에 대한 학습이 필요할 것 같습니다.
- 로그인/회원가입 기능 구현 시 유효성 검사를 효율적으로 하기 위해 React Hook Form 도입을 고려해봐야 할 것 같습니다. React Hook Form과 Zod를 함께 사용하면 폼 제출 시 유효성 검사를 효율적으로 수행할 수 있을 것 같습니다.
- React Query의 경우 캐싱 기능을 제공하는데, 무분별한 캐싱은 되려 성능 저하를 발생시키므로 React Query를 학습하며 캐싱 처리에 대해 생각해보면 좋을 것 같습니다.
- Zustand를 사용할 때, 클라이언트 상태 관리가 필요한 정보가 뭘지 생각해보며 개발하면 좋을 것 같습니다.