fix: reduce signup bonus to ten points
This commit is contained in:
+2
-1
@@ -86,7 +86,7 @@
|
||||
| T-604 | 中文敏感词本地过滤(本地 keyword provider) | T-302, T-401 | 按 [`moderation.md`](moderation.md) 实施。**范围收紧**:T-604 只做输入 prompt 的本地敏感词快筛,不做云内容安全、不做输出审核、不做图片审核。**关键时序**:serializer 后先审 prompt,命中即 `400 content_blocked`;不得先下载 `image_url`,不得预扣点,不写 `CallRecord` / `PointsLedger`,不调上游。**核心实现**:新增 `apps.moderation`、`SensitiveWord` 模型/admin/迁移、keyword provider、归一化管线、Aho-Corasick matcher;`ahocorapy` 作为候选依赖,编码前必须验证 PyPI 可用性和 API 形状。**缓存**:matcher 进程内缓存,词库变更用共享 cache 版本号失效,不能只靠 `post_save` signal;生产依赖共享 cache。**配置**:`MODERATION_ENABLED=false` 默认 no-op;启用时 `MODERATION_PROVIDER=keyword`;MVP `SensitiveWord.action` 只支持 `block`。**验收**:`check`/`test` 全绿,覆盖 no-op、命中拦截且不扣点/不建记录/不调上游/不下载图片、归一化防绕过、词库变更后 matcher 重建;真实词库数据不进仓库,`__pycache__` 不进 Git | DONE |
|
||||
| T-606 | 公开首页 + 客户端下载入口 | T-501 | 给网站补「前门」并提供桌面端下载。**路由改造**:`/` 从「重定向到 `/dashboard`」改为**公开首页**(匿名可访问、不跳登录);已登录用户显示「进入控制台」,匿名显示「注册/登录 + 下载客户端」。**首页内容**(SSR 模板):项目一句话介绍(生成标题/图片、按点数计费)+ 三步上手(注册→充值→建 API Key→桌面端填 Key)+ 下载入口 + 文档链接。**`DownloadRelease` 模型**:`platform`(如 windows)、`version`、`file`(FileField,**前期存 `MEDIA_ROOT`、服务器托管**) + `external_url`(URLField 可选,**后续切对象存储/CDN 用,有则优先**)、`sha256`、`is_current`(每平台仅一个当前版本)、`release_notes`、时间戳;admin 可上传安装包并标记当前版本;迁移。**下载区块**:展示当前 release 的版本、下载按钮、**SHA256 校验值**、可选 release notes;无 current release 时优雅提示「暂未发布」。**托管策略**:**前期安装包放本服务器**(生产由 **Nginx 直接服务 media/下载文件、不走 Django**,与 T-403 static/media serving 一致,大文件不占 gunicorn worker);`external_url` 预留,后续切对象存储只改后台链接不改代码。**安全**:下载走 HTTPS,页面展示 SHA256 供校验;**代码签名**作为决策登记——未签名 Windows 安装包会被 SmartScreen 拦「未知发布者」、macOS 被 Gatekeeper 拦,首页先给「如何忽略警告」说明,正式签名后续补(挂 Backlog / deployment)。**含测试**:`/` 匿名 200 不跳登录、下载区展示当前 release、无 current release 优雅处理、已登录用户显示「进入控制台」。**视觉原型(已定 v1)**:按 `prototypes/cmhub-homepage-v1.svg` 落地——「生成台」方向:靛蓝=生成 / 琥珀=点数;Hero 为「商品图 + 一句话 → 吸睛标题 + 生成主图 + 点数计量」转化图;四步上手 01–04、两张能力卡、深色计费 band、下载区(版本/SHA256/未签名提示);配色、间距、结构照此原型转成 Django 模板(Bootstrap + 本地 static)。**视觉一致性(brand token)**:按 [`brand.md`](brand.md) 抽出共享 CSS 变量(如 `apps/portal/static/portal/brand.css`),**首页与现有 portal 页面(dashboard/记录/充值/API Key)一起套用同一套 token**(把配色/字体变量灌进现有 Bootstrap,各页只引用变量不散写 hex),确保落地页与登录后控制台风格一致——**不是只做漂亮首页**。验收 `check`/`test`/`init` 全绿并在 `../progress.md` 留证据 | DONE |
|
||||
| T-607 | 桌面端最新版本检查接口 | T-606 | 给桌面端自动检查更新提供只读 JSON 合约。**新增路由**:`GET /api/v1/client/releases/latest?platform=windows`,公开匿名可访问,**不需要 API Key、不读取用户、不扣点、不占用生成接口限流**;只返回发布元数据,不返回本地文件系统路径、后台 ID、内部状态或任何用户数据。**请求参数**:`platform` 支持 `windows` / `macos` / `linux`,缺省按 `windows`;非法平台返回 `400 bad_request`。**响应结构**:有当前版本时返回 `{platform, release:{version, download_url, sha256, release_notes, published_at}}`;无当前版本或当前版本没有下载地址时返回 `{platform, release:null, message:"暂未发布"}` 且 HTTP 200,方便客户端安静处理。**数据来源**:复用 `DownloadRelease`,只查 `platform + is_current=True`;`download_url` 继续按 `external_url` 优先,否则由 `file.url` 生成绝对 HTTPS URL;`published_at` 可先使用 `updated_at`。**缓存与安全**:可加短 TTL 公共缓存(如 60 秒);生产下载仍走 HTTPS + SHA256 校验;不得把 `MEDIA_ROOT` 或服务器路径暴露给客户端。**含测试**:匿名无 Key 可访问;当前 release 返回完整结构和绝对下载 URL;无 current release 返回 `release:null`;非法 platform 返回 400;`external_url` 优先于 `file`;响应不含本地路径、模型/密钥/用户字段;`check`/目标测试通过并在 `../progress.md` 留证据 | DONE |
|
||||
| T-608 | 新用户注册赠送 100 点试用点数 | T-501, T-203, T-401 | 把 2026-07-08 的产品口径落地为账本安全实现。**业务口径**:只对 T-608 上线后的新注册用户自动发放 100 点;历史用户是否补发不在本任务内,需单独审批和批处理任务。**数据与服务**:新增 `PointsLedger.ChangeType.SIGNUP_BONUS`(展示为注册赠点)和 MySQL 兼容的数据库级幂等兜底 `SignupBonusGrant(user UNIQUE)`,不要用 partial unique / 条件唯一约束;新增 `apps.billing.services.grant_signup_bonus(user, points=100)`,在事务内锁/创建钱包、发放点数、写 `PointsLedger(signup_bonus,+100,balance_after,reason)`,重复调用或并发触发不得重复发放。**接入点**:allauth adapter 注册成功后调用 billing 服务,不得在 portal 直接写 `points_balance`;失败要清晰暴露并保持注册 / 账务一致性。**页面与文案**:公开首页、注册页、dashboard/记录页等用户端文案同步「注册送 100 点」;点数记录页能展示注册赠点正向流水;admin 可检索该流水和注册赠点记录。**防刷**:免邮箱验证策略下显式配置 `ACCOUNT_SIGNUP_RATE_LIMIT`(默认 `20/m/ip`),由 allauth signup rate limit 执行;图形验证码 / 人机验证仍作为上线前风控增强项。**测试**:注册后余额为 100 且有一条 `signup_bonus` 流水;重复调用服务不重复加点;并发触发不重复发放;现有用户不会自动补发;dashboard / 点数记录显示一致;`check`/迁移/目标测试通过并在 `../progress.md` 留证据 | DONE |
|
||||
| T-608 | 新用户注册赠送试用点数(当前 10 点) | T-501, T-203, T-401 | 已完成:仅对 T-608 上线后的新注册用户,经 `apps.billing.services.grant_signup_bonus(user, points=10)` 一次性发放 10 点;历史用户不补发。服务在事务内锁/创建钱包、写 `SignupBonusGrant(user UNIQUE)` 幂等记录和 `PointsLedger(signup_bonus,+10,balance_after,reason)`,重复调用或并发触发不重复发放;allauth adapter 只调用 billing 服务,不直接改余额。公开首页、注册页、dashboard/点数记录页展示当前 10 点,admin 可检索记录;免邮箱验证下由 `ACCOUNT_SIGNUP_RATE_LIMIT=20/m/ip` 限制注册频率。已覆盖注册余额/流水、重复调用、并发幂等、页面文案和后台检索;当前默认值由 `billing.0009_signup_bonus_default_ten` 与服务默认参数共同保证。 | DONE |
|
||||
| T-609 | 桌面端版本检查接口增加强制更新标记 | T-607 | 在 `GET /api/v1/client/releases/latest?platform=windows` 的当前版本响应中,为 `release` 对象新增布尔字段 `force_update`,用于桌面端判断是否必须升级。**接口兼容**:只新增字段,不删除既有 `version` / `download_url` / `sha256` / `release_notes` / `published_at` 字段;无当前版本或无下载地址时仍返回 `release:null`,不返回 `force_update`。**数据来源**:在 `DownloadRelease` 增加 `force_update` 布尔字段,默认 `false`;django-admin 可编辑并在列表展示。**示例**:`{platform:"windows", release:{version:"0.1.1", download_url:"...0.1.1.zip", release_notes:"优化了ai模块的生图的功能", force_update:true}}`。**安全**:接口仍公开匿名只读,不读取用户、不扣点、不暴露后台 ID、本地文件路径或内部状态。**文档**:同步 `api.md`、`routes.md`、`04-architecture.md`、`current-state.md`、版本接口对接文档口径。**测试**:覆盖 `force_update=true` / 默认 `false`、无 current release 不返回该字段、响应字段白名单更新、admin 字段可见;`makemigrations` / `migrate` / `check` / 目标测试通过并在 `../progress.md` 留证据 | DONE |
|
||||
| T-610 | 首页导入模板下载入口 | T-606 | 在公开首页“下载客户端”按钮右侧新增“下载导入模板”链接,让用户下载桌面端导入商品数据使用的 Excel 模板。**产品口径**:模板下载是公开资源,匿名可见;不需要登录、不需要 API Key、不扣点、不占用生成接口限流。**后台配置**:新增独立 `ImportTemplate`(不要复用 `DownloadRelease`,两者生命周期不同),字段建议包含 `name`、`file`(FileField,`MEDIA_ROOT/import_templates/`)、`external_url`(可选,有则优先,后续切 CDN/对象存储)、`sha256`(可选)、`is_current`、`notes`、`created_at`、`updated_at`;admin 可上传/更新模板并标记当前模板;每次保存 current 时把其他 current 置为 false,避免使用 MySQL 不支持的条件唯一约束。**首页行为**:`HomeView` 同时读取 Windows 当前 `DownloadRelease` 和当前 `ImportTemplate`;有当前模板且有可下载地址时,在“下载客户端”右侧展示“下载导入模板”链接;无模板时不显示该链接或显示不可用提示,不能影响客户端下载入口和首页 200。**托管策略**:本地上传模板复用生产 Nginx `/media/` 静态托管,不经 Django/Gunicorn 传大文件;`external_url` 优先于 `file.url`,响应/页面不得暴露本地 `MEDIA_ROOT` 或服务器文件路径。**UI**:保持 T-606 下载区现有布局,桌面端按钮为主按钮,导入模板为次级链接/按钮;移动端需换行不重叠。**文档**:同步 `02-requirements.md`、`04-architecture.md`、`routes.md`、`api.md`、`current-state.md`。**测试**:覆盖首页有模板时展示链接且 href 为绝对/可访问 media URL,`external_url` 优先,本地路径不泄露,无模板时首页正常且不显示错误;admin 字段可见;`makemigrations` / `migrate` / `check` / 目标测试通过并在 `../progress.md` 留证据 | DONE |
|
||||
| T-611 | 用户端品牌名统一为“虾皮圈” | T-606 | 把用户端页面上对外展示的项目/产品名从 `cmhub` 统一改为“虾皮圈”。**范围**:只改终端用户可见的 portal 页面文案和浏览器标题,包括公开首页、顶部导航品牌、注册/登录/登出页、控制台、充值、API Key、可用模型、充值记录、点数记录等模板中作为品牌/产品名出现的 `cmhub`;用户端文案里的“cmhub API Key”应改为“虾皮圈 API Key”。**不改**:仓库名、Python 包名、Django app 名、数据库表名、环境变量、API 路径、域名、对外接口字段、后台内部模型名和技术文档里指代服务代号的 `cmhub`。**文档**:同步 `02-requirements.md`、`00-ai-start-here.md`、`current-state.md` 与 `../progress.md`。**测试**:更新 portal 相关断言,覆盖首页展示“虾皮圈”且不再展示旧标题 `cmhub AI 电商生成台`;关键用户端页面渲染不含作为品牌展示的 `cmhub`;`check`、`makemigrations --check --dry-run`、目标 portal 测试通过并在 `../progress.md` 留证据 | DONE |
|
||||
@@ -123,6 +123,7 @@
|
||||
## 待办池(Backlog)
|
||||
|
||||
- ~~异步生成(任务队列 + 轮询/回调)~~ → 已立项 **T-612~T-615**(生图异步任务化:先硬截止 + 长请求池校准止血,再抽共享 core,最后新增 `/tasks` 提交+轮询接口与旧同步接口共存、旧路遥测后弃用)。
|
||||
- **T-621 注册赠点运营后台配置**:将当前固定 10 点改为 admin 可管理的单例策略,包含策略审计、停用时的 0 点决定记录及不追溯历史用户。该项涉及账本与后台配置,现移入 Backlog,暂不实施。
|
||||
- 按账号授权可用别名(`account_alias_permission`),防止调用未授权/昂贵模型。
|
||||
- 别名按比例分流到多个模型(灰度 / A/B / 故障转移);供应商 A 故障自动切 B。
|
||||
- 异步生图提交时模型配置快照:当前 worker 会复跑 `prepare_generation()`,重新审核 prompt、解析别名 / Provider / 定价,但账务使用已预扣 `CallRecord.points_cost`。短队列下可接受;若后续队列积压或后台频繁切换别名,应在 submit 阶段快照 `ai_model_id` / `model_used` / 必要 Provider 配置,worker 使用提交时模型执行,同时保留 prompt 复审。
|
||||
|
||||
Reference in New Issue
Block a user