披露:我为 CISPL 工作。
截至目前,WebCrypto API 不提供对 (Windows) 或任何其他密钥存储或本地加密 USB/智能卡设备的访问。
同样在大多数签名场景中,为了在服务器边界内保护 pdf 文件,不建议将完整的 pdf 文件发送到浏览器或签名 API 服务器。
因此,它的良好做法是创建 PDF 的哈希以进行签名,将哈希发送到浏览器并通过浏览器扩展使用 javascript 访问本地系统上运行的某些应用程序以访问本地密钥库(或 USB/智能卡)并生成签名并发送回( PKCS7 或 CMS 容器(在 PDF 签名的情况下)到服务器,在该服务器中签名可以被注入到 PDF 中,从该 PDF 中创建用于签名的哈希并发送到浏览器或签名 api 服务器。
对于基于浏览器的签名场景,我公司提供了一个这样的免费浏览器扩展 Signer.Digital 和服务器所需的 .NET 库。可以从cNET 下载站点下载本地系统(在 windows 上的 chrome 浏览器后面运行的主机)
安装此主机并重新启动 Chrome 将自动添加Signer.Digital Chrome Extension和/或Signer.Digital Firefox Extension
此处说明了此扩展的实际工作以及完整的代码演练和工作示例 VS 2015 项目源代码的下载链接。
Javascript 从扩展调用方法:
//Calculate Sign for the Hash by Calling function from Extension SignerDigital
SignerDigital.signPdfHash(hash, $("#CertThumbPrint").val(), "SHA-256") //or "SHA256"
.then(
function (signDataResp) {
//Send signDataResp to Server
},
function (errmsg) {
//Send errmsg to server or display the result in browser.
}
);
如果成功,则返回 Base64 编码的 pkcs7 签名 - 使用合适的库或 Signer.Digital 提供的库将签名注入 pdf
如果失败,则返回以“SDHost Error:”开头的错误消息
从浏览器进行数字签名
- 服务器将要签名的数据/文档/内容的哈希发送到浏览器。
- 浏览器使用 Signer.Digital Browser Extension Javascript API 从 Signer.Digital Browser Extension Host 调用操作。
- 在 Windows 上,浏览器扩展主机使用 Microsoft 证书存储和底层 CSP 来获得哈希签名。
- 在 Linux 上,浏览器扩展主机使用加密设备的 PKCS#11 .SO 库来获得哈希签名。
- 原始签名(哈希签名)或签名容器由Signer.Digital Browser扩展主机返回给浏览器。
- 如果是加密设备,即。USB 令牌或智能卡,用户的私钥永远不会从设备中出来,而是将要签名的哈希发送到设备以对其进行签名。
- Web 应用程序(浏览器中的 Javascript)将签名发送回服务器,并且可以在 PDF 文档、XML 或 Json 中或根据需要进行修改。