PdfTimeStamper Class |
Namespace: RadPdf.Integration
The PdfTimeStamper type exposes the following members.
Name | Description | |
---|---|---|
PdfTimeStamper |
Create a new time stamp provider using a callback function.
|
Name | Description | |
---|---|---|
Equals | (Inherited from Object.) | |
Finalize | Allows an object to try to free resources and perform other cleanup operations before it is reclaimed by garbage collection. (Inherited from Object.) | |
GetHashCode | Serves as a hash function for a particular type. (Inherited from Object.) | |
GetTimeStamp |
An abstract method which will be called by RAD PDF to time stamp a certificate based signature created to certify the output PDF.
| |
GetType | Gets the Type of the current instance. (Inherited from Object.) | |
MemberwiseClone | Creates a shallow copy of the current Object. (Inherited from Object.) | |
ToString | Returns a string that represents the current object. (Inherited from Object.) |
In this example, the open source library Bouncy Castle (https://www.bouncycastle.org/csharp/) and its classes TimeStampRequest and TimeStampResponse are used time stamp a signature.
using System; using System.Collections.Generic; using System.IO; using System.Net; using System.Security.Cryptography; // requires a project reference to System.Security using System.Security.Cryptography.Pkcs; using System.Security.Cryptography.X509Certificates; using System.Text; using Org.BouncyCastle.Math; //requires Bouncy Castle (https://www.bouncycastle.org/csharp/) using Org.BouncyCastle.Tsp; using RadPdf.Integration; public class MyTimeStamper : PdfTimeStamper { public override byte[] GetTimeStamp(SignerInfo signer) { byte[] digest; using (SHA256CryptoServiceProvider sha = new SHA256CryptoServiceProvider()) { digest = sha.ComputeHash(signer.GetSignature()); } TimeStampRequestGenerator reqGen = new TimeStampRequestGenerator(); reqGen.SetCertReq(true); TimeStampRequest tsReq = reqGen.Generate(TspAlgorithms.Sha256, digest, BigInteger.ValueOf(DateTime.UtcNow.Ticks)); HttpWebRequest req = (HttpWebRequest)WebRequest.Create("http://timestamp.digicert.com"); req.Method = "POST"; req.ContentType = "application/timestamp-query"; req.ContentLength = tsData.Length; byte[] reqData = tsReq.GetEncoded(); Stream reqStream = req.GetRequestStream(); reqStream.Write(reqData, 0, reqData.Length); reqStream.Close(); byte[] resData; using (HttpWebResponse res = (HttpWebResponse)req.GetResponse()) { using (MemoryStream ms = new MemoryStream()) { Stream resStream = res.GetResponseStream(); resStream.CopyTo(ms); resStream.Close(); resData = ms.ToArray(); } } TimeStampResponse tsRes = new TimeStampResponse(resRaw); tsRes.Validate(tsReq); return tsRes.TimeStampToken.ToCmsSignedData().GetEncoded(); } }
If using ASP.NET Core, the native classes Rfc3161TimestampRequest and Rfc3161TimestampToken can be used:
using System; using System.Collections.Generic; using System.IO; using System.Net; using System.Security.Cryptography; using System.Security.Cryptography.Pkcs; using System.Security.Cryptography.X509Certificates; using System.Text; using RadPdf.Integration; public class MyTimeStamper : PdfTimeStamper { public override byte[] GetTimeStamp(SignerInfo signer) { byte[] nonce = new byte[8]; using (RandomNumberGenerator rng = RandomNumberGenerator.Create()) { rng.GetBytes(nonce); } Rfc3161TimestampRequest request = Rfc3161TimestampRequest.CreateFromSignerInfo( signer, HashAlgorithmName.SHA256, requestSignerCertificates: true, nonce: nonce); byte[] tsData = request.Encode(); HttpWebRequest req = (HttpWebRequest)WebRequest.Create("http://timestamp.digicert.com"); req.Method = "POST"; req.ContentType = "application/timestamp-query"; req.ContentLength = tsData.Length; Stream reqStream = req.GetRequestStream(); reqStream.Write(tsData, 0, tsData.Length); reqStream.Close(); byte[] resRaw; using (HttpWebResponse res = (HttpWebResponse)req.GetResponse()) { using (MemoryStream ms = new MemoryStream()) { Stream resStream = res.GetResponseStream(); resStream.CopyTo(ms); resStream.Close(); resRaw = ms.ToArray(); } } Rfc3161TimestampToken token = request.ProcessResponse(resRaw, out _); return token.AsSignedCms().Encode(); } }
Use a custom PdfIntegrationProvider implementation to use your time stamper when certifying a document:
using System; using System.Web; using RadPdf.Integration; public class CustomPdfIntegrationProvider : PdfIntegrationProvider { public override void OnDocumentSaving(DocumentSavingEventArgs e) { base.OnDocumentSaving(e); e.CertifyUsing = new PdfCertifier(@"C:\path\to\cert.pfx", "password"); e.CertifyUsing.TimeStampUsing = new MyTimeStamper(); } }