[React] tailwindcss 사용기

Yunhye Park·2024년 1월 21일
1

Back To Basic

목록 보기
4/9

지난 프로젝트 때 했던 CSS 스타일링 중에 가장 인상 깊은 파트가 채팅 목록과 채팅방이다. 협업 과정은 동기 처리가 아니라 비동기 처리라서(ㅋㅋ) 대개 이것저것 하느라 하나에 몰두한 느낌은 아닌데, 채팅 UI는 2~3시간 안에 이거 하나에만 집중해서 팠다.

그래선가. 불편함이 확연히 느껴졌다.
1) 클래스명을 하나씩 지정해야 함
2) CSS 파일과 HTML 코드, 브라우저를 오가며 스타일링 해야 함

그나마 SASS를 사용한 덕에 클래스명을 한번에 작성하고, 클래스명을 중첩 구조로 작성해주니 파일을 오갈 일이 적긴 했다. 하지만 클래스명을 짓는 건 여간 복잡한 일이 아니었으므로.. CSS 프레임워크의 중요성을 느꼈다.

그리하여 클래스명 없이 작성할 수 있다는 tailwind를 한번 맛보려 한다.

tailwind 특징

1. Utility-First 접근 방식

클래스 기반의 유틸리티 클래스를 제공한다. 일반 CSS가 선택자를 통한 스타일링이라고 한다면, HTML class명에 스타일을 지정한다. 고로 CSS 파일, JS 파일을 왔다갔다 할 필요 없이 한 페이지에서 바로 스타일링 할 수 있다.

2. 커스터마이징 시스템

Tailwind를 사용하려면 config 파일(tailwind.config.js)은 필수다.

2-1. 이때 tailwind에서 자체적으로 제공하는 단위를 디테일하게 조정할 수 있다. 이를 테면 container라는 클래스명은 기본적으로 center가 되게끔 설정하는 식으로.

2-2. 개별 설정뿐만 아니라 theme 자체를 만들 수도 있다.

2-3. 다른 CSS 프레임워크와 혼용하기도 좋다. 많이들 사용하는 bootstrap을 예로 들어보자. 부트스트랩은 UI 컴포넌트를 제공하기에 margin과 padding border-radius 등이 정해져있다.

물론 부트스트랩 내에서도 커스터마이징 할 수 있지만, tailwind는 클래스명 자체에 스타일링을 추가할 수 있어서 별다른 과정 없이 간단한 커스터마이징이 가능하다.

3. 반응형

여느 CSS 프레임워크가 그러하듯 반응형도 지원한다.

4. JIT(Just-In-Time) 컴파일링

실시간으로 스타일을 빌드해서 개발 중에 코드를 고친 후 저장하면 바로 브라우저가 업데이트 된다. 리액트가 그러하듯.

최근 리액트를 자주 사용해서 이게 당연하다고 생각했는데, node에서 ejs 템플릿을 사용할 땐 바로바로 빌드가 안 되었다. 프론트엔드는 UI를 계속 확인해야 하니까 라이브러리든 프레임워크든 JIT 컴파일링이 기본인 것 같다. 그래도 개념을 한번 짚고 넘어간다는 의미로 적어봤다.

사용법

tailwind는 이것저것 config하고 설치할 게 생각보다 많다. 그래서 설치하는 과정이 진입장벽이 아닌가 싶다.

  1. 설치
npm i -D tailwindcss postcss autofixer postcss-loader
  • postcss :
    CSS 후처리기(Post-processor)로서 CSS를 변환하고 최적화하는 도구.
  • autofixer :
    CSS에 자동으로 벤더 프리픽스를 추가해주는 postcss 플러그인. 여러 브라우저에서 일관된 스타일을 유지하고자 사용.
  • postcss-loader :
    postcss를 웹팩 빌드 프로세스에 통합하여 CSS 파일 처리.
  • 잘 설치됐나 package.json에서 확인
...
  "dependencies": {
    "@testing-library/jest-dom": "^5.17.0",
    "@testing-library/react": "^13.4.0",
    "@testing-library/user-event": "^13.5.0",
    "postcss-loader": "^8.0.0",
    "react": "^18.2.0",
    "react-dom": "^18.2.0",
    "react-scripts": "5.0.1",
    "web-vitals": "^2.1.4"
  },
...

  "devDependencies": {
    "autoprefixer": "^10.4.17",
    "postcss": "^8.4.33",
    "tailwindcss": "^3.4.1"
  }

2.1. tailwindcss의 config 파일 생성

npx tailwindcss init

2.2. 생성한 파일 내용 아래와 같이 수정
root/tailwind.config.js

module.exports = {
  content: ['./src/**/*.{html,js,tsx,ts}'],
  theme: {
    extend: {},
  },
  plugins: [require('tailwindcss'), require('autoprefixer')],
};

3.1. tailwind의 설정 가져오기
src/styles/tailwind.css

