5 Commits
Author SHA1 Message Date
Henry_Du d1b643bd93 refactor(微信订阅): 重写订阅消息链路,每一步失败都可见
把「微信订阅消息」这套代码按验收标准推翻重写:用户能自己看懂为什么收不到,
任何一步失败都必须看得见。对外函数名不变,notificationService / test-subscribe
等调用点无需改动。

新增 server/utils/wechatSubscribeTemplates.ts(纯函数,零依赖):
  - 模板登记表唯一来源(内置 SONG_SELECTED / SONG_REJECTED),服务层不再自己写死
  - parseSubscribeTemplates 如实报告环境变量覆盖情况:坏 JSON 只报告不抛、
    只给 id 时沿用内置字段映射、缺 id 的项记进 unknownKeys 并忽略
  - findEmptyFields / findEmptyDataFields 发出前自查空字段(微信空值整条 47003)
  - explainWechatErrcode 把 43101/47003/40003/40037/40001/45009 翻成人话

重写 server/services/wechatSubscribeService.ts:
  - sendWechatSubscribe 返回 SendOutcome,用 stage 明确「卡在哪一步」:
    no-template / disabled-by-user / no-wechat-openid / no-access-token /
    empty-field / no-grant / rejected-no-quota / rejected-bad-field / rejected-other
  - 每一次返回都写一行日志,不再有静默跳过(这是「发不出去全靠猜」的根因)
  - inspectWechatSubscribe 只读体检:不发消息、不消耗额度,返回逐项 verdict + actions
  - grantWechatSubscribe 依靠新增的 WechatSubscribeGrant 表记账:微信没有查询
    剩余授权的接口,只能自己数(用户点允许 +1、发送成功 -1)
  - 记账表不可用时失败开放(fail-open):额度预检关闭、照常发送,避免通知整体哑掉
  - access_token 显式 responseType: json 并做字符串兜底解析

新增接口:
  - GET  /api/user/wechat-subscribe-status   小程序显示「还能收到几条 / 为什么收不到」
  - POST /api/user/wechat-subscribe-grant    小程序授权成功后上报 accept 的模板
  - GET  /api/admin/wechat/diagnose          重写:人话结论 + actions,?send=1 真发一次

其他:新增 WechatSubscribeGrant 表(schema + 手写迁移)、.env.example 说明 JSON 覆盖
写法、.gitattributes 补 *.sql eol=lf。

测试:新增 test/wechatSubscribeTemplates.test.mjs(13 个用例,可直接 import .ts,
不依赖 Nuxt 别名),npm test 里订阅相关 25/25 通过。
2026-10-11 16:02:33 +08:00
Henry_Du 381f3debf1 fix(admin+server): 酷狗 baseUrl 默认值移除 127.0.0.1 + 新增后台配置入口与推荐快捷地址
问题:容器内 SystemSettings.kugouApiBaseUrl 默认 http://127.0.0.1:3000 指向自己,sidecar 不可达。

修复:1) schema + migration 移除 kugouApiBaseUrl 默认值;kugouService + status API 兜底改空串(不再假设有 localhost),优先级 env(KUGOU_API_BASE) > DB。

2) 新增 POST /api/admin/kugou/settings:ADMIN+/SUPER 即时写 kugouApiBaseUrl 入库+刷新 CacheService。

3) KuGouImporter.client.vue 左栏新增 baseUrl 输入框(回车即存)+ 保存并测试按钮 + 两个推荐快捷按钮(容器宿主 http://172.19.0.1:3000、公网中继 https://bywmusic.bzw-hheb.top/kugou)+ 当前生效地址显式提示。

4) UI/Icon.vue 新增 server / globe / save 三个 SVG 图标与上述入口配套。
2026-09-19 13:40:59 +08:00
Henry_Du a0184fdeb0 feat(admin+server): 酷狗对接 - 扫码绑定管理员账号 / 按排期自动创建酷狗日歌单 + 同步歌曲
数据模型:SystemSettings 新增 kugouApiBaseUrl / kugouAdminCookie / kugouAdminToken / kugouAdminUser / kugouAdminBoundAt 5 字段;新建 KuGouPlaylistSync 同步历史表(12 字段 + playDate 倒序索引)。迁移脚本:app/drizzle/migrations/20260919143000_add_kugou_integration.sql

后端 Server:新增 server/services/kugouService.ts 封装 KuGouMusicApi sidecar 转发(自动拼 Cookie / Token header);新增 6 个 admin/kugou 路由:status / qr-create / qr-check / unbind / sync-schedule-playlists / sync-history。同步核心:逐日出非草稿排期 → kgHash 直取优先 → 失败用 cloudsearch/search 按标题+歌手三级召回 → /playlist/create + /playlist/tracks op=add 每 100 首分批;写同步历史(status、added/missing、歌单 URL)。

后台 UI:新建 Admin/KuGouImporter.client.vue 三栏布局——左栏 sidecar 健康卡+部署说明+扫码绑定/解绑弹窗;中栏多选排期日期+逐日出排期预览卡+按日同步;下栏最近 100 条同步历史(7 种状态 badge + 歌单链接跳转)。dashboard.vue L105 playlist-card 挂载点由 PlaylistCardPage 替换为 KuGouImporter;权限 permissions.js 5 个 ADMIN 族角色开放 playlist-card 页面访问(接口内部绑定/同步再强校验 ADMIN/SUPER_ADMIN)。

侧car要求:部署 KuGouMusicApi(参考文档 https://kugoumusicapi-docs.4everland.app),默认本机 http://127.0.0.1:3000,可通过 SystemSettings.kugouApiBaseUrl 或环境变量 KUGOU_API_BASE 覆盖。
2026-09-19 11:57:02 +08:00
Henry_Du bd8df1f026 feat(songs): 歌曲管理支持批量驳回、投稿留言自动审查与排期范围可见性过滤
构建并部署 BYW VoiceHub / Preflight 语法与构建检查 (push) Failing after 6m31s
构建并部署 BYW VoiceHub / 构建并推送容器镜像 (push) Skipped
构建并部署 BYW VoiceHub / 部署到生产服务器 (push) Failing after 4s
- 新增 /api/admin/songs/batch-reject.post 批量驳回接口(事务清排期/投票/扣接纳数/黑名单去重/异步通知)
- requireSongAdmin 三角色校验 + createApiError 统一错误包装
- scheduleDaysBefore/After 四字段排期可见范围限制(开放 API 与公开排期接口三处缓存路径 + DB 条件过滤)
- submissionNoteAutoModeration 基于黑名单 KEYWORD/LANGUAGE/GENRE 自动判定留言 publicStatus,命中自动关闭 submissionNotePublic
- 更新 songs/request.post 与 songs/[id]/update.put 接入自动审查逻辑
2026-09-06 17:03:20 +08:00
Henry_Du 4ce4649aaf 初次提交
Build VoiceHub FPK / build-fpk (push) Failing after 56m5s
Build and Push Docker Image / build-and-push (push) Canceled after 1h9m35s
2026-09-06 08:19:02 +08:00