# 积分体系模块 ## 概述 积分体系是追光AI的用户激励核心,包含20级成长系统、积分奖励引擎、积分商店、签到连击和Streak冻结保护,通过游戏化机制提升用户活跃度和留存率。 ## 积分规则 | 行为 | 积分 | 每日上限 | |------|------|----------| | 发表评论 | +5 | 50 | | 评论被点赞 | +2 | 20 | | 发布论坛话题 | +10 | 无限制 | | 论坛回复 | +5 | 30 | | 发表评价 | +8 | 20 | | 每日签到 | +1 (递增) | 1 | | 签到连击 bonus | 连续7天+3, 连续30天+10 | - | --- ## 等级系统 - 20级成长体系 ### 等级配置 - **配置文件**: `src/lib/level-config.ts` — 客户端安全(无Prisma依赖) - 等级范围: LV01(0分) → LV20(50000分) - 等级图标: ⭐(初级) → ⭐⭐⭐(中级) → 🌟(高级) → 🌟🌟(精英) → 🌟🌟🌟(大师) ### 等级表 | 等级 | 最低积分 | 徽章 | 每日限额 | |------|----------|------|----------| | LV01 | 0 | ⭐ | 50 | | LV02 | 10 | ⭐ | 80 | | LV03 | 30 | ⭐⭐ | 100 | | LV04 | 60 | ⭐⭐ | 120 | | LV05 | 100 | ⭐⭐ | 150 | | LV06 | 200 | ⭐⭐⭐ | 180 | | LV07 | 400 | ⭐⭐⭐ | 200 | | LV08 | 700 | ⭐⭐⭐ | 250 | | LV09 | 1000 | ⭐⭐⭐ | 300 | | LV10 | 1500 | 🌟 | 400 | | LV11 | 2000 | 🌟 | 500 | | LV12 | 3000 | 🌟 | 600 | | LV13 | 4500 | 🌟 | 700 | | LV14 | 6000 | 🌟🌟 | 800 | | LV15 | 8000 | 🌟🌟 | 1000 | | LV16 | 11000 | 🌟🌟 | 1200 | | LV17 | 15000 | 🌟🌟 | 1500 | | LV18 | 20000 | 🌟🌟🌟 | 1800 | | LV19 | 30000 | 🌟🌟🌟 | 2000 | | LV20 | 50000 | 🌟🌟🌟 | 3000 | ### 旧等级迁移映射 BRONZE→LV01, SILVER→LV03, GOLD→LV06, PLATINUM→LV10 ### 积分奖励引擎 - **文件**: `src/lib/points-reward.ts` - `rewardPoints()` — 自动发放积分 + 日限额检查 + 事务写入 - `getUserStats()` — 获取用户综合统计(积分/评论数/话题数等) - `getUserPointsHistory()` — 积分历史分页查询 --- ## 签到系统 ### 每日签到 - 基础+1分,连续签到递增奖励 - 连续7天: +3 bonus - 连续30天: +10 bonus - 中断重置 ### CheckInCard 组件 - 位置: 用户中心顶部 - 功能: 签到按钮、连击天数显示、季度签到日历 --- ## Streak 冻结保护 ### 功能说明 - 用户可通过积分商店购买 Streak Freeze 卡片 - 当用户某天未签到时,自动消耗一张 Freeze 卡保护连击不断 - 最多持有 3 张 Freeze 卡 ### 核心库 - **文件**: `src/lib/streak-freeze.ts` - `checkAndApplyFreeze(userId)` — 检查是否需要冻结并自动应用 - `getFreezeCardCount(userId)` — 获取当前持有数量 - `useFreezeCard(userId)` — 消耗一张冻结卡 ### 定时任务 - **脚本**: `scripts/grant-freeze-cards.mjs` - 定期为活跃用户发放 Freeze 卡(每日01:00) --- ## 积分商店 ### 功能概述 用户可使用积分兑换虚拟物品和社区权益。 ### 商品定义 - **文件**: `src/lib/shop-items.ts` - 商品类型: 头像框、昵称颜色、特效道具、Streak Freeze 卡 ### API 接口 | 路由 | 方法 | 功能 | |------|------|------| | /api/user/shop/items | GET | 获取可购买商品列表 | | /api/user/shop/purchase | POST | 购买商品(扣积分) | | /api/user/shop/my-items | GET | 获取用户已购物品 | ### 前端组件 - 积分商店页面(用户中心入口) - 商品卡片(名称/图标/价格/库存/购买按钮) - 已购物品展示(个人中心装饰效果) --- ## 数据模型 ### PointsHistory (积分历史) | 字段 | 类型 | 说明 | |------|------|------| | id | Int @id | 主键 | | userId | Int | 用户ID | | points | Int | 积分变动(正数获得/负数消耗) | | reason | String | 积分原因 | | detail | String? | 详细信息 | | refType | String? | 关联类型 | | refId | Int? | 关联ID | | createdAt | DateTime | 创建时间 | ### StreakFreeze (冻结卡) 🆕 | 字段 | 类型 | 说明 | |------|------|------| | id | Int @id | 主键 | | userId | Int | 用户ID | | cardCount | Int | 持有数量 | | lastUsedAt | DateTime? | 最近使用时间 | | createdAt | DateTime | 创建时间 | ### UserShopItem (已购物品) 🆕 | 字段 | 类型 | 说明 | |------|------|------| | id | Int @id | 主键 | | userId | Int | 用户ID | | itemId | String | 商品ID | | purchasedAt | DateTime | 购买时间 | | isActive | Boolean | 是否启用/佩戴 | --- ## 前端组件 | 组件 | 文件 | 说明 | |------|------|------| | MemberBadge | `src/components/common/MemberBadge.tsx` | 会员等级徽章(⭐🌟 + 积分显示,3种尺寸) | | LevelProgress | `src/components/common/LevelProgress.tsx` | 等级进度条(当前/下一级/进度百分比,动态变色) | | CheckInCard | `src/components/common/CheckInCard.tsx` | 签到卡片(签到按钮/连击天数/季度日历) | --- ## 技术实现要点 ### 积分自动奖励机制 所有评论/发帖/点赞操作自动通过 `rewardPoints()` 发放积分: - 每日上限检查(防刷分) - 事务写入(积分变更 + 历史记录同时写入) - 等级自动随积分变化更新 ### 日志分类 积分变动通过 `reason` 字段区分: - `comment` — 评论 - `comment_liked` — 评论被点赞 - `topic_create` — 发帖 - `reply` — 回复 - `review` — 评价 - `check_in` — 签到 - `shop_purchase` — 商店消费(负数)