@import 'tailwindcss/base';
@import 'tailwindcss/components';
@import 'tailwindcss/utilities';
  • create-react-app에서 자동 생성된 index.css에 작성하면 App.js에서 불러오는 작업 생략

3.2. App.js에 불러오기

import './styles/tailwind.css';

function App() {
  return (
    <div>
      <div className="font-bold">확인</div>
    </div>
  );
}

export default App;
  1. 루트 디렉터리에 postcss.config 파일 추가
    root/postcss.config.js
module.exports = {
  plugins: {
    tailwindcss: {},
    autoprefixer: {},
  },
};

트러블 슈팅

1. ts 파일은 무조건 export

  • 오류 메시지 :
cannot be compiled under '--isolatedModules'
because it is considered a global script file.
  • 원인 : ts 파일인데 내용이 비어서
  • 해결 : 빈 페이지에 export {} 추가

2. tailwindcss config

  • 오류 메시지 : TypeError: plugins.forEach is not a function
  • 해결 : tailwind.config.js의 plugins에 파일 경로 추가
module.exports = {
  content: ['./src/**/*.{html,js,tsx,ts}'],
  theme: {
    extend: {},
  },
  plugins: [require('tailwindcss'), require('autoprefixer')], // <--
};

3. ts파일을 자동 인식하도록

  • 오류 메시지 :
Module not found: Error: Can't resolve './components/CatCard' in '~~\src'
ERROR in ./src/App.js 4:0-43
Module not found: Error: Can't resolve './components/CatCard' in '~~\src'
  • 원인 : tsx 파일 확장자 없음
  • 해결 : import 한 부분에 파일 확장자(.tsx) 추가

4. React를 불러오지 않아도 되니까

  • 오류 메시지 :
'React' refers to a UMD global, but the current file is a module.
Consider adding an import instead.ts(2686)
  • 원인 : 리액트 17 버전부터는 React를 불러오지 않아도 되는데, typescript에 이 내용을 configure 해줘야 함
  • 해결 : tsconfig.json 에 "jsx": "react-jsx" 추가
{
  "compilerOptions": {
    "target": "es5",
    "lib": [
      "dom",
      "dom.iterable",
      "esnext"
    ],
    "allowJs": true,
    "skipLibCheck": true,
    "esModuleInterop": true,
    "allowSyntheticDefaultImports": true,
    "strict": true,
    "forceConsistentCasingInFileNames": true,
    "noFallthroughCasesInSwitch": true,
    "module": "esnext",
    "moduleResolution": "node",
    "resolveJsonModule": true,
    "isolatedModules": true,
    "noEmit": true,
    "jsx": "react-jsx" // <-- 이거 추가
  },
  "include": [
    "src"
  ]
}

5. env 파일 변경 시 서버 다시 시작하기

  • 상황 : 환경변수 사용하려는 중 (접두사 REACT_APP_ 기입)
  • 오류 메시지 :
SyntaxError: Unexpected token '<', "<!DOCTYPE "... is not valid JSON
  • 원인 : env 파일은 변경하면 서버 다시 시작해야 함
  • 해결 : 서버 끄고 다시 시작

적응 tip

tailwind는 css라서 사용 자체가 어려운 게 아니지만, 이 모듈만의 규칙에 익숙해져야 쓰기 편리하다고 느끼는 듯하다. 공식 문서 왔다갔다 하는 게 다소 귀찮을 땐 아래 플러그인을 설치해보자.

Tailwind CSS intelliSense

자동 완성이 되기 때문에 초반 적응에 도움이 될 듯하다.

써본 소감

  • 간결함
    클래스명이 없고 margin: 0 2rem이라고 적었던 것을 mx-2로 간결히 작성할 수 있어서 좋았다.

    • 다만 거의 비슷한 스타일을 여러 개 작성해야 할 때는 같은 걸 여럿 반복해야 해서 번거롭다고도 느껴진다.
  • 직관적
    tailwind를 안 써본 사람이라도 css 문법을 알면 대략 어떤 설정인지 눈으로 읽힌다.

    • 코드 작성 과정도 직관적이다. 직설적이라고 해야 하나? 클래스명 짓느라 고민할 것 없이 바로 스타일링을 시작할 수 있어서 좋다.
  • config 필수
    CSS 파일에서는 그냥 썼던 속성들이 tailwind에서는 config가 필요할 수 있다.

    • 예를 들어 backdrop-blur를 사용하고 싶었는데 tailwind에서는 바로 적용이 안 되었다. config 파일에서 속성 정의를 하는 등의 과정이 필요하다.

그럼에도 불구하고 SASS, module CSS, styled-component보다 마음에 든다. 클래스명 지으면서 스트레스를 꽤나 받은 모양이다.. tailwind가 조금 익숙해지면 또 새로운 라이브러리나 프레임워크를 찾아 써봐야겠다!

profile
일단 해보는 편

0개의 댓글