generated from gc/template-java-maven
- 디자인 시스템 CSS 변수 토큰 적용 (success/warning/danger/info) - PeriodFilter 공통 컴포넌트 생성 및 통계 페이지 적용 - SERVICE_BADGE_VARIANTS 공통 상수 추출 - 통계/요청로그/키관리/관리자 페이지 레퍼런스 디자인 반영 - 테이블 규격 통일 (h-8/h-7, px-3 py-1, text-xs, Button xs) - 타이틀 아이콘 전체 페이지 통일 - 카드 테두리 디자인 통일 (border + rounded-xl) - FHD 1920x1080 최적화
19 KiB
19 KiB
SNP Connection Monitoring — 디자인 시스템 적용 프롬프트
아래 프롬프트를 Claude Code에 붙여넣어 실행하세요.
해양 데이터 시스템(SNP Connection Monitoring) 프로젝트에 디자인 시스템을 적용해줘.
프로젝트 규칙(.claude/rules/)과 CLAUDE.md를 반드시 읽고 따라줘.
## 0. 사전 준비
- develop 브랜치에서 `feature/design-system` 브랜치를 생성해서 작업
- 커밋 메시지는 Conventional Commits 형식 (프로젝트 git-workflow.md 참조)
## 1. 디자인 가이드 문서 생성
`docs/design/` 디렉토리 아래에 아래 파일들을 생성해줘.
### 1-1. docs/design/colors.md
해양 데이터 시스템 컬러 시스템. 내용:
**브랜드 컬러 원본:**
| 역할 | HEX | 설명 |
|------|-----|------|
| Primary | #6D94C5 | Slate Blue — 신뢰, 전문성 |
| Secondary | #CBDCEB | Powder Blue — 부드러운 보조 |
| Accent | #E8DFCA | Warm Sand — 따뜻한 포인트 |
| Background | #F5EFE6 | Warm Cream — 배경색 |
**브랜드 컬러 스케일 (50~950):**
Primary (Slate Blue, hue≈213°):
- 50: #F5F7F9, 100: #E5EBF2, 200: #D2DAE5, 300: #B7C5D7, 400: #8AA5C7
- 500: #6D94C5, 600: #507FB9, 700: #3B669C, 800: #2D507B, 900: #1B2C41, 950: #0E1A2B
Secondary (Powder Blue, hue≈210°):
- 50: #F5F7F9, 100: #E6EDF5, 200: #D1DAE5, 300: #B7C8D7, 400: #89AAC8
- 500: #CBDCEB, 600: #6B9AC8, 700: #4E88BB, 800: #396E9D, 900: #1B2F41, 950: #0E1A2B
Accent (Warm Sand, hue≈38°):
- 50: #F9F8F6, 100: #F2EDE4, 200: #E4E0D7, 300: #D5CDB9, 400: #C4B48C
- 500: #E8DFCA, 600: #B59854, 700: #9A7E3E, 800: #786230, 900: #3F351D, 950: #2B2312
**디자인 토큰 (CSS 변수 — Light / Dark):**
| 토큰 | Light | Dark |
|------|-------|------|
| --color-primary | #507FB9 | #B7C5D7 |
| --color-primary-hover | #3B669C | #D2DAE5 |
| --color-primary-active | #2D507B | #8AA5C7 |
| --color-primary-subtle | #F5F7F9 | #1B2C41 |
| --color-primary-text | #2D507B | #D2DAE5 |
| --color-secondary | #CBDCEB | #B7C8D7 |
| --color-secondary-hover | #89AAC8 | #D1DAE5 |
| --color-secondary-active | #4E88BB | #89AAC8 |
| --color-secondary-subtle | #F5F7F9 | #1B2F41 |
| --color-secondary-text | #396E9D | #D1DAE5 |
| --color-accent | #E8DFCA | #D5CDB9 |
| --color-accent-hover | #C4B48C | #E4E0D7 |
| --color-accent-active | #B59854 | #C4B48C |
| --color-accent-subtle | #F9F8F6 | #3F351D |
| --color-accent-text | #786230 | #E4E0D7 |
**시멘틱 컬러 (Light / Dark):**
| 역할 | Light | Dark |
|------|-------|------|
| Success | #059669 | #34D399 |
| Warning | #D97706 | #FBBF24 |
| Danger | #DC2626 | #FCA5A5 |
| Info | #0284C7 | #38BDF8 |
**뉴트럴 (Blue-tinted warm gray):**
| 토큰 | Light | Dark |
|------|-------|------|
| --color-bg-base | #F5EFE6 | #131416 |
| --color-bg-surface | #FFFFFF | #1E2023 |
| --color-bg-elevated | #FFFFFF | #282A2E |
| --color-border | #D5D2CC | #3A3C41 |
| --color-border-strong | #9198A1 | #5C6570 |
| --color-text-primary | #1E2329 | #F4F5F5 |
| --color-text-secondary | #5C6570 | #9198A1 |
| --color-text-tertiary | #9198A1 | #5C6570 |
**다크모드 토큰 사용 가이드:**
다크모드 시멘틱 토큰(--color-primary, --color-secondary, --color-accent)은 텍스트/아이콘용 밝은 톤이다.
버튼/뱃지처럼 배경색이 필요한 인터랙티브 요소는 다크모드에서 스케일 값(600~700)을 직접 사용해야 한다.
- 텍스트/아이콘: `text-[--color-primary]` → 다크모드에서 자동으로 밝은 톤 적용 (OK)
- 버튼 배경: `bg-[--color-primary]` → 다크모드에서 `dark:bg-[--color-primary-600]`으로 오버라이드 (필수)
**차트 팔레트 (6색 Hue 분산, Cool+Warm 교차):**
Light (흰 배경):
1. #507FB9 — Slate Blue (213°, 브랜드 Primary)
2. #B59854 — Warm Gold (38°, 브랜드 Accent)
3. #B5607D — Rose (340°)
4. #3D998A — Teal (168°)
5. #8B6DB5 — Lavender (270°)
6. #C07850 — Coral (22°)
Dark (어두운 배경, 밝기 강화):
1. #6D94C5 — Slate Blue
2. #C4B48C — Warm Sand
3. #D4839B — Rose
4. #5BB5A6 — Teal
5. #B79FD4 — Lavender
6. #D4956B — Coral
### 1-2. docs/design/typography.md
타이포그래피 시스템:
- 기본 폰트: Pretendard (한글), Inter (영문/숫자)
- 8단계 타입 스케일: Display 48px, H1 36px, H2 30px, H3 24px, Body-lg 18px, Body 16px, Caption 14px, Overline 12px
- line-height: heading 1.2~1.3, body 1.5~1.6
- font-weight: 300(light), 400(regular), 500(medium), 600(semibold), 700(bold)
- 한국어 word-break: keep-all 규칙
### 1-3. docs/design/spacing.md
스페이싱 시스템:
- 4px 기반 스케일: 0(0px), 0.5(2px), 1(4px), 1.5(6px), 2(8px), 3(12px), 4(16px), 5(20px), 6(24px), 8(32px), 10(40px), 12(48px), 16(64px), 20(80px), 24(96px)
- 컴포넌트별 내부 여백: Button(px-4 py-2), Card(p-4~p-6), Input(px-3 py-2), Modal(p-6)
- 반응형 브레이크포인트: sm 640px, md 768px, lg 1024px, xl 1280px, 2xl 1536px
- 그리드: 12컬럼, gap-4~gap-6
### 1-4. docs/design/components.md
컴포넌트 스펙:
**Button 변형 (Light 모드):**
- primary: bg-[--color-primary] text-white hover:bg-[--color-primary-hover]
- secondary: bg-[--color-secondary] text-[--color-secondary-text] hover:bg-[--color-secondary-hover]
- accent: bg-[--color-accent] text-[--color-accent-text] hover:bg-[--color-accent-hover]
- outline: border border-[--color-border-strong] text-[--color-text-primary] hover:bg-[--color-primary-subtle]
- ghost: text-[--color-text-secondary] hover:bg-[--color-primary-subtle]
- danger: bg-danger-600 text-white hover:bg-danger-700
**Button 변형 (Dark 모드) — 채도/대비 강화:**
다크모드에서 시멘틱 토큰(--color-primary 등)은 연한 파스텔 톤이라 버튼 배경으로 부적합.
스케일 값(600~700)을 직접 사용하여 선명한 대비를 확보한다.
- primary: dark:bg-[--color-primary-600] dark:text-white dark:hover:bg-[--color-primary-500]
- secondary: dark:bg-[--color-secondary-700] dark:text-white dark:hover:bg-[--color-secondary-600]
- accent: dark:bg-[--color-accent-600] dark:text-white dark:hover:bg-[--color-accent-500]
- outline: dark:border-[--color-primary-400] dark:text-[--color-primary-300] dark:hover:bg-primary-600/15
- ghost: dark:text-[--color-primary-300] dark:hover:bg-primary-600/12
- danger: dark:bg-[#EF4444] dark:text-white dark:hover:bg-[#DC2626]
**Button 사이즈:** sm(h-8 px-3 text-sm), md(h-10 px-4 text-sm), lg(h-12 px-6 text-base)
**Badge shape:**
- pill (기본): rounded-full — 상태 표시, 카테고리 태그에 사용
- filled (버튼 스타일): rounded-md — 강조 라벨, 카운트 뱃지에 사용
**Badge 변형 (pill):** default, primary, secondary, accent, success, warning, danger, info
- 연한 배경(subtle) + 색상 텍스트
**Badge 변형 (filled):** Chart Palette 1:1 맵핑, 연한 배경(subtle) + 색상 텍스트, shape rounded-md
- default (neutral)
- blue = Chart 1 (#507FB9 / dark #6D94C5)
- gold = Chart 2 (#B59854 / dark #C4B48C)
- rose = Chart 3 (#B5607D / dark #D4839B)
- teal = Chart 4 (#3D998A / dark #5BB5A6)
- lavender = Chart 5 (#8B6DB5 / dark #B79FD4)
- coral = Chart 6 (#C07850 / dark #D4956B)
- 라이트: rgba(색상, 0.12~0.14) 배경 + 진한 텍스트 / 다크: rgba(색상, 0.14) 배경 + 밝은 텍스트
- ⚠️ success, warning, danger, info는 Pill 전용 — Filled에 사용 금지
- ⚠️ primary, secondary, accent, navy는 Filled에 사용 금지 (Chart 맵핑 색상만 사용)
**Card:** bg-[--color-bg-surface] border border-[--color-border] rounded-lg shadow-sm
**Input:** border-[--color-border] focus:ring-2 focus:ring-[--color-primary]/30 focus:border-[--color-primary]
**Modal:** bg-[--color-bg-surface] rounded-xl shadow-2xl, overlay bg-black/50
**Toast:** success(green), error(red), warning(amber), info(blue) — 시멘틱 컬러 사용
### 1-5. docs/design/icons.md
아이콘 시스템:
- Lucide React 사용
- 사이즈: xs(14px), sm(16px), md(20px), lg(24px), xl(32px)
- 색상: 시멘틱 토큰 사용 (text-[--color-text-secondary] 기본)
- 인터랙티브 아이콘: hover 상태 시 text-[--color-primary]
### 1-6. docs/design/motion.md
모션 시스템:
- Duration: fast(100ms), normal(200ms), slow(300ms), slower(500ms)
- Easing: ease-out(진입), ease-in(퇴장), ease-in-out(이동)
- 패턴: fade-in, slide-up, scale, collapse
- prefers-reduced-motion: reduce 시 애니메이션 비활성화
### 1-7. docs/design/code-conventions.md
코드 컨벤션:
- 파일명: PascalCase(컴포넌트), camelCase(유틸/훅), kebab-case(CSS)
- Tailwind 클래스 순서: layout → sizing → spacing → border → bg → text → effect → transition
- cn() 유틸리티 사용 (clsx + twMerge)
- import 순서: react → 외부 → 내부(@/) → 타입 → 스타일
- forwardRef 패턴: DOM 래핑 컴포넌트에 적용
### 1-8. docs/design/do-dont.md
Do/Don't 가이드:
- DO: CSS 변수 토큰 사용 (bg-[--color-primary])
- DON'T: 하드코딩 HEX (#6D94C5, #507FB9, #5C6570, #9198A1, #D5D2CC, #1E2329 등)
- DO: 시멘틱 컬러로 상태 표현
- DON'T: 임의 색상으로 상태 표현
- DO: spacing 스케일 사용 (p-4, gap-6)
- DON'T: 임의 px값 (p-[13px])
- DO: cn() 유틸리티로 조건부 클래스
- DON'T: 삼항연산자로 className 문자열 조합
- DO: 다크모드 버튼에 스케일 값 사용 (dark:bg-[--color-primary-600])
- DON'T: 다크모드 버튼에 시멘틱 토큰 그대로 사용 (dark:bg-[--color-primary] → 연한 파스텔톤으로 구분 안됨)
### 1-9. docs/design/prompts/new-component.md
새 컴포넌트 생성 프롬프트 템플릿:
[컴포넌트명] 컴포넌트를 만들어줘.
- docs/design/ 가이드 참조
- Props interface 정의
- 변형(variant), 사이즈(size) 지원
- 다크모드 대응 (CSS 변수 토큰)
- forwardRef 적용 (DOM 래핑 시)
- cn() 유틸리티 사용
### 1-10. docs/design/prompts/review-checklist.md
디자인 리뷰 체크리스트 (9개 카테고리):
1. 컬러: CSS 변수 토큰 사용 여부, 하드코딩 HEX 없는지
2. 타이포그래피: 타입 스케일 준수
3. 스페이싱: 4px 스케일 준수
4. 반응형: 브레이크포인트 대응
5. 다크모드: .dark 클래스 + CSS 변수 동작
6. 접근성: color contrast 4.5:1 이상
7. 컴포넌트: variant/size 시스템 준수
8. 모션: duration/easing 스케일 준수
9. 코드: cn(), forwardRef, import 순서
### 1-11. docs/design/prompts/refactor-style.md
스타일 리팩토링 프롬프트 템플릿:
[파일/컴포넌트] 스타일을 디자인 시스템으로 리팩토링해줘.
- 하드코딩 색상 → CSS 변수 토큰
- Tailwind 기본 색상(bg-gray-, text-blue-) → 커스텀 토큰
- spacing 임의값 → 스케일 값
- docs/design/ 가이드 기준으로 검증
## 2. frontend/src/index.css 수정
현재 내용 유지하면서, `@import 'tailwindcss';` 뒤에 `@theme` 블록과 다크모드 블록을 추가해줘:
```css
@import 'tailwindcss';
@custom-variant dark (&:where(.dark, .dark *));
@theme {
/* === Brand: Primary (Slate Blue) === */
--color-primary-50: #F5F7F9;
--color-primary-100: #E5EBF2;
--color-primary-200: #D2DAE5;
--color-primary-300: #B7C5D7;
--color-primary-400: #8AA5C7;
--color-primary-500: #6D94C5;
--color-primary-600: #507FB9;
--color-primary-700: #3B669C;
--color-primary-800: #2D507B;
--color-primary-900: #1B2C41;
--color-primary-950: #0E1A2B;
/* === Brand: Secondary (Powder Blue) === */
--color-secondary-50: #F5F7F9;
--color-secondary-100: #E6EDF5;
--color-secondary-200: #D1DAE5;
--color-secondary-300: #B7C8D7;
--color-secondary-400: #89AAC8;
--color-secondary-500: #CBDCEB;
--color-secondary-600: #6B9AC8;
--color-secondary-700: #4E88BB;
--color-secondary-800: #396E9D;
--color-secondary-900: #1B2F41;
--color-secondary-950: #0E1A2B;
/* === Brand: Accent (Warm Sand) === */
--color-accent-50: #F9F8F6;
--color-accent-100: #F2EDE4;
--color-accent-200: #E4E0D7;
--color-accent-300: #D5CDB9;
--color-accent-400: #C4B48C;
--color-accent-500: #E8DFCA;
--color-accent-600: #B59854;
--color-accent-700: #9A7E3E;
--color-accent-800: #786230;
--color-accent-900: #3F351D;
--color-accent-950: #2B2312;
/* === Semantic === */
--color-success: #059669;
--color-warning: #D97706;
--color-danger: #DC2626;
--color-info: #0284C7;
/* === Neutral (Light defaults) === */
--color-bg-base: #F5EFE6;
--color-bg-surface: #FFFFFF;
--color-bg-elevated: #FFFFFF;
--color-border: #D5D2CC;
--color-border-strong: #9198A1;
--color-text-primary: #1E2329;
--color-text-secondary: #5C6570;
--color-text-tertiary: #9198A1;
/* === Design Tokens (Light defaults) === */
--color-primary: #507FB9;
--color-primary-hover: #3B669C;
--color-primary-active: #2D507B;
--color-primary-subtle: #F5F7F9;
--color-primary-text: #2D507B;
--color-secondary: #CBDCEB;
--color-secondary-hover: #89AAC8;
--color-secondary-active: #4E88BB;
--color-secondary-subtle: #F5F7F9;
--color-secondary-text: #396E9D;
--color-accent: #E8DFCA;
--color-accent-hover: #C4B48C;
--color-accent-active: #B59854;
--color-accent-subtle: #F9F8F6;
--color-accent-text: #786230;
/* === Chart Palette === */
--color-chart-1: #507FB9;
--color-chart-2: #B59854;
--color-chart-3: #B5607D;
--color-chart-4: #3D998A;
--color-chart-5: #8B6DB5;
--color-chart-6: #C07850;
/* === Typography === */
--font-sans: 'Pretendard Variable', Pretendard, -apple-system, BlinkMacSystemFont, system-ui, Roboto, 'Helvetica Neue', 'Segoe UI', 'Apple SD Gothic Neo', 'Noto Sans KR', 'Malgun Gothic', 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol', sans-serif;
--font-mono: 'JetBrains Mono', 'Fira Code', Consolas, Monaco, 'Courier New', monospace;
}
/* === Dark Mode === */
@media (prefers-color-scheme: dark) {
:root:not(.light) {
--color-success: #34D399;
--color-warning: #FBBF24;
--color-danger: #FCA5A5;
--color-info: #38BDF8;
--color-bg-base: #131416;
--color-bg-surface: #1E2023;
--color-bg-elevated: #282A2E;
--color-border: #3A3C41;
--color-border-strong: #5C6570;
--color-text-primary: #F4F5F5;
--color-text-secondary: #9198A1;
--color-text-tertiary: #5C6570;
--color-primary: #B7C5D7;
--color-primary-hover: #D2DAE5;
--color-primary-active: #8AA5C7;
--color-primary-subtle: #1B2C41;
--color-primary-text: #D2DAE5;
--color-secondary: #B7C8D7;
--color-secondary-hover: #D1DAE5;
--color-secondary-active: #89AAC8;
--color-secondary-subtle: #1B2F41;
--color-secondary-text: #D1DAE5;
--color-accent: #D5CDB9;
--color-accent-hover: #E4E0D7;
--color-accent-active: #C4B48C;
--color-accent-subtle: #3F351D;
--color-accent-text: #E4E0D7;
--color-chart-1: #6D94C5;
--color-chart-2: #C4B48C;
--color-chart-3: #D4839B;
--color-chart-4: #5BB5A6;
--color-chart-5: #B79FD4;
--color-chart-6: #D4956B;
}
}
.dark {
--color-success: #34D399;
--color-warning: #FBBF24;
--color-danger: #FCA5A5;
--color-info: #38BDF8;
--color-bg-base: #131416;
--color-bg-surface: #1E2023;
--color-bg-elevated: #282A2E;
--color-border: #3A3C41;
--color-border-strong: #5C6570;
--color-text-primary: #F4F5F5;
--color-text-secondary: #9198A1;
--color-text-tertiary: #5C6570;
--color-primary: #B7C5D7;
--color-primary-hover: #D2DAE5;
--color-primary-active: #8AA5C7;
--color-primary-subtle: #1B2C41;
--color-primary-text: #D2DAE5;
--color-secondary: #B7C8D7;
--color-secondary-hover: #D1DAE5;
--color-secondary-active: #89AAC8;
--color-secondary-subtle: #1B2F41;
--color-secondary-text: #D1DAE5;
--color-accent: #D5CDB9;
--color-accent-hover: #E4E0D7;
--color-accent-active: #C4B48C;
--color-accent-subtle: #3F351D;
--color-accent-text: #E4E0D7;
--color-chart-1: #6D94C5;
--color-chart-2: #C4B48C;
--color-chart-3: #6B9AC8;
--color-chart-4: #B59854;
--color-chart-5: #8AA5C7;
--color-chart-6: #D5CDB9;
}
/* Dark mode date input calendar icon */
.dark input[type="date"]::-webkit-calendar-picker-indicator {
filter: invert(1);
}
3. cn() 유틸리티 생성
frontend/src/utils/cn.ts 파일을 생성:
import { type ClassValue, clsx } from 'clsx';
import { twMerge } from 'tailwind-merge';
export const cn = (...inputs: ClassValue[]) => twMerge(clsx(inputs));
clsx와 tailwind-merge 패키지가 없으면 설치해줘:
cd frontend && npm install clsx tailwind-merge
4. 차트 팔레트 상수 파일 생성
frontend/src/constants/chart.ts:
export const CHART_COLORS = [
'var(--color-chart-1)',
'var(--color-chart-2)',
'var(--color-chart-3)',
'var(--color-chart-4)',
'var(--color-chart-5)',
'var(--color-chart-6)',
] as const;
/** CSS computed value가 필요한 경우 (Recharts 등) */
export const CHART_COLORS_HEX = {
light: ['#507FB9', '#B59854', '#B5607D', '#3D998A', '#8B6DB5', '#C07850'],
dark: ['#6D94C5', '#C4B48C', '#D4839B', '#5BB5A6', '#B79FD4', '#D4956B'],
} as const;
5. CLAUDE.md에 디자인 가이드 참조 추가
CLAUDE.md의 ## 팀 규칙 섹션 아래에 다음을 추가:
## 디자인 시스템
- 컬러 시스템: `docs/design/colors.md`
- 타이포그래피: `docs/design/typography.md`
- 스페이싱/레이아웃: `docs/design/spacing.md`
- 컴포넌트 스펙: `docs/design/components.md`
- 아이콘: `docs/design/icons.md`
- 모션: `docs/design/motion.md`
- 코드 컨벤션: `docs/design/code-conventions.md`
- Do/Don't: `docs/design/do-dont.md`
### 프롬프트 템플릿
- 새 컴포넌트: `docs/design/prompts/new-component.md`
- 리뷰 체크리스트: `docs/design/prompts/review-checklist.md`
- 스타일 리팩토링: `docs/design/prompts/refactor-style.md`
### 핵심 규칙
- 색상은 반드시 CSS 변수 토큰 사용 (하드코딩 HEX 금지)
- 브랜드 컬러: Primary #6D94C5(Slate Blue), Secondary #CBDCEB(Powder Blue), Accent #E8DFCA(Warm Sand), BG #F5EFE6(Warm Cream)
- 다크모드: `.dark` 클래스 + CSS 변수 자동 전환
- 차트: CHART_COLORS_HEX 상수 사용 (Cool+Warm 교차 배치)
- Tailwind 기본 색상(gray-*, blue-* 등) 대신 커스텀 토큰 사용
6. 빌드 검증
모든 파일 생성 후:
cd frontend && npm run build로 프론트엔드 빌드 성공 확인- 에러 없으면 커밋:
- 1차 커밋:
docs(design): 디자인 시스템 가이드 문서 추가 - 2차 커밋:
feat(frontend): 디자인 토큰 및 테마 시스템 적용
- 1차 커밋:
주의사항
- 기존 컴포넌트의 하드코딩 색상(bg-gray-900, text-blue-500 등)은 이번 작업에서는 변경하지 않는다 (별도 리팩토링 예정)
- ThemeContext.tsx는 이미 존재하므로 수정하지 않는다
@theme블록은 반드시@import 'tailwindcss';뒤,@custom-variant뒤에 위치해야 한다- npm 레지스트리는 frontend/.npmrc에 설정된 Nexus 프록시를 사용한다
---
**사용법:** 위의 ` ``` ` 블록 안의 전체 내용을 복사하여 Claude Code에 프롬프트로 입력하세요.