簡體   English   中英

com.itextpdf.text.exceptions.InvalidPdfException:未找到PDF標頭簽名

[英]com.itextpdf.text.exceptions.InvalidPdfException: PDF header signature not found

嘗試對PDF文檔進行數字簽名時出現此錯誤。 傳遞兩個pdf格式的SOURCEPDF名稱和DESTINATIONPDF名稱(數字簽名)pdf名稱。 在第一次在SOURCEPDF上進行數字簽名后,我得到了DESTINATIONPDF。 對於第二次數字簽名,使用DESTINATIONPDF作為源pdf和目標pdf。

這是我的代碼

try
{
    for(int i=1;i<=signature_Count;i++)
    {
        if(i==1)
        {
            tmpPdfSource=sourcePdfPath;
        }else{
            this.tmpPdfSource=destinationPdfPath;
        }

        int pageNo=Integer.parseInt(ad.readXML(xmlString, rootName,"PageNo-"+i));
        String imageSource=ad.readXML(xmlString, rootName,"ImageSource-"+i);
        float llx=Float.parseFloat(ad.readXML(xmlString, rootName,"llx-"+i));
        float lly=Float.parseFloat(ad.readXML(xmlString, rootName,"lly-"+i));
        float urx=Float.parseFloat(ad.readXML(xmlString, rootName,"urx-"+i));
        float ury=Float.parseFloat(ad.readXML(xmlString, rootName,"ury-"+i));
        String signature=ad.readXML(xmlString, rootName,"SignatureName-"+i);

        File dest = new File(destinationPdfPath);
        KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
        ks.load(new Fil eInputStream(certificatePath), keystore_password.toCharArray());
        String alias = (String) ks.aliases().nextElement();
        PrivateKey pk = (PrivateKey) ks.getKey(alias,key_password.toCharArray());
        java.security.cert.Certificate[] chain = ks.getCertificateChain(alias);
        PdfReader reader = new PdfReader(tmpPdfSource);
        stamper = PdfStamper.createSignature(reader,new FileOutputStream(dest), '\0', null, true);
        PdfSignatureAppearance appearance = stamper.getSignatureAppearance();

        appearance.setCrypto(pk, chain, null,PdfSignatureAppearance.SELF_SIGNED);

        if (true)
        {
            appearance.setAcro6Layers(true);
            Image img=Image.getInstance(imageSource);
            appearance.setImage(img);
            appearance.setVisibleSignature(new com.itextpdf.text.Rectangle(llx, lly, urx, ury), pageNo, signature);
        }
    }//for
    stamper.close();
} catch (Exception e) {
    GenericLog gl=new  GenericLog();
    gl.writeWarning("Error Occured in SignPdfDocument ");
    gl.writeError(e);
    e.printStackTrace();
}

請幫助我修復此錯誤。

重新格式化代碼以使其可讀后,問題出現了:

for(int i=1;i<=signature_Count;i++)
{
    if(i==1)
    {
        tmpPdfSource=sourcePdfPath;
    }else{
        this.tmpPdfSource=destinationPdfPath;
    }
    [...]
    File dest = new File(destinationPdfPath);
    [...]
    PdfReader reader = new PdfReader(tmpPdfSource);
    stamper = PdfStamper.createSignature(reader,new FileOutputStream(dest), '\0', null, true);
    [...]
}//for
stamper.close();

從第二次迭代你閱讀由生成的文件PdfStamper前次迭代中,你必須關閉stamper在迭代結束時,不應超出for循環:

    stamper = PdfStamper.createSignature(reader,new FileOutputStream(dest), '\0', null, true);
    [...]
    stamper.close();
}//for

此外,您最好將new FileOutputStream(dest)放入變量中,並在關閉stamper:后立即將其顯式關閉stamper:

    FileOutputStream fout = new FileOutputStream(dest);
    stamper = PdfStamper.createSignature(reader, fout, '\0', null, true);
    [...]
    stamper.close();
    fout.close();
}//for

當然,請遵循Bruno的建議,閱讀他的PDF簽名白皮書,並更新您的簽名創建代碼以生成非棄用類型的簽名。

我看到了setCrypto()方法,這意味着您沒有使用最新版本的iText。 我還看到選項PdfSignatureAppearance.SELF_SIGNED ,這意味着您正在創建的簽名不再符合當今的標准。

您能幫個忙,閱讀文檔嗎?

另外:您正在使用與源和目標相同的文件嗎? 這不可能。 您至少需要創建一個臨時文件或在內存中創建該文件,然后覆蓋現有文件。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM