Pullanner porject - 환경설정 with Vite, NPM

이소라·2023년 1월 26일
0

1. vite 설치

  • react-ts template의 vite 설치하기
npm create vite@latest pullanner --template react-ts
cd pullanner
npm install

Note: vite의 번들 시각화

  • vite는 번들시 rollup을 사용하므로, 번들 시각화 도구로 rollup-plugin-visualizer를 사용하기 (참고: rollup-plugin-visualizer)

2. eslint, prettier 설치

  • eslint를 devDependencies에 설치하기
npm i -D eslint
  • Airbnb's eslint를 따르기로 결정했으므로, eslint-config-airbnb를 devDependencies에 설치하기
npx install-peerdeps --dev eslint-config-airbnb
  • prettier, eslint-config-prettiereslint-plugin-prettier 를 devDependencies에 설치하기
npm i -D prettier
npm i -D eslint-config-prettier
npm i -D eslint-plugin-prettier
  • eslint-typescript/parser, eslint-typescript/eslint-plugin를 devDependencies에 설치하기
npm i -D @typescript-eslint/eslint-plugin
npm i -D @typescript-eslint/parser

3. tsconfig 절대경로 설정

참고 : vite 시작하는 법 with react+ts

  • tsconfig 절대경로를 사용하기 위해, vite-tsconfig-paths를 설치하기
npm i -s vite-tsconfig-paths
  • vite.config.ts의 plugins에 tsconfigPaths() 넣기
// vite.cofig.ts
import { defineConfig } from 'vite'
import tsconfigPaths from 'vite-tsconfig-paths'

export default defineConfig({

  //... some configs

  plugins: [..., tsconfigPaths()],

  //... some configs

})
  • tsconfig.jsonbaseUrlpaths 옵션 설정하기
// tsconfig.json
{
  "compilerOptions": {
  ...,
    "baseUrl": ".", // "paths"가 있는 경우 반드시 지정되어야함.
    "paths": {
      "@src/*": [
        //@src로 시작하면 아래 줄의 디렉토리를 의미한다.
        "src/*" //baseUrl을 기준으로 src/ 하위 디렉토리를 @src로 표현한다.
      ]
    }
  }
}

4. storybook 설치

참고 : Storybook builder for Vite

npx sb@next init --builder vite && npm run storybook
  • storybook 7.0을 선택한 이유 (참고 : First-class Vite support in Storybook)
    • 이유 1 : storybook 7.0부터 컴포넌트 코드를 빌드할 때 Webpack 대신 vite를 사용할 수 있게됨
      • webpack을 설치할 필요가 없어서 설치 크기를 28% 간단화함
    • 이유 2 : zero config
      • 존재하는 vite config file로부터 확장되어서, storybook만의 config file을 만들 필요 없음
  • 프로젝트에 sb가 설치되어 있지 않으므로, sb를 설치하기
    • sb : storybook/cli로 storybook의 설치를 도와줌
npm i sb@7.0.0-beta.34
  • prompt 창에서 ESlintPlugin 설치를 동의했을 때, eslint-plugin-storybook가 devDependencies에 설치됨 (참고 : eslint-plugin-storybook)
// ESlintPlugin 설치 동의시, .eslintrc.js 파일에 추가된 것
{
	...,
    "extends": ["plugin:storybook/recommended"]
}
  • .eslintignore 파일에 !.storybook을 추가하기
    • .으로 시작하는 폴더(.*)와 그 안의 파일들은 기본적으로 무시됨 (참고 : Ignoring Code)
    • !.storybook : .storkbook 폴더 안의 configuration 파일도 린트할 수 있도록 해주는 설정
// .eslintignore 파일
!.storybook

5. tailwind CSS 설치

  • tailwindcss, postcss, autoprefixer를 설치하기
npm install -D tailwindcss postcss autoprefixer
  • init 명령어를 통해 config 파일 생성하기
    • p 옵션 : tailwind.config.jspostcss.config.js 파일을 동시에 생성함
npx tailwindcss init -p
  • tailwind.config.js의 content에 tailwind class 이름을 사용하는 파일의 경로를 넣기
// tailwind.config.js
module.exports = {
  content: ['./index.html', './src/**/*.{js,ts,jsx,tsx}'],
  theme: {
    extend: {},
  },
  variants: {
    extend: {},
  },
  plugins: [],
}
// postcss.config.js
module.exports = {
  plugins: {
    'postcss-import': {},
    tailwindcss: {},
    autoprefixer: {},
  }
}
  • index.css에 @tailwind directives를 추가하기 (참고: Install Tailwind CSS with Vite)
    • vscode가 css 파일에서 @tailwind를 인식하지 못하는 에러가 발생함
    • vscode에 PostCSS Language Support extension을 설치함
