Initialize sample Nuxt project with TypeScript and Tailwind CSS, including .gitignore, package.json, and configuration files. Add CLAUDE.md for project guidelines and structure, and implement basic app.vue layout. Create submodule configuration in .gitmodules and add project-specific architecture and conventions documentation.

This commit is contained in:
hyeonggil
2026-04-11 19:33:24 +09:00
commit 76e52e195a
12 changed files with 320 additions and 0 deletions

View File

@@ -0,0 +1,39 @@
# 아키텍처 (Sample)
## 레이어 구조
```
┌───────────────────────────────────┐
│ pages (Nuxt) │ ← 라우팅, 데이터 페칭 진입점
├───────────────────────────────────┤
│ components │ ← 재사용 UI (도메인/공용 분리)
├───────────────────────────────────┤
│ composables (use*) │ ← 상태 + 로직 (뷰 독립)
├───────────────────────────────────┤
│ composables/api (wrapper) │ ← 서버 통신 단일 창구
├───────────────────────────────────┤
│ server/api │ ← Nuxt 서버 라우트
└───────────────────────────────────┘
```
## 규칙
- 하위 레이어는 상위 레이어를 import 할 수 없습니다. (단방향 의존)
- `components` 는 비즈니스 로직을 직접 수행하지 않고, composable 에 위임합니다.
- 전역 상태는 필요한 경우에만 Pinia store 로 승격합니다.
## 데이터 흐름
1. 사용자 이벤트 → `components` 에서 `composable` 호출
2. `composable``composables/api` 래퍼 호출
3. 래퍼 → `$fetch` 로 Nuxt `server/api` 또는 외부 API 요청
4. 응답은 타입이 보장된 상태로 composable → component 로 전달
## 상태 관리 가이드
| 상태 종류 | 권장 위치 |
| -------------------- | ------------------------ |
| 컴포넌트 로컬 상태 | `ref` / `reactive` |
| 페이지 단위 공유 상태| `provide/inject` 또는 composable |
| 앱 전역 상태 | Pinia store |
| 서버 데이터 | `useAsyncData`/`useFetch`|

View File

@@ -0,0 +1,34 @@
# 프로젝트 전용 컨벤션 (Sample)
공통 지침(`.claude/common/`) 외에 **이 프로젝트에서만** 적용되는 규칙을 정의합니다.
공통 지침과 충돌할 경우 이 문서가 우선합니다.
## 디렉토리 규칙
- `components/` — 재사용 컴포넌트. 도메인별 하위 폴더(`user/`, `order/`)로 분리
- `composables/``useXxx` 형태의 재사용 로직
- `pages/` — Nuxt 파일 기반 라우팅
- `server/api/` — 서버 라우트 핸들러
- `types/` — 전역/공통 타입 정의
## 컴포넌트 규칙 (오버라이드)
- 이 프로젝트에서는 컴포넌트 파일 길이를 **150줄**로 제한합니다. (공통 200줄보다 엄격)
- 컴포넌트 당 `defineProps` 의 항목은 **최대 7개**. 초과 시 객체 props 로 묶습니다.
## Tailwind
- 색상은 `tailwind.config.ts``theme.extend.colors` 에 등록된 토큰만 사용합니다.
(임의 색상 사용 금지)
- 다크모드 클래스 prefix 는 `dark:` 를 사용합니다.
## 네트워크
- API 호출은 반드시 `composables/api/` 의 래퍼를 통해 수행합니다.
- 직접 `$fetch` / `fetch` 사용은 금지 (테스트 목적 제외).
## 테스트
- Vitest 를 기본 테스트 러너로 사용합니다.
- 테스트 파일은 소스 옆에 `*.spec.ts` 로 배치합니다.
- 공통 유틸과 composable 은 테스트 커버리지 80% 이상을 유지합니다.

View File

