- 后台全面引入 Naive UI 组件库,统一 UI 规范 - 前台 usePublicApi 切换到 API 调用(GET /api/content/[key]) - 前后台数据源统一(site_content 表) - 产品线统一管理(tour/camp/course 三套编辑器) - 产品数据归一化(itinerary/faq/pricing 格式统一) - 表单提交 API 改写入 submissions 表 - 新增 submissions 标记已读 API - site-content PUT 支持 upsert - 修复前台 bug(stories 路由冲突、占位符警告、selector breadcrumb) - 消除 PageHero 类型警告(useSEO reactive 修复) - 25 个前台页面全部 HTTP 200,展示效果不变 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
203 行
7.2 KiB
Markdown
203 行
7.2 KiB
Markdown
# 呼籁文旅官网 (hulai-website)
|
||
|
||
## 项目概述
|
||
|
||
呼籁文旅(呼伦贝尔旅行公司)的官方网站,包含前台展示和后台管理系统。
|
||
|
||
## 技术栈
|
||
|
||
| 层级 | 技术 | 版本 |
|
||
|------|------|------|
|
||
| 框架 | Nuxt 3 | 3.17.5 |
|
||
| 前端 | Vue 3 (Composition API + `<script setup>`) | — |
|
||
| 服务端 | Nitro (Nuxt 内置) | — |
|
||
| 数据库 | SQLite + better-sqlite3 | 12.8.0 |
|
||
| ORM | Drizzle ORM | 0.45.1 |
|
||
| 样式 | LESS (全局变量 + Mixins) | — |
|
||
| 包管理 | pnpm | — |
|
||
|
||
## 项目结构
|
||
|
||
```
|
||
hulai-website/
|
||
├── assets/less/ # 全局 LESS 变量和 Mixins
|
||
├── components/
|
||
│ ├── admin/ # 后台复用组件
|
||
│ │ ├── DataTable.vue # 分页表格(搜索、分页、sticky 表头、插槽)
|
||
│ │ ├── ImageUpload.vue # 图片上传(拖拽、预览、URL 输入)
|
||
│ │ └── SeasonProduct.vue # 季节产品编辑器
|
||
│ └── ... # 前台组件
|
||
├── composables/
|
||
│ ├── useAdmin.js # 后台认证(token 管理、adminFetch)
|
||
│ ├── usePublicApi.js # 前台 API
|
||
│ └── useSEO.js # SEO 配置
|
||
├── layouts/
|
||
│ ├── admin.vue # 后台布局(侧栏 + 内容区)
|
||
│ └── default.vue # 前台布局
|
||
├── middleware/
|
||
│ └── admin.js # 后台路由守卫
|
||
├── pages/
|
||
│ ├── admin/ # 后台页面
|
||
│ │ ├── login.vue # 登录页(无 layout)
|
||
│ │ ├── index.vue # 仪表盘
|
||
│ │ ├── articles/ # 新闻管理(index.vue 列表 + [id].vue 编辑)
|
||
│ │ ├── blogs/ # 博客管理
|
||
│ │ ├── reviews/ # 评论管理
|
||
│ │ ├── faqs/ # FAQ 管理
|
||
│ │ ├── gallery/ # 图库管理
|
||
│ │ ├── stories/ # 故事管理
|
||
│ │ ├── submissions/ # 表单提交(只读)
|
||
│ │ ├── navigation.vue # 导航菜单编辑
|
||
│ │ └── content/ # 站点内容编辑
|
||
│ │ ├── [key].vue # JSON 编辑器(兜底)
|
||
│ │ ├── products/ # 夏季产品(index + [idx])
|
||
│ │ ├── autumn-products/
|
||
│ │ ├── winter-products/
|
||
│ │ ├── pricing/ # 价格配置
|
||
│ │ ├── selector/ # 产品选择器
|
||
│ │ ├── destinations-detail/
|
||
│ │ └── *.vue # 各内容可视化编辑器
|
||
│ └── ... # 前台页面
|
||
├── server/
|
||
│ ├── api/admin/ # 后台 REST API
|
||
│ ├── database/
|
||
│ │ ├── schema.js # Drizzle 表定义
|
||
│ │ ├── index.js # DB 连接单例
|
||
│ │ ├── migrate.js # 建表
|
||
│ │ └── seed.js # 种子数据(从 JSON 导入)
|
||
│ └── utils/
|
||
│ ├── auth.js # Session 管理(SQLite 存储,7 天过期)
|
||
│ ├── db.js # useDB() 服务端工具
|
||
│ ├── pagination.js # parsePagination() 分页参数解析
|
||
│ └── ...
|
||
└── public/uploads/ # 上传文件存储
|
||
```
|
||
|
||
## 多角色 Agent 工作流
|
||
|
||
本项目使用 5 个协作 Agent,通过 `/workflow` 命令调度:
|
||
|
||
| 角色 | 职责 | 约束 |
|
||
|------|------|------|
|
||
| **PM** | 分析需求、拆解任务、分配执行、验收结果 | 只分析不写代码 |
|
||
| **Frontend** | 前端页面开发(Vue 组件、页面、样式) | 只改前端代码 |
|
||
| **Backend** | 后端 API、数据库、服务端逻辑 | 只改 server/ 代码 |
|
||
| **UI/UX** | 出设计方案、页面结构、交互规格 | 只出方案不写代码 |
|
||
| **Tester** | 代码审查、质量检测、出测试报告 | 只测不改 |
|
||
|
||
### 工作流阶段
|
||
|
||
```
|
||
Phase 1: PM 分析需求 → 拆解任务
|
||
Phase 2: UI/UX 设计(如有新页面)
|
||
Phase 3: Backend 开发(如有 API 变更)
|
||
Phase 4: Frontend 开发
|
||
Phase 5: Tester 测试验证
|
||
Phase 6: 修复闭环(最多 3 轮)
|
||
Phase 7: PM 验收 → 提交代码
|
||
```
|
||
|
||
### 命令
|
||
|
||
| 命令 | 用途 |
|
||
|------|------|
|
||
| `/workflow` | 全自动工作流,一条命令走完全流程 |
|
||
| `/pm` | 单独启动产品经理分析 |
|
||
| `/frontend` | 单独启动前端开发 |
|
||
| `/backend` | 单独启动后端开发 |
|
||
| `/uiux` | 单独启动 UI/UX 设计 |
|
||
| `/tester` | 单独启动测试验证 |
|
||
|
||
## 编码规范
|
||
|
||
### 前端页面(pages/admin/)
|
||
|
||
**列表 + 编辑分离模式:**
|
||
- 列表页:`index.vue`,使用 `AdminDataTable` 组件,带搜索、分页
|
||
- 编辑页:`[id].vue`(数据库表)或 `[idx].vue`(JSON 数组项)
|
||
- 面包屑导航 + 返回链接
|
||
- 底部 sticky 保存栏
|
||
|
||
**页面模板:**
|
||
```vue
|
||
<script setup>
|
||
definePageMeta({ layout: 'admin', middleware: 'admin' })
|
||
const { adminFetch } = useAdmin()
|
||
</script>
|
||
```
|
||
|
||
**API 调用统一用 `adminFetch`**,自动带 token、401 自动登出。
|
||
|
||
### 后端 API(server/api/admin/)
|
||
|
||
**认证中间件:**
|
||
```js
|
||
const user = await requireAdmin(event)
|
||
```
|
||
|
||
**分页查询:**
|
||
```js
|
||
const { page, limit, offset, search, sort } = parsePagination(event)
|
||
```
|
||
|
||
**响应格式(列表):**
|
||
```js
|
||
{ items: [...], total, page, limit, totalPages }
|
||
```
|
||
|
||
**响应格式(单条):**
|
||
```js
|
||
{ id, ...fields }
|
||
```
|
||
|
||
### 数据库(Drizzle ORM)
|
||
|
||
- 表定义在 `server/database/schema.js`
|
||
- 使用 `useDB()` 获取数据库实例
|
||
- 导入操作符:`import { eq, desc, like } from 'drizzle-orm'`
|
||
|
||
### 站点内容(site_content 表)
|
||
|
||
存储复杂 JSON 配置的键值对:
|
||
- 读取:`GET /api/admin/site-content?key=xxx`
|
||
- 更新:`PUT /api/admin/site-content` body: `{ key, data }`
|
||
- 单项读取:`GET /api/admin/site-content/item?key=xxx&index=0`
|
||
- 单项更新:`PUT /api/admin/site-content/item` body: `{ key, index, item }`
|
||
|
||
### 样式规范
|
||
|
||
**后台页面使用 scoped CSS**,主色调:
|
||
- 主色:`#3a7d44`(绿色)
|
||
- 悬停:`#2d6235`
|
||
- 文字:`#111827`
|
||
- 次要文字:`#6b7280`
|
||
- 边框:`#e5e7eb`
|
||
- 背景:`#f0f2f5`
|
||
|
||
**复用组件:**
|
||
- `AdminDataTable` — 带分页搜索的表格
|
||
- `AdminImageUpload` — 拖拽上传图片
|
||
- `AdminSeasonProduct` — 季节产品编辑器
|
||
|
||
### 命名约定
|
||
|
||
| 类型 | 命名 | 示例 |
|
||
|------|------|------|
|
||
| 页面文件 | kebab-case | `winter-products/` |
|
||
| 组件 | PascalCase | `DataTable.vue` |
|
||
| API 路由 | kebab-case | `site-content.get.js` |
|
||
| 数据库表 | camelCase (Drizzle) | `galleryItems` |
|
||
| CSS class | kebab-case | `.page-header` |
|
||
|
||
## 记忆系统
|
||
|
||
每个 Agent 有 4 个记忆文件,存储在 `.claude/agents/memory/{role}/` 下:
|
||
|
||
| 角色 | 文件 | 内容 |
|
||
|------|------|------|
|
||
| PM | decisions / patterns / lessons / priorities | 决策记录 / 业务模式 / 经验教训 / 优先级策略 |
|
||
| Frontend | patterns / pitfalls / components / pages | 代码模式 / 踩坑记录 / 组件清单 / 页面模式 |
|
||
| Backend | patterns / pitfalls / api-design / database | 代码模式 / 踩坑记录 / API 设计 / 数据库经验 |
|
||
| UI/UX | design-system / page-patterns / feedback / consistency | 设计系统 / 页面模式 / 反馈记录 / 一致性 |
|
||
| Tester | common-bugs / checklist / api-issues / quality-metrics | 常见 Bug / 检查清单 / API 问题 / 质量指标 |
|