All checks were successful
序列化结构检查 / serialization-schema-check (push) Successful in 2s
7.6 KiB
7.6 KiB
序列化结构检测 — CI 集成说明
1. 集成概览
开发者 push 代码(可含多个 commit)
↓
Gitea Actions 触发
↓
浅克隆业务仓库 tip(depth=1)+ 按需取 push 前 tip(before)
↓
从 Nexus 下载 serialization-schema-checker.jar
↓
java -jar 执行(对比 before → after,累计 diff)
↓
有结构变更 → 企微通知(按 Key 骨架;删除橙/新增绿/修改灰)
↓
mode=block 且含任意结构变更 → exit 1(流水线失败)
1.1 对比区间(重要)
| 参数 | 取值 | 含义 |
|---|---|---|
--old-sha |
gitea.event.before |
本次 push 前的远端 tip |
--new-sha |
gitea.sha |
本次 push 后的 tip |
一次 push 推了多个 commit 时,只跑 一次 检测,覆盖整次 push 的累计代码差,不会因为「变更发生在中间 commit、最后一个 commit 没改相关文件」而漏检。
不需要全量历史:工作树是当前 tip;before 通过 git fetch --depth 1 <sha>(或 deepen)取到即可。责任人过滤依赖 git log old..new,流水线已通过 ensure_range deepen,保证区间提交可见。
边界:
before全0/ 空 → 新分支首次 push,跳过workflow_dispatch无 before → 回退HEAD~1- 中间 commit 改坏又被末 commit 改回 → 累计可能无告警(以最终结构为准)
- commit 计数:优先取
gitea.event.commits长度;否则 deepen 到before为祖先后再git rev-list(浅克隆下直接rev-list会少算)
1.2 责任人过滤(合并推送不背锅)
前提:A/B 各自 push 都会跑检测;B 的结构变更已在 B 的 push 告警。合并/代推时不应再让推送人背他人的锅,也不按人拆多条通知。
| 项 | 行为 |
|---|---|
| 对比区间 | 仍为整次 push 的 before → after(Schema 新旧用全量 diff 回填) |
| 触发集 | 仅 责任人非 merge 提交 触及的 Java 文件 ∩ 区间 diff |
| 责任人参数 | --responsible-author(流水线传 gitea.actor);--modifier 同为 actor,报告抬头「责任人」 |
| Author 匹配 | 对 git log 的 %an <%ae> 不区分大小写包含 actor(中文名/邮箱对不上时可能匹配失败) |
--no-merges |
纯 merge 推送 → 触发集为空 → 不告警(符合前提) |
| 责任人无自有 Java 改动 | 空报告、打日志跳过 |
java -jar serialization-schema-checker-1.0.0.jar \
--old-sha "$OLD_SHA" \
--new-sha "$NEW_SHA" \
--modifier "${{ gitea.actor }}" \
--responsible-author "${{ gitea.actor }}" \
...
2. 前置条件
| 项 | 说明 |
|---|---|
| Gitea Runner | 标签 jdk11,已安装 Java 11 |
| Nexus 私库 | 可访问 http://192.168.3.25:18081/nexus/repository/maven-releases |
| 工具 JAR | com.codechecker:serialization-schema-checker:1.0.0 已发布 |
3. 业务仓库文件清单
在 jnpf-java-cloud 中新增:
jnpf-java-cloud/
├── .gitea/
│ ├── workflows/
│ │ └── serialization-schema-check.yaml # 流水线
│ └── config/
│ └── serialization-schema-check-config.yaml # 检测配置
请以本仓库 .gitea/workflows/serialization-schema-check.yaml 为模板同步到业务仓。
4. 流水线模板(要点)
完整可运行版本见:.gitea/workflows/serialization-schema-check.yaml。
核心逻辑摘要:
# 1) 浅拉 tip
git clone --depth 1 --single-branch --branch "$BRANCH" "$REPO_URL" .
git checkout -B "$BRANCH" "$NEW_SHA" # NEW_SHA = gitea.sha
# 2) OLD_SHA = gitea.event.before(全 0 则跳过;手动触发回退 HEAD~1)
# 3) 本地没有 OLD_SHA 时:
git fetch --depth 1 origin "$OLD_SHA" # 优先
# 或 git fetch --deepen N # 兜底
# 4) 执行(对比区间全量;责任人过滤触发集)
java -jar serialization-schema-checker-1.0.0.jar \
--old-sha "$OLD_SHA" \
--new-sha "$NEW_SHA" \
--modifier "${{ gitea.actor }}" \
--responsible-author "${{ gitea.actor }}" \
...
5. 与现有流水线的关系
| 流水线 | 作用 | 关系 |
|---|---|---|
demo.yaml (AI代码质量分析) |
AI Code Review | 并行,互不影响 |
code-check (CodeChecker) |
通用变更检测 | 同模式,可并列执行 |
serialization-schema-check |
序列化结构检测 | 新增 |
6. 工具发布流程(schemaCheck 仓库)
# 在 schemaCheck 仓库根目录
mvn clean package -DskipTests
# 发布到 Nexus(需配置 settings.xml)
mvn clean deploy -DskipTests
发布产物:
com/codechecker/serialization-schema-checker/1.0.0/
├── serialization-schema-checker-1.0.0.jar # 可执行 fat-jar
└── serialization-schema-checker-1.0.0.pom
7. 退出码约定
| 退出码 | 含义 | 流水线表现 |
|---|---|---|
| 0 | 通过(含 notify 模式下的告警) / 跳过 | 绿色 |
| 1 | 阻断(block 模式) | 红色 |
| 2 | 执行错误(配置缺失、无法取 before、jar 异常等) | 红色 |
8. 故障排查
| 现象 | 可能原因 | 处理 |
|---|---|---|
| 新分支首次 push 跳过 | before 全 0 |
正常行为 |
| 无法获取 before / exit 2 | 浅克隆未取到对象、服务端禁 fetch SHA | 看日志中的 deepen;确认 Gitea 允许按 SHA fetch |
| 下载 jar 失败 | Nexus 地址/版本错误 | 检查 env 变量 |
| 未收到企微 | Secret 未配 / notify.enabled=false / webhook_url 空 | 检查配置 |
| 大量 Redis 误报 | 锁/计数器未过滤 | 补充 ignore.key_patterns |
| 大量 MQ 误报 | 压测/临时 topic | 补充 ignore.mq_destinations |
| commit 数显示为 1(实际多个) | 浅克隆下 rev-list 看不到中间提交 |
已修复:优先事件 commits 长度;并 deepen 到 before 为祖先 |
| 漏报(模式/模块) | W0x/MQ 未开 / include_modules 过窄 | 确认 W01mq_read_hints_enabled 与模块过滤 |
| 类型展开不完整 | 类型在依赖 jar 中 | 补充 manual_mappings.value_type |
| 合并推送仍告他人改动 | 未传 --responsible-author / jar 过旧 |
同步流水线模板;确认 jar ≥ 含责任人过滤的版本 |
| 责任人过滤后漏报自己的改动 | actor 与 %an <%ae> 对不上 |
看日志「责任人过滤…」;核对 commit author 是否含 actor 子串 |
9. 本地调试
模拟一次「多 commit push」的累计区间:
# OLD = 推送前 tip,NEW = 当前 tip(可用 origin/branch@{1} 或显式 sha)
OLD_SHA=$(git rev-parse origin/$(git branch --show-current)~3) # 示例:假设 ahead 3
NEW_SHA=$(git rev-parse HEAD)
AUTHOR=$(git log -1 --format=%an)
java -jar /path/to/serialization-schema-checker-1.0.0.jar \
--config .gitea/config/serialization-schema-check-config.yaml \
--repo-root . \
--old-sha "$OLD_SHA" \
--new-sha "$NEW_SHA" \
--branch $(git branch --show-current) \
--modifier "$AUTHOR" \
--responsible-author "$AUTHOR" \
--modify-time "$(git log -1 --format=%cd --date=format:'%Y-%m-%d %H:%M:%S')" \
--dry-run
单 commit 自测仍可用 --old-sha HEAD~1 --new-sha HEAD。未传 --responsible-author 时不做作者过滤(全量 diff 触发)。
10. 相关文档
| 文档 | 说明 |
|---|---|
| 实施方案.md | 缓存检测总体方案 |
| 配置说明.md | YAML 配置项 |
| MQ序列化结构检测方案.md | MQ 消息体 Schema(RocketMQ + Kafka,方案已落地) |