# 🔐 权限控制实施计划
## ✅ 已完成
### 1. 权限工具函数 (`lib/permissions.ts`)
- ✅ 创建 `permissions` 对象,包含所有权限检查函数
- ✅ 添加辅助函数:`getRoleDisplayName`、`getRoleDescription`、`getRolePermissions`
- ✅ 修复类型冲突问题
- ✅ 添加完整的中文注释
### 2. 首页 (`app/page.tsx`)
- ✅ 导入 `permissions`
- ✅ 更新"添加成员"按钮权限控制
---
## 🚧 进行中
### 3. 成员列表页 (`app/members/page.tsx`)
需要更新的按钮:
- [ ] 筛选按钮(所有人可见)
- [ ] 新增成员按钮 → `permissions.canCreate(role)`
- [ ] 在族谱图中定位按钮(所有人可见)
### 4. 成员详情页 (`app/members/[id]/page.tsx`)
需要更新的按钮:
- [ ] 添加父亲 → `permissions.canCreate(role)`
- [ ] 添加母亲 → `permissions.canCreate(role)`
- [ ] 添加子女 → `permissions.canCreate(role)`
- [ ] 添加配偶 → `permissions.canCreate(role)`
- [ ] 编辑 → `permissions.canUpdate(role)`
- [ ] 删除 → `permissions.canDeleteMember(role)`
- [ ] 打印(所有人可见)
- [ ] 分享(所有人可见)
### 5. 新增成员页 (`app/members/new/page.tsx`)
需要检查:
- [ ] 整个页面需要 `permissions.canCreate(role)` 权限
- [ ] 无权限时重定向
### 6. 族谱图页 (`app/tree/page.tsx`)
需要更新的按钮:
- [ ] 关系查询(所有人可见)
- [ ] 视图模式(所有人可见)
- [ ] 放大/缩小/重置(所有人可见)
- [ ] 导出图片 → `permissions.canExport(role)`
### 7. 关系计算页 (`app/relationship/page.tsx`)
需要检查:
- [ ] 所有按钮都是查询功能,所有人可见
### 8. 系统设置页 (`app/settings/page.tsx`)
需要更新的按钮:
- [ ] 导出数据 → `permissions.canExport(role)`
- [ ] 导入数据 → `permissions.canImport(role)`
- [ ] 导出GEDCOM → `permissions.canExport(role)`
- [ ] 导入GEDCOM → `permissions.canImport(role)`
- [ ] 清空数据 → `permissions.canClearData(role)`
- [ ] 清空日志 → `permissions.canClearData(role)`
- [ ] 修改密码(所有人可见)
### 9. 全局导航 (`components/site-header.tsx`)
需要更新的按钮:
- [ ] 删除家族树 → `permissions.canDeleteTree(role)`
- [ ] 创建新家族树 → `permissions.canCreateTree(role)`
- [ ] 搜索(所有人可见)
- [ ] 通知(所有人可见)
- [ ] 设置(所有人可见)
---
## 📝 待办事项
### API 层面权限验证
- [ ] `/api/trees/[treeId]/members` POST → 检查 EDITOR 权限
- [ ] `/api/trees/[treeId]/members/[memberId]` PATCH → 检查 EDITOR 权限
- [ ] `/api/trees/[treeId]/members/[memberId]` DELETE → 检查 EDITOR 权限
- [ ] `/api/trees/[treeId]` DELETE → 检查 OWNER 权限
- [ ] `/api/trees/[treeId]/invite` POST → 检查 OWNER 权限
- [ ] `/api/trees/[treeId]/collaborators/[collaboratorId]` DELETE → 检查 OWNER 权限
- [ ] `/api/trees/[treeId]/import` POST → 检查 EDITOR 权限
### 组件层面
- [ ] `components/members/member-form.tsx` → 检查编辑权限
- [ ] `components/tree/collaborator-dialog.tsx` → 检查 OWNER 权限
- [ ] `components/settings/activity-log-viewer.tsx` → 清空日志需要 OWNER 权限
### 测试
- [ ] 测试 OWNER 权限
- [ ] 测试 EDITOR 权限
- [ ] 测试 VIEWER 权限
- [ ] 测试权限边界情况
### 文档
- [ ] 更新用户手册
- [ ] 更新 API 文档
- [ ] 添加权限错误处理说明
---
## 🎯 实施优先级
### P0 - 立即实施(本次)
1. ✅ 创建权限工具函数
2. ✅ 更新首页
3. 🚧 更新成员列表页
4. 🚧 更新成员详情页
5. 🚧 更新系统设置页
### P1 - 短期实施(今天)
6. 更新全局导航
7. 更新新增成员页
8. 更新族谱图页
### P2 - 中期实施(本周)
9. API 层面权限验证
10. 组件层面权限控制
11. 错误处理和提示
### P3 - 长期实施(下周)
12. 完整测试
13. 文档更新
14. 性能优化
---
## 📋 代码模板
### 前端按钮权限控制
```tsx
// 导入权限函数
import { permissions } from "@/lib/permissions"
// 获取当前角色
const { currentTree } = useFamily()
const role = currentTree?.currentUserRole
// 条件渲染(推荐)
{permissions.canCreate(role) && (
)}
// 禁用状态
```
### API 权限验证
```typescript
// API 路由中
import { checkPermission } from "@/lib/permissions"
import { Role } from "@prisma/client"
export async function POST(request: Request) {
const session = await getServerSession(authOptions)
if (!session?.user?.id) {
return NextResponse.json({ error: "未授权" }, { status: 401 })
}
// 检查权限
const { hasPermission, role } = await checkPermission(
session.user.id,
treeId,
Role.EDITOR // 需要的最低权限
)
if (!hasPermission) {
return NextResponse.json({ error: "权限不足" }, { status: 403 })
}
// 执行操作...
}
```
---
## 🔍 检查清单
### 每个页面完成后检查
- [ ] 所有按钮都添加了权限控制
- [ ] 导入了 `permissions`
- [ ] 获取了 `role`
- [ ] 使用了正确的权限检查函数
- [ ] 测试了三种角色的显示效果
### 每个 API 完成后检查
- [ ] 添加了权限验证
- [ ] 返回了正确的错误码
- [ ] 添加了错误信息
- [ ] 测试了权限边界
---
**当前进度**: 2/9 页面完成 (22%)
**预计完成时间**: 今天晚上
**负责人**: System