@@ -0,0 +1,27 @@
# 프로젝트 개요 (Sample)
## 서비스
- **이름**: Sample Nuxt App
- **설명**: fe-common-rules 도입 예시용 샘플 프로젝트
- **배포 환경**: 로컬 전용 (샘플)
## 기술 스택
- **Framework**: Nuxt 4
- **UI**: Vue 3 (`<script setup lang="ts">`)
- **Language**: TypeScript (strict)
- **Styling**: Tailwind CSS
- **상태관리**: Pinia (필요 시)
- **패키지매니저**: pnpm
## 주요 기능 (예시)
- 메인 페이지 (`/`)
- 샘플 컴포넌트 `HelloCard.vue`
- 공통 지침을 활용한 린트/타입 검증
## 팀 / 오너
- Frontend Team
- 문의: #fe-chapter (Slack)

24
.gitignore vendored Normal file
View File

@@ -0,0 +1,24 @@
# Nuxt dev/build outputs
.output
.data
.nuxt
.nitro
.cache
dist
# Node dependencies
node_modules
# Logs
logs
*.log
# Misc
.DS_Store
.fleet
.idea
# Local env files
.env
.env.*
!.env.example

7
.gitmodules vendored Normal file
View File

@@ -0,0 +1,7 @@
# 실제 프로젝트에서는 이 파일이 .gitmodules 로 생성됩니다.
# git submodule add <repo-url> .claude/common 명령 실행 후 자동 생성되며,
# 아래와 같은 형태로 저장됩니다. (샘플은 실제 submodule 이 아니므로 예시로 포함)
[submodule ".claude/common"]
path = .claude/common
url = http://gilnas.synology.me:3000/gil/fe-common-rules.git
branch = main

16
CLAUDE.md Normal file
View File

@@ -0,0 +1,16 @@
# sample-nuxt-project
Nuxt 4 + Vue 3 + TypeScript + Tailwind CSS 기반의 샘플 프로젝트입니다.
이 프로젝트는 `fe-common-rules` 공통 지침을 submodule 형태로 연결하여 사용합니다.
## 공통 지침
@.claude/common/CLAUDE.md
## 프로젝트 지침
@.claude/project/overview.md
@.claude/project/conventions.md
@.claude/project/architecture.md

81
README.md Normal file
View File

@@ -0,0 +1,81 @@
# sample-nuxt-project
`fe-common-rules` 공통 지침을 실제 프로젝트에서 어떻게 사용하는지 보여주는 **샘플**입니다.
> 💡 이 샘플은 실제로 실행 가능한 Nuxt 앱이 아니라, **디렉토리 구조와 CLAUDE.md 연동 방식**을 보여주기 위한 최소 구성입니다.
## 구조
```
sample-nuxt-project/
├── CLAUDE.md # 공통 + 프로젝트 지침 @import 엔트리
├── .claude/
│ ├── common/ # fe-common-rules submodule (샘플에서는 파일 복제)
│ │ ├── CLAUDE.md
│ │ ├── rules/
│ │ │ ├── coding-conventions.md
│ │ │ ├── framework-rules.md
│ │ │ ├── commit-pr.md
│ │ │ └── claude-workflow.md
│ │ └── scripts/
│ │ ├── install.sh
│ │ └── update.sh
│ └── project/ # 프로젝트 고유 지침
│ ├── overview.md
│ ├── conventions.md
│ └── architecture.md
├── package.json # Nuxt 4 + Vue 3 + TS + Tailwind 의존성
├── nuxt.config.ts
├── tsconfig.json
├── tailwind.config.ts
├── app.vue
└── .gitignore
```
## 실제 프로젝트에서는 어떻게 만드나요?
실제 프로젝트에서는 `.claude/common/`**submodule** 로 연결합니다.
```bash
# 1) Nuxt 프로젝트 초기화 (이미 존재한다면 생략)
npx nuxi@latest init my-project
cd my-project
git init && git add . && git commit -m "chore: init"
# 2) fe-common-rules 를 submodule 로 추가
git submodule add git@github.com:<팀-조직>/fe-common-rules.git .claude/common
git submodule update --init --recursive
# 3) 프로젝트 CLAUDE.md 작성
# (이 샘플의 CLAUDE.md 를 참고하세요)
```
또는 `fe-common-rules` 저장소의 `scripts/install.sh` 를 사용하면 submodule 추가와
`CLAUDE.md` 템플릿 생성을 한 번에 할 수 있습니다.
```bash
curl -fsSL https://<raw-url>/scripts/install.sh | bash -s -- git@github.com:<팀-조직>/fe-common-rules.git
```
## 공통 지침 업데이트
```bash
git submodule update --remote --merge .claude/common
git add .claude/common
git commit -m "chore: update fe-common-rules submodule"
```
또는
```bash
bash .claude/common/scripts/update.sh
```
## Claude 가 읽는 순서
1. Nuxt 루트의 `CLAUDE.md` 를 먼저 읽습니다.
2. `@.claude/common/CLAUDE.md` 구문으로 공통 지침 엔트리가 로드됩니다.
3. 엔트리 내부의 `@rules/*.md` 가 차례로 로드됩니다.
4. 이어서 `@.claude/project/*.md` (overview, conventions, architecture) 가 로드됩니다.
5. Claude는 로드된 모든 지침을 참고하여 작업을 수행합니다.
6. 충돌이 있을 경우 **프로젝트 지침이 우선**합니다.