// index.css
@tailwind base;
@tailwind components;
@tailwind utilities;
  • tailwindcss 관련 IDE Extension 설치하기
    • TailwindCss IntelliSense
      • 자동완성, 문법 하이라이팅, 린트 제공함
    • Headwind
      • 클래스의 일관적인 순서를 강화, 정렬해줌

6. Recoil 설치

npm install recoil
  • recoil은 Webpack이나 Rollup과 같은 모듈 번들러와도 문제 없이 호환된다고 함

  • recoil은 ES5와 함께 사용하는 것은 지원되지 않음

    • 우리 프로젝트에서는 ESNext를 사용할 예정이라 상관 없음
  • 프로젝트에서 eslint-plugin-react-hook을 사용하는 경우, useRecoilCallback을 additionalHook 목록에 추가하는 것이 좋다고 함 (참고: Recoil - 설치)

    • 추가할 경우, useRecoilCallback()을 사용 시 dependency가 잘못 지정되었을 경우 경고하고 해결 방안을 제시한다고 함
  • 우리 프로젝트에서 eslint-plugin-react-hook을 사용하고 있으므로, useRecoilCallback()을 사용할 예정이라면 추가 설정하는 것이 좋음

    • useRecoilCallback()의 사용 예 (참고: Recoil - useRecoilCallback())
      • atom이나 selector를 갱신할 경우, 리렌더링하는 React 컴포넌트 구독 없이 비동기적으로 Recoil 상태를 사용할 때
      • 렌더링 시 작동하길 원하지 않는 비동기 액션에 대한 비싼 살펴보기를 지연할 때
      • Recoil 상태를 읽고 쓰길 원하는 곳에서 부수 효과를 수행할 때
      • 렌더링 시에는 어떤 atom이나 selector를 갱신하고 싶은지 모르는 atom이나 selector를 동적으로 갱신할 때
      • 렌더링 전에 프리페칭할 때
// eslintrc.js
{
  ...,
  "rules": {
    ...,
    "react-hooks/exhaustive-deps": "warn" // 추가
  }
}

7. TanStack React Query 설치

npm i @tanstack/react-query

8. axios 설치

npm install axios
export default defineConfig({
  plugins: [react(), tsconfigPaths()],
  server: {
    proxy: {
      '/api': 'http://localhost:3010'
    }
  }
});

9. MSW (Mock Service Worker) 설치

npm install msw --save-dev
  • Mock Service Worker CLI의 init 명령어를 실행하기
npx msw init public/ --save
  • src 폴더 안에 mocks 폴더 생성하기
  • src/mocks 폴더 안에 handler.js 파일 생성하기
// src/mocks/handlers.ts
import { rest } from 'msw'
export const handlers = [
  rest.get('http://localhost:3000/', async (req, res, ctx) => {
    return res(
      ctx.status(200),
      ctx.json({
        message: 'Welcome',
      }),
    );
  }),
  rest.post('http://lcoalhost:3000/user', async (req, res, ctx) => {
    return res();
    // ...
  }),
];
  • src/mocks 폴더 안에 browser.js 파일 생성하기
    • handler.js에서 정의한 request handler를 가진 worker 인스턴스를 생성함
// src/mocks/browser.ts
import { setupWorker } from 'msw'
import { handlers } from './handlers'
// This configures a Service Worker with the given request handlers.
export const worker = setupWorker(...handlers);
  • main.tsx에서 개발환경인 경우에만 Mocking Service Worker가 작성되도록 수정하기 (참고: vite-react-ts-extended Github Repository의 main.tsx)
    • mocking은 개발 환경에서 실행되므로, 개발환경일 때만 Mocking Service Worker가 조건적으로 작성되도록 함
    • Mocking Service Worker는 비동기로 동작하기 때문에, worker가 실행된 이후에 애플리케이션이 실행되도록 로직을 작성해줘야 함
// main.tsx
// Before
ReactDOM.createRoot(document.getElementById('root') as HTMLElement).render(
  <React.StrictMode>
    <App />
  </React.StrictMode>,
);


// After
const renderRoot = () => {
  ReactDOM.createRoot(document.getElementById('root') as HTMLElement).render(
    <React.StrictMode>
      <App />
    </React.StrictMode>,
  );
};

if (process.env.NODE_ENV === 'development') {
  import('@src/mocks/browser')
    .then(({ worker }) => {
      worker.start();
    })
    .then(() => renderRoot());
} else {
  renderRoot();
}
  • process의 type 에러가 발생하므로, @types/node를 설치해야 함
npm i @types/node

0개의 댓글