我正在使用数字签名签署 PDF 文件。我使用 SyncFusion 作为 PDF 库,使用 GlobalSign 作为证书提供商/颁发机构。
与外部方签署文档时,实现IPdfExternalSigner接口,在“Sign”方法中,我应该给出一个名为“timeStampResponse”的字节数组。我的猜测是,来自受信任的时间戳服务器的响应。
我已调用我的签名机构的外部服务器,并收到“根据 RFC3161 的时间戳令牌的 Base64 编码 DER 表示形式。它包括 SignedData.CertificatesSet 中的 TSA 签名证书。”
我已将此令牌的字节解析为Rfc3161TimestampToken,因此我非常确定令牌本身是正确的,并且字节包含权威机构所说的内容。
但是无论我将什么内容放入界面的请求数组中,都不会出现任何类型的错误或警告,但是当我在 Adobe 中打开生成的签名 PDF 时,它总是显示
签名包含嵌入的时间戳,但无法验证
签名过程的其余部分工作正常,文档已签名,有绿色复选标记,是 LTV,一切都很好。只是时间戳是一个问题。
我尝试传递来自权威机构(DER 表示)的令牌字节。
我尝试过从
rfc3161TimestampToken.AsSignedCms().Encode()
传递字节。
但一切都没有改变。
鉴于该领域完全缺乏任何文档,我迷失了。
有谁知道我需要将什么传递给这个字节数组,以便我可以看到经过验证的时间戳?
(是的,我开了一张支持票,但我以前从未与他们打过交道,我不知道那会多快,也不知道答案有多有能力。我希望这里有人以前这样做过,或者暗示我什么可能会做错。)
由于不熟悉该问题的人只会单击关闭,因为没有代码,这是我的代码......尽管与问题略有无关:
public byte[] Sign(byte[] message, out byte[] timeStampResponse)
{
var sha256MessageDigest = SHA256.HashData(message);
var hexEncodedSha256MessageDigest = Convert.ToHexString(sha256MessageDigest);
var globalSignTimeStampToken = // call their server with hexEncodedSha256MessageDigest and receive token
// token is supposed to be Base64 encoded DER representation
// of timestamp token according to RFC3161. It includes the
// TSA signing certificate in SignedData.CertificatesSet.
var timeStampTokenBytes = Convert.FromBase64String(globalSignTimeStampToken);
if (Rfc3161TimestampToken.TryDecode(timeStampTokenBytes, out var rfc3161TimestampToken, out var bytesConsumed))
{
timeStampResponse = rfc3161TimestampToken.AsSignedCms().Encode();
}
else
{
timeStampResponse = [];
}
var hexEncodedSignatureValue = // call their server with hexEncodedSha256MessageDigest and receive signature
return Convert.FromHexString(hexEncodedSignatureValue);
}
再次在线查看后(我猜是第十次)我读到了签名包含嵌入式时间戳,但无法验证并在我的令牌上调用了VerifySignatureForData和VerifySignatureForHash,两者都回来了true
并附有预期的证书。
第二个问题是 GlobalSign 用于签署时间戳的证书在 Acrobat 中默认不受信任。当我们尝试这个 GlobalSign 时间戳服务器
http://timestamp.globalsign.com/tsa/r6advanced1时,我们得到了结果: 这会影响时间戳的验证。
当我们尝试 DigiCert 时间戳服务器http://timestamp.digicert.com 时,我们得到了结果:
我的建议是尝试 DigiCert 时间戳服务器(您必须为其准备完整的时间戳请求),并在timeStampResponse
参数中返回 DigiCert 时间戳服务器返回的完整响应(它返回完整的时间戳响应)并查看如何就这样了。