15
app.vue Normal file
View File

@@ -0,0 +1,15 @@
<script setup lang="ts">
const title = 'fe-common-rules 연동 샘플'
</script>
<template>
<div class="flex min-h-screen items-center justify-center bg-brand-50">
<div class="rounded-2xl bg-white px-8 py-10 shadow-md">
<h1 class="text-2xl font-bold text-brand-700">{{ title }}</h1>
<p class="mt-2 text-slate-600">
공통 지침은 <code>.claude/common</code>,
프로젝트 지침은 <code>.claude/project</code> 에서 확인하세요.
</p>
</div>
</div>
</template>

19
nuxt.config.ts Normal file
View File

@@ -0,0 +1,19 @@
// https://nuxt.com/docs/api/configuration/nuxt-config
export default defineNuxtConfig({
compatibilityDate: '2025-01-01',
devtools: { enabled: true },
modules: ['@nuxtjs/tailwindcss'],
typescript: {
strict: true,
typeCheck: true,
},
app: {
head: {
title: 'Sample Nuxt Project',
meta: [
{ charset: 'utf-8' },
{ name: 'viewport', content: 'width=device-width, initial-scale=1' },
],
},
},
})

27
package.json Normal file
View File

@@ -0,0 +1,27 @@
{
"name": "sample-nuxt-project",
"private": true,
"type": "module",
"scripts": {
"dev": "nuxt dev",
"build": "nuxt build",
"preview": "nuxt preview",
"lint": "eslint .",
"format": "prettier --write .",
"typecheck": "nuxt typecheck"
},
"dependencies": {
"nuxt": "^4.0.0",
"vue": "^3.5.0"
},
"devDependencies": {
"@nuxtjs/tailwindcss": "^6.12.0",
"@types/node": "^20.0.0",
"eslint": "^9.0.0",
"prettier": "^3.3.0",
"prettier-plugin-tailwindcss": "^0.6.0",
"tailwindcss": "^3.4.0",
"typescript": "^5.5.0",
"vitest": "^2.0.0"
}
}

22
tailwind.config.ts Normal file
View File

@@ -0,0 +1,22 @@
import type { Config } from 'tailwindcss'
export default {
content: [
'./components/**/*.{vue,js,ts}',
'./layouts/**/*.vue',
'./pages/**/*.vue',
'./app.vue',
],
theme: {
extend: {
colors: {
brand: {
50: '#eef2ff',
500: '#6366f1',
700: '#4338ca',
},
},
},
},
plugins: [],
} satisfies Config

9
tsconfig.json Normal file
View File

@@ -0,0 +1,9 @@
{
"extends": "./.nuxt/tsconfig.json",
"compilerOptions": {
"strict": true,
"noImplicitAny": true,
"noUnusedLocals": true,
"noUnusedParameters": true
}
}