Some checks failed
Build and Deploy (service.xpcool.com) / build-and-deploy (push) Failing after 54s
- 修正 status 列默认值为 0,避免历史失败记录被误标为成功
- 历史数据回填改为幂等更新,可重复执行
- 过滤未解析的 ${...} 配置占位符,优化 Bark 推送错误提示
- LogDetail 记录不存在时统一返回参数错误,避免暴露 SQL 细节
76 lines
32 KiB
Go
76 lines
32 KiB
Go
# service.xpcool.com 变更记录
|
||
> 倒序:最新在上。格式:YYYY-MM-DD | 类型 | 摘要
|
||
|
||
2026-09-14 | CFG | **安装 chrome-devtools MCP(用户级配置)**:全局 `npm i -g chrome-devtools-mcp@1.9.0`(本机 Node v23.0.0 满足其 `engines: ^20.19.0 || ^22.12.0 || >=23`),在 `C:\Users\xxl\.codebuddy\mcp.json` 的 `mcpServers` 下新增 `chrome-devtools` 条目。**刻意沿用现有 `dbx` 条目的绝对路径写法**(`command` 指向 `...\nvm\v23.0.0\node.exe`,`args[0]` 指向 `...\node_modules\chrome-devtools-mcp\build\src\bin\chrome-devtools-mcp.js`),而非 `npx chrome-devtools-mcp@latest`——Windows 上 `npx` 实为 `npx.cmd`,由 IDE 直接 spawn 时存在解析风险,绝对路径最稳。附 `--no-usage-statistics` 关闭 Google 使用统计。Chrome 已就位(`C:\Program Files\Google\Chrome\Application\chrome.exe`,MCP 默认自动发现,未额外传 `--executablePath`)。冒烟测试:`initialize` 请求下进程正常启动、stderr 打印自身横幅、退出码 0。**需重启 IDE(或重载 MCP 面板)方生效**;默认行为是新开一个独立 profile 的 Chrome 实例,若要接管已开的浏览器需改用 `--browser-url http://127.0.0.1:9222`
|
||
|
||
2026-09-14 | CHG | **壁纸模块后端上线(12 接口 + 开源平台聚合 + 自建图库)**。为 xpcool.com 提供「开源壁纸平台 + 后台自建图库」双来源,**保留**原有浏览器实时生成能力。设计核心是**带宽经济学**(本机出口仅 5M≈625KB/s 且多站共用):① 开源平台(Bing 每日一图 / Picsum / Unsplash / Pexels / Wallhaven)图片**不经过服务器**,后端只代理元数据并返回官方 CDN 直链,`sources`/`list`/`random`/`download-track` 挂 `open` 分组,平台响应内存缓存(Bing 1h、其余 10min);② 自建图库分三档落盘(480px 缩略图 / 长边 1920 预览 / 原图),**由 nginx 直出 `/wallpaper/`**,后端只管元数据与上传。接口遵守本仓库强制规范:**全 POST、URL 不带参、入参走 body**。`manifest/sql/018_wallpaper.sql` 为幂等种子(菜单 + 5 平台,`ON DUPLICATE KEY UPDATE` 只更新 name/sort/remark)
|
||
|
||
2026-09-14 | FIX | **全量加密(fullBody)下 multipart 上传必被拒**(生产才暴露、dev 永不复现):`encrypt.fullBody=true` 时中间件对所有非豁免请求一律 `json.Unmarshal` body,而 multipart 是二进制流必然失败 → 上传被判定为「未加密请求」拒绝(前端对 `FormData` 本就跳过加密,**两端语义不一致**)。修法:`internal/middleware/encrypt.go` 新增 `isMultipartRequest` 豁免,与前端 `request.ts` 的 `config.data instanceof FormData` 分支对齐;**不影响安全** —— 上传接口同样挂在 `/api/service/admin` 分组下,仍受 JWT + RBAC(POST+path 精确匹配)双重保护
|
||
|
||
2026-09-14 | FIX | **`.gitignore` 的 `log/` 规则误伤源码包,导致干净检出无法编译**:`log/` 未锚定根目录、匹配任意层级,把 `api/admin/{base,system}/log`、`internal/service/admin/{base,system}/log` 四个**源码包**静默忽略,而 `internal/controller/admin/log.go` 已在库 → 干净 clone 后 `go build .` 直接失败(`no required module provides package service.xpcool.com/api/admin/base/log`)。修法:改为 `/log/` 并补交这 4 个包;此后干净 HEAD 交叉编译通过(31,075,947 字节)
|
||
|
||
2026-09-14 | DEP | **壁纸模块部署上线 + 端到端验证**:`GOOS=linux GOARCH=amd64 CGO_ENABLED=0` 交叉编译 → 替换 `/data/deploy/projects/service.xpcool.com/main`(旧版备份 `main.bak.20260914b`)→ 配置换为仓库版 → `docker build` 重建容器。**两个必守点**:① 容器必须显式传 `GF_GCFG_FILE=config.prod.yaml`(gf v2.10.2 起不再自动替换 `${ENV}` 占位符,且新 `main.go` 只认 `GF_GCFG_FILE`/`GF_GCFG_PATH`、**不认 `GF_GCFG_ENV`**,漏传即崩溃循环 `specified config file "config.dev.yaml" not found`);② 双挂载 `/data/www/wallpaper` + `/data/service-crypto`(**防容器重建后 RSA 私钥漂移,否则前端解密全挂**)。**验证全绿**:5 平台 sources、朝向过滤、来源限定 random、停用来源返回明确中文错误、CORS 正确回显、密文登录解密成功、响应体 `{"encryptedData":…}`、明文业务请求被拒 `encrypted request required`
|
||
|
||
2026-09-14 | DOC | 壁纸模块上线中修复的**生产数据问题(中文双编码 mojibake)**:`admin_menu`/`wallpaper_source` 中文呈 `Bing æ¯æ—¥ä¸€å›¾`,判据 `HEX(name)` 为 `C3A7C2B3…` 且 `LENGTH/CHAR_LENGTH = 25/12`(正确应为 9)。根因是**导入 SQL 时未指定 `--default-character-set`**,MySQL 客户端按 latin1 解码 UTF-8 字节、再按 utf8mb4 重编码。以 `--default-character-set=utf8mb4` 重放 `018_wallpaper.sql` 后壁纸相关中文恢复。**注意 `admin_menu` 全表历史乱码(id 1~96)本次有意未动**,待用户决定是否批量修复
|
||
|
||
2026-09-14 | FIX | **招聘抓取模块健壮性实施与真实站点校准(阶段一完成)**。基于贵阳市人社局真实列表页做离线+在线校准,修正两处**方案级错误**:① **评分判定必须按「URL 结尾形态」而非「路径关键词」**——栏目页 `/zfxxgk/.../rszk/`(以 `/` 结尾)与正文页 `/zfxxgk/.../rszk/202609/t20260908_xxx.html`(以 `.html` 结尾)**共享同一段栏目路径**,按路径段减分会把真实公告一并误杀(首版实测 19 条真实公告全被过滤只剩 1 条);改为「`.html` 等后缀 +3 / 以 `/` 结尾 -5」后,16 个真实锚点用例分类全对。② **图片型锚点会以文件名污染标题**——`<a href=".../ysqgk/index.html"><img src="ysqgk3.png" title="ysqgk3.png"></a>` 经 stripTags 后为空、`title` 属性回退取到图片名 `ysqgk3.png`,**绕过全部中文排除词**且叠加 `.html` 的 +3 分通过筛选,故新增 `isImageFileName`(图片锚点优先取 alt,取不到整体丢弃)+ 排除域名硬拦友链(gyrc.cn 贵阳人才网、cx.guiyang.gov.cn 信用中国)。另完成:发布日期**分段抽取**(meta PubDate/og:published_time → 语义容器 class=time/date → 「发布时间:」前缀 40 字内 → 自定义正则 → **置空**,替代原「取整页首个日期」把页头"今天是…"误当发布日)、失败**自动禁用**(连续 5 次禁用+告警、3 次预警、成功归零,用坏源 http://127.0.0.1:1 实测第 5 次 `enabled` 1→0)、`Sources()` 改读 `last_log_*` 冗余列消除 `crawl_log` 全表扫描、`resolveCfgValue` 把未解析 `${...}` 占位符视为空(避免「invalid character { in host name」误导)、`cleanText` 清洗 `\n\t\t\t` 标题污染、`bark.go` 4 处英文日志中文化。**实测对比(源1)**:增量 8 条含 6 噪声 → 2 条全真实;force 全量 8 条 → **21 条真实公告**;日期识别率 → **100%**(0 条空)。单测 `go test ./internal/service/recruitment/` 全绿。详见 `docs/recruitment-crawler-design.md` 第七节
|
||
|
||
2026-09-14 | FEAT | **通知历史记录表格界面(后端能力补齐 + 前端页面 + 联调,跨两个仓库)**。① **后端**:`api/notice/notice.go` 日志契约由 11 字段扩到 27 字段(新增 batchId/ruleName/eventName/noticeType/typeName/group/groupName/channelName/userName/status/statusName/retryCount/durationMs/source/remark),新增 `keyword/noticeType/group/userId/batchId/status/orderBy/orderDir` 筛选与 `stats` 统计概览,新增 4 个端点 `log/detail`、`log/delete`、`log/clear`、`log/options`;`dto/notice_meta.go`(新增)收口「渠道/事件/类型/分组」四级字典与中文名映射(**类型与分组由 event_type 派生,不落库**,避免双写不一致);`entity/do` 的 NoticeLog 加 6 列;service `LogList` 重写为多维筛选 + 列表/统计**共用同一 logQuery 保证口径一致** + 批量补齐规则名与接收人(避免 N+1),新增 LogDetail/LogDelete/LogClear,`Send` 引入 batchId、`deliver` 记录耗时/来源/状态,写库由 `map[string]interface{}` **改回 do 对象**(符合 AGENTS.md 硬规范);controller 新增 4 方法 + toLogItem/toMetaItems 转换。② **SQL**:`manifest/sql/017_notice_log_enhance.sql`(notice_log 加 6 列 + 3 索引 + 按 result 回填 status + 菜单 982 改「通知历史」+ 5 条 type=2 权限 + 超管绑定,全幂等)。⚠️**关键坑**:`ADD COLUMN status ... DEFAULT 1` 会把**全部历史行**置 1(含失败记录)→ 显示"历史失败记录成功",故默认取 0 再按 result 回填。③ **前端**(`E:\Project\admin.xpcool.com`):`api/notice.ts` 扩类型与 4 个新方法;`views/system/notice/log/index.vue` 重写(4 张统计卡 + 9 项筛选 + 多选表格 + 详情抽屉 + 批量删除 + 保留 N 天清空 + 权限码控显)。④ **联调**:迁移已执行(notice_log 17 列、菜单 982/9821-9825、14 条历史 status 正确回填为 2);经前端 Vite 代理(20100→10100)跑通 登录→选项→列表→详情,5 接口全部通过 RBAC 返回 code=0;真实投递一条测试通知验证 batchId/durationMs/source/userName/target/remark 落库回显;vue-tsc/oxfmt/oxlint 全 0 错误。⑤ **联调中修复缺陷**:LogDetail 对不存在 ID 会把 `sql.ErrNoRows` 包装上抛 → gf 归为 code=50 且**回显 SQL 细节**,改为忽略 Scan 错误 + `Id==0` 判定,现返回 code=10001「通知记录不存在」。详见 docs/change-log/2026-09-14.md
|
||
|
||
2026-09-14 | CHG | **归档提交 09-13~09-14 压在工作区的两批改动(招聘爬虫健壮性 + 通知记录增强)**,11 改 9 增。① **招聘爬虫**:新增 `source_config.go`(`crawl_source.config` 这个 VARCHAR(1000) JSON 的源级抓取参数解析——增量窗口/单次上限/分页/限速/自定义标准词,**全字段可选、解析失败即回退默认**,保证历史数据零迁移可用、一个脏配置不会拖垮整个调度)、`keywords.go`(链接筛选改「评分制」:URL 形态加分 + 标准词加分 + 排除词大幅减分达阈值入选,取代原先「URL 形态与文本语义必须同时命中」的与逻辑——该逻辑会系统性漏抓「补充工作人员的通知」「公开选调公务员简章」等标题变体且静默无报错,带 `keywords_test.go` 单测与 `testdata/`)、`manifest/sql/recruitment/004_crawl_source_status.sql`(`crawl_source` 增「最近一次运行状态」冗余列,规避 `Sources()` 全表扫只增不减的 `crawl_log`、随运行时间线性劣化);`crawler.go` 在既有两级抓取流程上做锚点抽取/过滤与编码回退的健壮性增强,`bark.go` 推送配合调整。② **通知模块**:`notice.go`/controller/api/dto 扩展通知日志的查询与操作(批次号、状态、重试次数、来源、耗时、详情、删除、清空)、`dto/notice_meta.go`(312 行,字典选项元数据)、`manifest/sql/017_notice_log_enhance.sql`(notice_log 扩列 + 新增接口权限,幂等可重放)。③ `.gitignore` 补 `rc_*` 挡掉本地验证产物(含 30MB 的 `rc_verify.exe`)。设计依据见 `docs/recruitment-crawler-design.md`
|
||
|
||
2026-09-13 | DOC | 项目整理与全局中文化:①重写 README.MD(原英文且路由陈旧 /api/v1 → 实际三分组 /api/service/{open,user,admin},补分层约定/RBAC 权限映射/gen dao 流程/本地启动);②重写 PROJECT_STRUCTURE.md(原英文目录树缺 house/recruitment/notice/job/serversecurity,标注手写 entity/do/dao 风险);③hack/hack.mk + hack-cli.mk 注释中文化;④common/doc.go + common/tools/doc.go 工具清单中文化,ip/main.go/cmd.go 英文注释中文化;⑤**校验提示与服务层错误信息中文化**(19 文件逾 90 处):api 层 v:"#提示" 中文(user/auth、tools/md5、tools/random、menu_manage、admin)、service 层 gerror.Wrap/response.Error 全部中文(admin/admin、admin/login、system/{role,menu,menu_manage,login_log}、user/auth、house/{community,listing,dashboard,transaction,presale}、notice、job、serversecurity、recruitment/{recruitment,crawler})、jwt.go、controller/admin/admin.go、各 service 的 panic("xxx implementation not registered")→"xxx 实现未注册";⑥api/user/login/login.go 补中文包文档。生成代码(entity/do/dao)英文注释按约定保持原样(DO NOT EDIT,重生成会覆盖)。仅注释/文档/字符串改动,无业务逻辑变更;read_lints 全绿,go build 因 proxy.golang.org 网络超时未跑通。详见 docs/change-log/2026-09-13.md
|
||
|
||
2026-08-27 | CHG | 登录接口从全量加密豁免,永远只加密密码字段:APICrypto plainRoutes 增 /system/auth/login(登录请求不整体加密,handler 直接收 {username, encryptedKey, encryptedData},登录响应因无会话密钥保持明文);ResolveLogin 分支顺序调整——密码字段密文优先解密,其次 fullBody 明文、开发 allowPlain。全量模式验证 5 项(登录明文响应/info 密文/解密成功/未加密拒绝/登出)+ dev 回归 15 项全过
|
||
|
||
2026-08-27 | FEAT | 全量请求/响应加密(生产 encrypt.fullBody=true / env ENCRYPT_FULL_BODY):①crypto.Service 增 fullBody 开关 + DecryptRequest(RSA 解 AES 会话密钥 + AES-GCM 解 body,返回会话密钥)+ EncryptResponse(用同一会话密钥 AES-GCM 加密响应回传,请求结束即销毁);②新增 middleware/APICrypto——请求整体解密(io.ReadAll 直接读 r.Request.Body 勿用 GetBody,否则缓存密文致 handler Parse 读到密文)+ 响应加密 buffer(HandlerResponse 外层、Recover 内层,500 也加密),public-key 明文豁免,未加密业务请求一律拒绝;③admin 组中间件链改 CORS→APICrypto→Recover→HandlerResponse;④ResolveLogin/resolvePassword 增 fullBody 分支(传输层已整体解密,直接信任明文 username/password);⑤injectEnv 支持 ENCRYPT_FULL_BODY/ENCRYPT_ALLOW_PLAIN(直接跑二进制恒加载 config.yaml,GF_GCFG_ENV 仅 gf run 认,必须 env 注入)。⚠️GF 坑:r.GetBody() 缓存密文到 bodyContent,handler Parse 走缓存 → 中间件必须 io.ReadAll(r.Request.Body)。dev(仅密码加密)E2E 15 项、prod(全量加密)E2E 9 项全过
|
||
|
||
2026-08-27 | FEAT | 登录密码「RSA + AES-GCM」混合加密传输(对称+非对称结合)+ 创建/重置密码加密字段:①新建 internal/library/crypto——密钥优先级 配置 encrypt.privateKey(PEM) > data/crypto/rsa_private.pem > 自动生成落盘(data/ 已 gitignore);公钥输出 SPKI(x509.MarshalPKIXPublicKey,前端 WebCrypto importKey('spki'),⚠️PKCS#1 会 ASN.1 wrong tag);DecryptLogin 解密 {username,password,ts}(ts 5 分钟窗口防重放)、DecryptField 解密 {value,ts}(创建/重置密码复用);进程级 SetDefault/Get 单例。②公开接口 POST /system/auth/public-key 返回 publicKey;LoginReq 改 encryptedKey+encryptedData(明文字段仅 encrypt.allowPlain=true 时可用,config.yaml/prod 默认 false、dev true);controller.ResolveLogin 统一解析凭据。③AdminCreate/AdminResetPwd 同样支持加密 password(resolvePassword 复用 DecryptField)。④密文结构:encryptedData=base64(nonce(12B)||ciphertext||tag)、encryptedKey=base64(RSA-OAEP(SHA-256) 加密 AES-256 密钥)。端到端 Node 模拟 WebCrypto 15 项全过(公钥/加密登录/错密码30002/篡改密文/过期载荷/受保护接口/加密创建/加密重置/旧密码失效/登出撤销/登出后刷新拒绝)。注:数据库密码本就是 bcrypt 哈希保存(bcrypt.GenerateFromPassword),存储安全已达标
|
||
|
||
2026-08-27 | FEAT | 认证链路联调(登录/登出/超时,3d24dbd):①未授权响应 HTTP 200+code10002 改 401 语义化(response.JSONWithStatus;三处中间件切换)——vben authenticateResponseInterceptor 只认 HTTP 401,此前 token 过期永不触发静默刷新;②LogoutReq 支持 refreshToken,登出撤销刷新会话(IAdminAuth.Revoke 幂等),Refresh 顺带清理过期会话行;③injectEnv 开发兜底:${DB_DSN}/${RECRUITMENT_DB_DSN}/${JWT_SECRET} 占位符未注入 env 时回填本地默认 DSN,任何启动方式零配置可跑(当日两起登录 500 均为启动漏 env),prod 不兜底。端到端 8 项 curl 全过:错密码 30002/登录/伪造 token HTTP401/轮换/旧令牌重放拒绝/登出撤销/登出后拒绝/有效访问 200。注:并行 notice/job 会话提交的 admin_user entity 为 bool/string 映射(公司 gen 模板),已按旧风格手工恢复 int/gtime 并补两列
|
||
2026-08-27 | CHG | 通知模块+自动任务+用户渠道字段:016 SQL(admin_user 加 bark_device_id/pushplus_token;建 notice_channel/rule/log + auto_job/auto_job_log 5 表;菜单 98 通知中心(980规则/981渠道/982日志)/99 自动任务(990任务/991日志) + type=2 权限;渠道/规则/任务种子;人员管理菜单改名用户管理);api/notice + api/job(11 接口全 POST 无 URL 参数);service/notice(Send 统一发送:Bark 路径式 POST /{key} + pushplus 官方接口;渠道/规则/日志/测试);service/job(DB 驱动 gcron:List/Save/Trigger/LogList + Register 业务函数注册 + 完成/失败自动通知 job_done/job_fail);recruitment scheduler 改 RegisterTasks 纳管(原 StartScheduler 废弃);用户 admin 接口支持渠道字段;已部署:容器重建 api.json 200、11 路由全注册、调度器无 handler 缺失告警、种子数据验证 OK。
|
||
2026-08-27 | FIX | 菜单种子主键冲突修复(743683e):recruitment/003_menu.sql 招聘中心一级菜单 id=95 与 014_house_presale_menu.sql 新房预售 id=95(挂看房中心 90)ON DUPLICATE 互相覆盖、后导者赢,本地实际发生(新房预售菜单被顶掉致 /house/presale 404、生产库同样风险);改为 id=96 后发现 015_server_security.sql(并行会话,生产已部署)也用 96=安全日志(挂系统监控5),再改 **97**:95=新房预售(挂90)、96=安全日志(挂5)、97=招聘中心,三模块错开;本地按 014→015→003 重放,routes 接口 22 节点验证全部正确(e18b25f)。⚠️ 生产库需按 014→015→003 顺序重放修复(当前生产 95=招聘中心、新房预售菜单丢失)
|
||
|
||
2026-08-27 | CHG | 服务器安全日志模块:015 SQL 建 server_security_log 表 + 菜单(96安全日志/960查询/961统计);api/serversecurity/v1 三接口全 POST——open 上报 /api/service/open/security/log/report(body token+list,校验 internalToken=INTERNAL_TOKEN env)+ admin 查询 /server-security/log/list、统计 /server-security/log/stats(时间/IP/类型/端口筛选+TOP攻击源);entity/do/dao(主库)/dto/service/controller(ReportController+ManageController 双控制器);cmd.go 注入 INTERNAL_TOKEN→internalToken、open 组绑 NewReport、protected 组绑 NewManage;go build 通过,交叉编译上传 + 服务器 docker build + 容器重建(复用 env 追加 INTERNAL_TOKEN),路由/上报验证 OK(错误 token 返回 10002)
|
||
2026-08-27 | FIX | 本地登录 500 修复:根因=config.dev.yaml 的 ${RECRUITMENT_DB_DSN} 占位符在本地无对应 env(injectEnv 只回填已有变量),gdb 配置解析失败致 g.DB() 全局报 invalid link configuration;本地补建 recruitment 库(导入 001_init+002_seed_sources,6 表 5 源)+.env.dev 与 .run/service-dev.run.xml 补 RECRUITMENT_DB_DSN(两文件 gitignore 不入库);附带修复 gcron 5 段式表达式注册失败(invalid pattern "0 3 * * *")——改 6 段式 '0 0 3 * * *'/'0 0 8 * * *',此前线上每日抓取/推送 cron 实际从未执行(f81ce64);验证:重启后登录返回业务码 30002(非500)、无 cron 报错
|
||
2026-08-27 | CHG | 看房新增新房预售证模块:api/house/presale + controller/service(POST /api/service/admin/house/presale/list,筛选 region/purpose/keyword,id 倒序);dto 加 HousePresaleVO;house_presale 加 publish_date 字段(013 SQL 同步 + hack/config.yaml tables 补 house_presale + gen dao 更新);权限种子 014(菜单 95 新房预售 + 950 查询权限);go build 通过、接口返回 487 条干净数据(presaleNo/publishDate 正确)
|
||
|
||
2026-08-27 | CHG | 看房数据扩充:013_house_presale.sql 建预售证表(presale_no 唯一);house_community 加 avg_price 字段(010 SQL 同步 + gen dao 更新 entity/do 加 AvgPrice);go build 通过
|
||
2026-08-27 | CHG | 服务器日志(操作审计 admin_operation_log)全面增强为综合分页列表:① 新增字段 admin_username(冗余账号)、ip_location(IP归属地)、error_message(失败原因)、user_agent;② 自建纯 Go 的 xdb v4 离线解析器 internal/library/iploc(go:embed 嵌入 ip2region.xdb,无外部依赖,单次内存二分),审计写入时解析账号+归属地、记录 UA 与错误摘要;③ 查询筛选覆盖时间范围/账号/IP/归属地/HTTP方法/结果(成功2xx·失败非2xx)/关键字(权限码·路径·IP)/耗时上下限/排序(时间·耗时);④ 接口 POST /api/service/admin/system/log(body 入参,遵守全 POST 无参约定),dto.LogQuery/LogItem 同步;⑤ SQL:001_core.sql 建表补列 + 新增 010_server_log_enhance.sql 增量迁移(须手动导库,DB 结构变更不自动 DDL);go build 通过、iploc 单元冒烟通过
|
||
2026-08-27 | FIX | 看房中心接口异常修复:根因=后端进程是旧代码(recruitment 模块中途编译错误致项目编译不过、后端停在旧进程未加载 house 路由),重启后端加载新代码;附带修复 house listing/transaction 的 List 方法 Fields 在 Count 前设置导致 COUNT(t.*,c.name) SQL 语法错误(Fields 移到 Scan 前);7 个看房接口全部 code 0 验证通过
|
||
2026-08-27 | CFG | 新增 013_workbench_menu.sql:工作台顶层菜单(id=9, parent_id=0, path=/workbench, component=dashboard/workbench/index, permission=workbench, sort=0 置顶)+ 超管 role_id=1 绑定;前端工作台页面复用既有列表接口聚合,无新增 Go 接口
|
||
2026-08-27 | CHG | 看房成交模块:api/house/transaction + service/house/transaction + controller/house/transaction 实现成交记录 list 接口(/api/service/admin/house/transaction/list,全 POST 分页,关联小区名,按成交日期倒序),dto 加 HouseTransactionVO,cmd.go 注册;012_house_transaction_menu.sql 权限种子(house:data:transaction id=941 挂数据明细 94);go build 通过
|
||
2026-08-26 | CFG | 新增 Gitea act_runner 自动部署:.gitea/workflows/deploy.yml(push main/dev → 下载 Go1.23 工具链 npmmirror + GOPROXY goproxy.cn → CGO=0 linux/amd64 交叉编译 → 组装 main+manifest/config(config.yaml+config.prod.yaml)+resource+deploy/Dockerfile → docker build 重建容器 127.0.0.1:10100(xpcool-net,GF_GCFG_ENV=prod,DB_DSN/JWT_SECRET 走 Gitea Actions secrets)→ curl /api.json 冒烟);deploy/Dockerfile 仓库内维护;DB 结构变更不自动 DDL,需手动导 manifest/sql
|
||
2026-08-26 | FIX | 本地登录 no rows 修复:根因=本地库 service_xpcool_com 的 admin_user 空表(本地/服务器库两套,此前仅改服务器);补 super_admin 角色 + 导入 009_admin_account_v2.sql(须 --default-character-set=utf8mb4 否则中文 Data too long)→ 本地 xxcool/xxCool@2026 登录成功(subject=3);同时服务器废弃 webhook 方案已删除(deploy-webhook.service/webhook.py/secrets.env/deploy.sh),自动部署改走 Gitea act_runner + .gitea/workflows(仓库内尚未配置,待补)
|
||
2026-08-26 | CHG | 看房 house 模块后端落地:010_house_tables.sql 建 9 表(community/building/listing/price_snapshot/transaction/facility/community_facility/school_district/preference)+ 011_house_menu.sql 菜单/权限种子(超管 role_id=1 绑定);gf gen dao 生成 dao/entity/do;实现 api/house/{community,listing,dashboard} + controller/house + service/house(管理 CRUD + 看板聚合,全 POST 动作式,前缀 /api/service/admin/house,含多平台软关联 match_group_id、笋盘/低可信标记);cmd.go 注册 housectl + 3 个 RegisterService;go build 通过。坑①gf CLI 为 com.lib.gf.v2 分支,gen dao 产物 import 需 sed 回 github.com/gogf/gf/v2(18 文件);②mysql 客户端须 --default-character-set=utf8mb4 否则中文 COMMENT/INSERT 乱码;③TINYINT 字段 comment 含 0/1 被 gf 映射 bool(status 三值改 INT);hack/config.yaml 的 link+tables 已指向本地库
|
||
2026-08-26 | CHG | 生产超级管理员账号替换:删除 admin/admin123(用户/绑定/refresh 会话全清),新增 xxcool/xxCool@2026(bcrypt $2b$10$,绑定 super_admin);脚本 manifest/sql/009_admin_account_v2.sql(008 编号已被 008_menu_rbac_v4.sql 占用);004_seed.sql 种子账号同步改 xxcool;登录验证:xxcool 成功、admin 报 no rows(预期);⚠️ 线上前端仍是旧版(默认 admin/admin123),需部署新版 dist 后 xxcool 才可正常登录
|
||
2026-08-26 | CHG | RBAC 菜单调整:移除管理员管理(id=2 及按钮 21-25 软删+解绑),新增日志管理菜单(id=7, system:log, component=system/log/index),原按钮 63(system:log:list)挂到 id=7 下;超管绑定新菜单;幂等脚本 manifest/sql/008_menu_rbac_v4.sql
|
||
2026-08-26 | FIX | RBAC 安全漏洞修复:禁用角色(status=0)绑定的权限仍生效。根因为 Codes/HasPermission/Routes 三处联表查询未过滤 admin_role 启用状态,仅 roleCodes 过滤。修复:三处统一 LeftJoin admin_role 并加 r.status=1,opuser 联调验证 codes 空/routes 空/接口 403,admin 全链路回归通过
|
||
|
||
2026-08-26 | REQ | 看房方案补充「后台管理 + 可视化看板」两层:数据管理用 vben 标准列表 CRUD(查询表单 + vxe-table + 分页 + 批量,页面含小区/房源/快照/成交/配套学区/采集任务),可视化看板用全局筛选器驱动图表联动(筛选器→图表、图表交叉过滤、列表↔地图双向,状态放 Pinia);Go 接口分管理 CRUD 与看板聚合两类,统一 FilterDto 入参供管理与看板共用;echarts/vxe-table/RBAC 均复用现有依赖
|
||
2026-08-26 | REQ | 看房方案迭代:推送改 Bark(苹果,自建 Server 到腾讯云/或官方免费版,用 level/group/url/badge 参数);可视化加贵阳区域地图(底图腾讯地图 GL JS,区县边界 DataV 审图号 GeoJSON,叠加地铁线/学区划片/楼栋点/价格热力,楼栋坐标三级落地:小区中心自动→楼栋图解析→重点盘人工校准);多平台同房源「不去重、软关联对比」(推翻去重,source+source_house_id 同平台唯一,match_group_id 跨平台软关联);补充:笋盘识别/挂牌天数+调价历史/租金回报率/可负担性硬过滤/面积建面套内标准化/贵阳区域画像(观山湖新中心、地铁1/2/3号线、山地通勤)/快照长期保留1-2年
|
||
2026-08-26 | REQ | 规划「看房」功能模块(贵阳购房决策辅助,仅规划设计未开发):架构定为 service 新增 house 业务模块(复用 gf gen dao + MySQL,数据模型 9 张表 community/listing/price_snapshot/transaction/facility/community_facility/school_district/preference/score),admin 新增看房页面(echarts@6 已内置),另立独立 Python 采集分析服务(采集/清洗/去重/打分,只写库不对外 API);决策:目标城市贵阳、新房+二手房都做、先本地后上云;核心风险为贵阳网签/成交数据公开程度不如一线
|
||
2026-08-26 | DEP | 生产部署上线(193.112.118.168):交叉编译 linux/amd64,重建容器 service.xpcool.com:new(127.0.0.1:10100,GF_GCFG_ENV=prod,DB_DSN 补 mysql: 前缀,沿用 JWT_SECRET);nginx 改 HTTPS(443+80→301,证书 /data/nginx/ssl/service.xpcool.com/)反代 10100;DB service 库补种 003→004→004b→007,权限映射对齐 /api/service 路由,admin/admin123 登录验证通过
|
||
2026-08-26 | CFG | 新增 manifest/sql/007_menu_permissions_v3.sql(type=2 权限路径映射最新 /api/service 全 POST 路由,含 system:log:list id=63)与 004b_fill_seed.sql(004 中断后的幂等补齐脚本);部署要点:容器内需 config.yaml(基础配置)否则 GoFrame 启动报找不到 config
|
||
|
||
2026-08-26 | FIX | RBAC 安全漏洞修复:禁用角色(status=0)绑定的权限仍生效。根因为 Codes/HasPermission/Routes 三处联表查询未过滤 admin_role 启用状态,仅 roleCodes 过滤。修复:三处统一 LeftJoin admin_role 并加 r.status=1,opuser 联调验证 codes 空/routes 空/接口 403,admin 全链路回归通过
|
||
|
||
2026-08-26 | CFG | 修复 GoLand 直接 Run 报「找不到 config.yaml」:新增项目级运行配置 .run/service-dev.run.xml(内置 GF_GCFG_FILE=config.dev.yaml + DB_DSN + JWT_SECRET 三环境变量);.run/ 加入 .gitignore(含口令);README 补「Local startup」小节(终端 .env.dev / GoLand 运行配置两种方式)
|
||
|
||
2026-08-26 | FIX | 前端登录 502 联调:根因为服务未启动(10100 无监听);按 .env.dev 启动后 login/info/codes/menu-routes 全链路 curl 200,dev server(20100/20101/20102/20103)代理全部恢复
|
||
2026-08-26 | CFG | CHANGELOG 纳入 git 管理(.gitignore 放行 .workbuddy/memory/CHANGELOG.md),中央工作空间迁移至 ../workbuddy.xpcool.com(相对路径索引)
|
||
|
||
2026-08-26 | CHG | 统一 API 前缀 /api/service/(admin→/api/service/admin、user→/api/service/user、open→/api/service/open);服务端口统一 10100(dev/prod/test);DB admin_menu 权限映射前缀同步;前端 vite 代理与 api 文件同步适配(全 POST + 动作式路径),路由回归 29 条一致
|
||
2026-08-26 | CHG | 遗留 /v1 全移除(URL 前缀 /admin/v1→/admin、/api/v1→/api、/api/open/v1→/api/open);全部接口改 POST(5 组 CRUD 冲突路径改动作式 /list /create /update/{id} 等);DB admin_menu 权限映射 path 同步;全项目英文注释转中文(含 dao/entity/do/table 生成模板),路由回归 29 条全 POST 一致
|
||
2026-08-26 | FIX | 修复审计落库失败:admin_operation_log.request_param 为 JSON 列,仅合法 JSON 入库、其余存 NULL(此前一直失败被「尽力而为」吞掉,系统日志查不到数据)
|
||
2026-08-26 | CHG | 区分系统日志与服务器日志:审计服务由 admin/system/audit 归位为 admin/system/log(package admin_system_log,含 Record+List),新增 GET /admin/v1/system/log 分页查询 + system:log:list 权限映射(菜单 id=63);服务器日志保持 admin/base/log
|
||
2026-08-26 | CHG | login 资源迁移至 admin/admin/login(api+service),全 api/service 包名统一为「路径下划线拼接」(package admin_admin_login / admin_system_menu / user_auth 式);恢复 api/open 并规范化(去 v1,包名 open_tools_ip 式);controller/cmd 引用同步,路由回归 28 条一致
|
||
2026-08-26 | REQ | 后台登录接口联调通过:login/info/codes/menu-routes/RBAC/refresh(单次)/logout 全链路 curl 验证 OK(库 service_xpcool_com)
|
||
2026-08-26 | FIX | 联调发现并修复 admin refresh 单次使用漏洞:Refresh 撤销旧会话后补 RowsAffected 校验,重复使用旧 refreshToken 返回 code 10002
|
||
2026-08-26 | CFG | 新建 .env.dev 本地配置(DB_DSN=mysql:root:root123@tcp(127.0.0.1:3306)/service_xpcool_com?loc=Local + JWT_SECRET),.gitignore 追加 .env* 防口令入库
|
||
2026-08-26 | CHG | 清理模板:删除 api/hello、api/open、common/tools 及 controller/hello、controller/open;API 目录去掉 v1 层(api/admin/system/auth/auth.go 式),service 层完全镜像;URL 前缀保持 /admin/v1 兼容前端
|
||
2026-08-26 | CHG | 目录重构:API 层资源目录化(api/admin/v1/system/auth/auth.go 式);service 层严格镜像 API 多级结构(internal/service/admin/system/auth/auth.go 式),接口随实现归位、admin_rbac 拆为 admin/role/menu_manage 三包,controller/cmd 引用同步,路由回归 29 条一致
|
||
2026-08-26 | CHG | 补全管理端登录接口:新增 Refresh/Logout 端点(/admin/v1/system/auth/refresh|logout),登录改走 issue 把刷新令牌 JTI 落库,与 user 端刷新撤旧机制一致
|
||
2026-08-26 | CHG | 同步三铁律(中文注释/做记录/中文优先)至 AGENTS.md「统一工作约定」小节
|
||
2026-08-26 | CFG | 建立统一变更记录机制(CHANGELOG),接入 xpcool.com 中央索引
|