173 lines
6.1 KiB
Markdown
173 lines
6.1 KiB
Markdown
# Frontend — Claude Code 项目指南
|
||
|
||
本文件为 Claude Code(及其它 AI Agent)提供前端项目的背景、结构说明和开发规范。
|
||
|
||
## 项目状态
|
||
|
||
**技术栈已确定,项目已初始化。**
|
||
|
||
| 维度 | 选型 |
|
||
|------|------|
|
||
| 框架 | React 18 + TypeScript 5 |
|
||
| 构建 | Vite 6 |
|
||
| UI 库 | Ant Design 5 + @ant-design/icons |
|
||
| 路由 | React Router 6 |
|
||
| 状态管理 | Zustand(客户端状态) |
|
||
| HTTP 客户端 | Axios(API 封装在 `src/api/`) |
|
||
|
||
## 定位
|
||
|
||
`frontend/` 是 asset_helper 的 **Web 管理后台**,调用后端 API(通过 Nginx 网关暴露)。
|
||
|
||
- 与 `backend/` 通过 HTTP/JSON 交互,遵循根目录 [CLAUDE.md](../CLAUDE.md) 中定义的跨端契约
|
||
- 与 `app/`(移动/桌面端)共享后端,但 UI 实现独立
|
||
- 当前为后台管理系统,后续可扩展为面向用户的 Web 端
|
||
|
||
## Docker 部署
|
||
|
||
前端**不再单独编排**,统一由项目根目录的 docker compose 一并启动。详见 [根目录 CLAUDE.md](../CLAUDE.md#部署)。
|
||
|
||
| 环境 | 启动命令(在项目根目录执行) | 访问地址 |
|
||
|------|------|---------|
|
||
| 正式 | `docker compose up -d --build` | `http://localhost:20080` |
|
||
| 测试 | `docker compose -f docker-compose.dev.yml up -d --build` | `http://localhost:18888` |
|
||
|
||
两套环境前端均为多阶段构建(Node 构建 → Nginx 静态托管),通过 Nginx 的 `location /api/` 反代到网关容器(服务名 `gateway`,同 Docker 网络内可达)。
|
||
|
||
## 与后端的协作约定
|
||
|
||
以下约定来自 [backend/CLAUDE.md](../backend/CLAUDE.md),前端调用时**必须遵守**:
|
||
|
||
### 1. 请求包装(注册/业务类接口)
|
||
|
||
```ts
|
||
interface ApiRequest<T> {
|
||
device: number; // 前端固定使用 Device.Web = 3
|
||
language: number; // 默认 Language.SimplifiedChinese = 1
|
||
data: T; // 业务字段
|
||
}
|
||
```
|
||
|
||
**device 编码:**
|
||
- `1` = iOS、`2` = Android、`3` = Web ← **前端使用此值**
|
||
- `4` = iPad、`5` = macOS、`6` = Windows、`7` = Linux
|
||
|
||
**language 编码:**
|
||
- `1` = 简体中文(默认)、`2` = 繁体中文、`3` = 英文
|
||
|
||
### 2. 响应包装
|
||
|
||
```ts
|
||
interface ApiResponse<T> {
|
||
success: boolean;
|
||
message: string;
|
||
data: T | null; // 失败时为 null
|
||
}
|
||
```
|
||
|
||
### 3. 登录/认证类接口(扁平响应)
|
||
|
||
```ts
|
||
interface LoginResponse {
|
||
success: boolean;
|
||
token: string | null; // JWT
|
||
message: string;
|
||
}
|
||
```
|
||
|
||
**JWT 存储策略**:存于 Zustand 内存中(页面刷新丢失,需重新登录)。如需持久化,可改为 localStorage,但需注意 XSS 风险。
|
||
|
||
### 4. 错误响应(HTTP 非 200)
|
||
|
||
```ts
|
||
interface ErrorResponse {
|
||
error: string;
|
||
message: string;
|
||
code: number;
|
||
}
|
||
```
|
||
|
||
## 目录结构
|
||
|
||
```
|
||
frontend/
|
||
├── docker/
|
||
│ ├── Dockerfile # 多阶段构建(Node 构建 + Nginx 静态托管)
|
||
│ └── nginx.conf # 生产 Nginx SPA 配置 + /api 反代到网关
|
||
├── src/
|
||
│ ├── api/
|
||
│ │ ├── client.ts # Axios 封装(device/language 注入、JWT、错误处理)
|
||
│ │ └── auth.ts # 认证相关 API
|
||
│ ├── components/ # 可复用 UI 组件(待扩展)
|
||
│ ├── hooks/ # 自定义 Hooks(待扩展)
|
||
│ ├── layouts/
|
||
│ │ └── MainLayout.tsx # 后台主布局(侧边栏 + 头部 + 内容区)
|
||
│ ├── pages/
|
||
│ │ ├── LoginPage.tsx # 登录页(账号/邮箱切换)
|
||
│ │ ├── DashboardPage.tsx # 仪表盘首页
|
||
│ │ └── NotFoundPage.tsx # 404
|
||
│ ├── router/
|
||
│ │ └── index.tsx # 路由配置(登录守卫 + 受保护路由)
|
||
│ ├── stores/
|
||
│ │ └── auth.ts # Zustand 认证状态(token + login/logout)
|
||
│ ├── types/
|
||
│ │ ├── api.ts # 通用 API 类型(device/language 枚举、包装类型)
|
||
│ │ └── auth.ts # 认证相关类型
|
||
│ ├── utils/
|
||
│ │ └── storage.ts # localStorage 封装(带前缀隔离)
|
||
│ ├── App.tsx # 根组件(ConfigProvider + RouterProvider)
|
||
│ └── main.tsx # 入口
|
||
├── index.html
|
||
├── package.json
|
||
├── tsconfig.json / tsconfig.app.json / tsconfig.node.json
|
||
└── vite.config.ts
|
||
```
|
||
|
||
> 编排文件已统一上移到项目根目录的 `docker-compose.yml` / `docker-compose.dev.yml`。
|
||
|
||
## API 调用规范
|
||
|
||
**必须使用封装函数,禁止直接 fetch/axios:**
|
||
|
||
```ts
|
||
// ✅ 业务接口(自动注入 device/language)
|
||
import { apiPost, apiGet } from '@/api/client'
|
||
const data = await apiPost<RequestType, ResponseType>('/api/v1/users/xxx', payload)
|
||
|
||
// ✅ 认证接口(扁平格式,不包装)
|
||
import { loginAccount } from '@/api/auth'
|
||
const result = await loginAccount({ account: 'xxx', password: 'xxx' })
|
||
```
|
||
|
||
## 代码风格
|
||
|
||
- 注释使用**中文**(与后端保持一致)
|
||
- TypeScript 类型与后端 Rust 结构体一一对齐,禁止 `any`
|
||
- API 调用集中在 `src/api/`,不在组件中直接写 axios
|
||
- 路由守卫在 `src/router/index.tsx` 中统一配置
|
||
|
||
## 常用命令
|
||
|
||
| 命令 | 说明 |
|
||
|------|------|
|
||
| `npm install` | 安装依赖(开发容器内自动执行) |
|
||
| `npm run dev` | 启动开发服务器(容器内) |
|
||
| `npm run build` | 生产构建 |
|
||
| `npm run preview` | 预览生产构建 |
|
||
|
||
## 开发环境
|
||
|
||
- 推荐:在项目根目录用 `docker compose -f docker-compose.dev.yml up -d --build` 启动整套测试环境,前端为 Nginx 静态托管,访问 `http://localhost:18888`
|
||
- 如需快速调试前端而不构建镜像,本目录下 `npm run dev` 可启动 Vite dev server(监听 `0.0.0.0:5173`),需自行确保后端网关在宿主机可达;可通过 `VITE_API_BASE_URL` 覆盖 proxy 目标
|
||
|
||
## 扩展指南
|
||
|
||
新增页面/功能时:
|
||
1. 先在 `types/` 定义与后端对齐的类型
|
||
2. 在 `api/` 添加调用封装(务必通过统一封装注入 `device`/`language`)
|
||
3. 在 `pages/` 创建页面组件
|
||
4. 在 `router/index.tsx` 添加路由
|
||
5. 如需加入侧边栏菜单,在 `layouts/MainLayout.tsx` 的 `menuItems` 中配置
|
||
|
||
发现重复逻辑时优先抽到 `utils/` 或自定义 Hook。
|