java - 无需为每个文件调用登录即可签署多个 PDF

标签 java pdf itext pkcs#11

当我要签署多个 PDF 文件时,我遇到了一个问题。

我的代码是:

public void signPDF(X509Certificate cert, List<File> fInl, List<File> fOutl,
                    PrivateKey key)
            throws IOException, NoSuchAlgorithmException, 
                   NoSuchProviderException, InvalidParameterSpecException,
                   DocumentException, InvalidKeyException,
                   SignatureException, KeyStoreException,
                   CertificateException, UnrecoverableKeyException {

    Certificate[] cc = new Certificate []{cert};

    int i=0;

    for(i=0;i<fInl.size();i++){
        PdfReader reader = new PdfReader(fInl.get(i).getAbsolutePath());
        FileOutputStream outputFile = new FileOutputStream(fOutl.get(i).getAbsolutePath());
        PdfStamper stamper = PdfStamper.createSignature(reader, outputFile, '\0');
        PdfSignatureAppearance sap = stamper.getSignatureAppearance();
        sap.setVisibleSignature(new Rectangle(100, 100, 200, 200), 1, null);

        Calendar cal = Calendar.getInstance();
        PdfSignature dic = new PdfSignature(PdfName.ADOBE_PPKLITE, PdfName.ADBE_PKCS7_DETACHED);
        dic.setDate(new PdfDate(cal));
        dic.setName(PdfPKCS7.getSubjectFields((X509Certificate)cc[0]).getField("CN"));
        sap.setCryptoDictionary(dic);
        sap.setLayer2Text("Digitally signed by "+ dic.get(PdfName.NAME) +"\n\nDate: " + cal.getTime().toString());

        HashMap<PdfName,Object> exc = new HashMap<PdfName,Object>();
        exc.put(PdfName.CONTENTS, new Integer(0x2502));
        sap.preClose(exc);

        PdfPKCS7 pk7 = new PdfPKCS7(key, cc, null, "SHA1", null, false);
        MessageDigest messageDigest = MessageDigest.getInstance("SHA1");
        byte buf[] = new byte[8192];
        int n;
        InputStream inp = sap.getRangeStream();

        while ((n = inp.read(buf)) > 0) {
            messageDigest.update(buf, 0, n);
        }

        byte hash[] = messageDigest.digest();
        byte sh[] = pk7.getAuthenticatedAttributeBytes(hash, cal);
        pk7.update(sh, 0, sh.length);

        PdfDictionary dic2 = new PdfDictionary();
        byte sg[] = pk7.getEncodedPKCS7(hash, cal);
        byte out[] = new byte[0x2500 / 2];

        System.arraycopy(sg, 0, out, 0, sg.length);
        dic2.put(PdfName.CONTENTS, new PdfString(out).setHexWriting(true));
        sap.close(dic2);
    }
}

它可以工作,但会为每个文件调用“登录 token ”。

在这一行 byte sh[] = pk7.getEncodedPKCS7(hash, cal); 总是调用安装证书的登录,我只想调用一次。

我该如何解决?

最佳答案

你得到这个是因为你在 for 循环中有那一行。因此,该行将在每次迭代时执行。

要解决这个问题,您必须先进行身份验证,然后循环结果。

希望对您有所帮助!
继续编码
战神。

关于java - 无需为每个文件调用登录即可签署多个 PDF,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26258313/

相关文章:

java - 使用缓冲读取器时出错

java - young GC 暂停与 STW 暂停

javascript - 我正在使用 html2pdf 生成 pdf,我可以隐藏 html 以便用户看不到它吗?

php - 我无法将 pdf 上传到我的 mysql 数据库

java - iText Java 到 PDF : how to output a JPanel without having to add it to the Container

c# - 使用 iTextSharp 完成 PDF 中的复选框

java - 将 Java byte[] 解释为字符串

java - 如何从方法返回 ArrayList<String>?

java - iText PdfStamper 增加签名 pdf 的大小

java - 使用iTextpdf删除java中的pdf页面