主题
签名验证报告
OfdDoc.verifySignatures(trustedKeyHex?, anchors?) 返回 SigReport[],每个元素对应文档中的一份签名。
三层结论
一份签名的可信度分三层呈现——不要只看一个布尔值:
| 层 | 字段 | 回答的问题 |
|---|---|---|
| 签名值 | signatureValid | 签名是否由声明的公钥生成(SM2 对 TBS 校验) |
| 文档完整性 | digestValid | 签名保护的内容是否被改动(dataHash / References 逐文件比对) |
| 身份可信 | chainTrusted / chainStatus | 签名者证书是否可信(链校验 + 信任锚命中) |
常见组合:
signatureValid ✓ digestValid ✓→ 徽章显示「有效」(文档未被修改且签名真实)signatureValid ✓ digestValid ✗→ 「文档已被修改」signatureValid ✗→ 「签名值无效」- 链为
no-anchor→ 前两层可信,但未配置信任锚,无法确认身份——这是诚实的中间态 signatureValid ✓ digestValid ✓但未配置信任锚/信任公钥 → 只能证明"未被修改且与内嵌证书 一致";内嵌证书是签名方自带的(可自造自签),signatureValid不能单独作为可信结论, 集成方应以chainTrusted为准
字段全表
| 字段 | 类型 | 说明 |
|---|---|---|
index | number | 签名序号(从 0 开始) |
signer | string? | 签名人(SES 内声明的显示名) |
signTime | string? | 签名时间(SES 记录,如 20200723130907.763Z) |
signatureValid | boolean | 签名值是否有效 |
digestValid | boolean | 文档摘要是否一致 |
unprotectedFiles | string[] | 签名后新增的未保护文件(注释/附件等合法增补)。只作提示,不影响 digestValid——签名后的增补工作流与篡改分级呈现 |
usedEmbeddedCert | boolean | 是否用内嵌证书验签 |
sesVersion | 1 | 4 | null | SES 版本;null 为纯数字签名 |
chainStatus | string | 机器可读结论(见下表) |
chainLabel | string | 中文短标签(可直接上界面) |
chainTrusted | boolean | 链是否受信任(命中锚且逐跳通过) |
chainPath | string? | 链上主体路径(A ← B ← C) |
chainErrors | string[] | 链校验失败原因/警告 |
anchorSubject | string? | 命中的信任锚主体 |
certSubject | string? | 签名证书主体(CN=…, O=…, C=CN) |
certIssuer | string? | 签发者 |
certNotBefore / certNotAfter | string? | 证书有效期 |
message | string? | 失败说明(成功为 null) |
references | {file, ok}[] | 逐文件摘要比对结果 |
chainStatus 取值
| 值 | 含义 |
|---|---|
trusted | 链顶命中信任锚,逐跳校验通过 |
untrusted-root | 链顶不是给定锚 |
incomplete | 链不完整(缺签发者证书),无法到达锚 |
bad-signature | 上级签名无效 |
expired | 按签名时间证书已过期/未生效 |
not-ca | 上级证书不是 CA |
unsupported | 签名算法不支持 |
no-cert | 签名没有内嵌证书(需 trustedKeyHex) |
no-anchor | 未配置信任锚(只验了签名值与摘要) |
本地签名:signOfd
验签之外,WASM 端也提供本地签名生成(同步返回新字节,详见 API 参考):
js
import { signOfd } from "rust-ofd";
const signed = signOfd(ofdBytes, {
signer: "张三", // 签署人显示名(自签证书 CN)
seal: sealPngBytes, // 印章图片(缺省内置占位章)
page: 0, x: 140, y: 240, // 盖章页(0 起)与 Boundary(mm,缺省 0,0)
basis: { reason: "同意", location: "北京" },
});即时生成 SM2 密钥对与自签证书(SES v4 + 印章)。签名针对当前内容:签名后再做旋转/合并等修改,摘要即失效(验签显示「文档已被修改」)——生产场景的最终签名建议放在文档定稿之后。
调用示例
js
const doc = new OfdDoc(ofdBytes);
const reports = doc.verifySignatures(undefined, pemText);
for (const r of reports) {
console.log(r.signer, r.signatureValid && r.digestValid, r.chainLabel);
}信任锚文件支持 .cer/.crt/.pem/.der:PEM 原样文本传入,DER 转 base64 后传入(demo 站与 WPF 端均有现成实现可参考)。