java iText5 5.5.X版本 对pdf进行数字签名 在签名过程中应用时间戳

因为公司对发出的pdf报告进行有权威的认证,所以需要使用数字签名。

Apache PDFBox: 实现不了,
spire.pdf.free: 虽然可以用,但是免费的他有限制,限制了转为数字签名的pdf只有10页

iText5:所以使用了iText5

首先你要有CA证书、密码、以及时间戳服务器(TSA)的url、用户、密码。

接下来引入对应的jar


        
            com.itextpdf
            itextpdf
            5.5.13.4
        

        
        
            org.bouncycastle
            bcprov-jdk15on
            1.70
        

        
            org.bouncycastle
            bcpkix-jdk15on
            1.70
        

然后就是代码了

package com.stc;

import com.itextpdf.text.DocumentException;
import com.itextpdf.text.pdf.PdfReader;
import com.itextpdf.text.pdf.PdfStamper;
import com.itextpdf.text.pdf.PdfSignatureAppearance;
import com.itextpdf.text.pdf.security.BouncyCastleDigest;
import com.itextpdf.text.pdf.security.ExternalDigest;
import com.itextpdf.text.pdf.security.ExternalSignature;
import com.itextpdf.text.pdf.security.MakeSignature;
import com.itextpdf.text.pdf.security.PrivateKeySignature;
import com.itextpdf.text.pdf.security.TSAClientBouncyCastle;

import org.bouncycastle.jce.provider.BouncyCastleProvider;

import java.io.FileOutputStream;
import java.io.IOException;
import java.security.GeneralSecurityException;
import java.security.KeyStore;
import java.security.PrivateKey;
import java.security.Security;
import java.security.cert.Certificate;
import java.util.Enumeration;

/**
 * @ClassName: SignPdfWithTimestamp
 * @Description: TODO
 * @Author: ZhangZeYu
 * @date: 2024/7/3 14:39
 * @Version: V1.0
 */
public class SignPdfWithTimestamp {

    public static void main(String[] args) throws IOException, GeneralSecurityException, DocumentException {
        // 添加BouncyCastleProvider
        Security.insertProviderAt(new BouncyCastleProvider(), 1);

        // PDF文件路径
        String src = "E:/pdfszzs.pdf";
        // 签名后PDF文件路径
        String dest = "E:/pdfszzs22.pdf";
        // PKCS#12文件路径
        String pkcs12 = "E:/1111.pfx";
        // PKCS#12文件密码
        String password = "1111";
        // TSA服务器URL
        String tsaUrl = "http://your-tsa-server.com/ts";

        // 加载证书和私钥
        KeyStore ks = KeyStore.getInstance("PKCS12");
        ks.load(new java.io.FileInputStream(pkcs12), password.toCharArray());
        Enumeration aliases = ks.aliases();
        String alias = aliases.nextElement();
        PrivateKey pk = (PrivateKey) ks.getKey(alias, password.toCharArray());
        Certificate[] chain = ks.getCertificateChain(alias);

        // 创建PDF阅读器和签署者
        PdfReader reader = new PdfReader(src);
        FileOutputStream os = new FileOutputStream(dest);
        PdfStamper stamper = PdfStamper.createSignature(reader, os, '\0');
        PdfSignatureAppearance appearance = stamper.getSignatureAppearance();
        appearance.setReason("Signed by example");
        appearance.setLocation("Somewhere");

        // 设置签名外观的其他属性,如签名位置等

        // 创建签名和摘要实例
        ExternalSignature pks = new PrivateKeySignature(pk, "SHA-256", "BC");
        ExternalDigest digest = new BouncyCastleDigest();

        // 创建时间戳客户端
        TSAClientBouncyCastle tsaClient = new TSAClientBouncyCastle(tsaUrl);

        // 执行签名并应用时间戳
        MakeSignature.signDetached(appearance, digest, pks, chain, null, null, tsaClient, 0, MakeSignature.CryptoStandard.CMS);

        // 关闭资源
        stamper.close();
        os.close();
    }
}

你可能感兴趣的:(pdf,java)