签名在修订版2中无效 - 由附件引起

时间:2013-08-13 10:53:53

标签: pdf adobe digital-signature acrobat pdfbox

我刚刚编写了将文件附加到PDF文档的代码。我在PDFBox页面上看过代码。

PDEmbeddedFilesNameTreeNode efTree = new PDEmbeddedFilesNameTreeNode();

PDComplexFileSpecification fs = new PDComplexFileSpecification();
fs.setFile( "Test.txt" );
InputStream is = ...;
PDEmbeddedFile ef = new PDEmbeddedFile(doc, is );
ef.setSubtype( "test/plain" );
ef.setSize( data.length );
ef.setCreationDate( new GregorianCalendar() );
fs.setEmbeddedFile( ef );
Map efMap = new HashMap();
efMap.put( "My first attachment", fs );
efTree.setNames( efMap );
PDDocumentNameDictionary names = new PDDocumentNameDictionary( doc.getDocumentCatalog() );
names.setEmbeddedFiles( efTree );
doc.getDocumentCatalog().setNames( names );
doc.save("attachedPDF"); 

那,有效。

然后,我附加文件和签名文件。 结果是 - 一切正常!

然后,我获得了已签名的文档(其中包含附件),然后使用其他附件对文档进行签名(我创建了修订版2)换句话说,我将另一个文件附加到签名文档并再次签名)。结果 ,没有旧文件。新文件覆盖了旧文件(签名也变得无效,因为更改了哈希 - 这是正确的);

所以,我这样做是为了从PDEmbeddedFilesNameTreeNode获取oldFiles并添加到新的文件映射。

PDEmbeddedFilesNameTreeNode oldFiles=names.getEmbeddedFiles();
        if(oldFiles!=null){
            Map oldFilesMap = oldFiles.getNames();
            Iterator iterator = oldFilesMap.entrySet().iterator();
            while (iterator.hasNext()) {
                Map.Entry mapEntry = (Map.Entry) iterator.next();
                System.out.println("The key is: " + mapEntry.getKey()+ ",value is :" + mapEntry.getValue());
                efMap.put(mapEntry.getKey(),  mapEntry.getValue());
            }

        }
efTree.setNames(efMap);

有效。但是当我创建第二个修订版时,签名再次无效。 我认为,主要的问题是,当我将新文件添加到同一文件NameDictionary时,文档的哈希值会发生变化。

所以,我认为,我应该在下一个版本中创建新的NameDictionary,可能是我错了(我不能使用现有的NameDictionary)。我不明白我能知道什么吗?你觉得怎么样?

顺便说一句,我觉得这对我来说不合适,对于下一次修订

PDDocumentNameDictionary names = new PDDocumentNameDictionary(doc.getDocumentCatalog());

那是my sample documents

1 个答案:

答案 0 :(得分:2)

  

然后,我获得了已签名的文档(其中包含附件),然后使用其他附件对文档进行签名(我创建了修订版2)换句话说,我将另一个文件附加到签名文档并再次签名。

无论你遇到什么其他问题,这项任务本身已经注定失败。即使您以增量更新的方式执行此操作,也不会对签名文档执行此操作。

以前签署的文件允许的操作要么受到规范的限制(如果是认证签名),要么通过认证规则的推断(仅限批准签名)。

如果是认证签名( DocMDP 签名), DocMDP转换参数字典中的 P 值会选择允许的操作集文件:

  

(可选)为此文档授予的访问权限。有效值应为:

     

1不允许对文件进行任何更改;对文件的任何更改都将使签名无效。

     

2允许的更改应填写表格,实例化页面模板和签名;其他更改将使签名无效。

     

3允许的更改应与2相同,以及注释创建,删除和修改;其他变更将使签名无效。

     

默认值:2。

     

ISO 32000-1中的第12.8.2.2.2节)

如您所见,附加文件不在其中。

不幸的是,如果没有认证签名( DocMDP 签名),说明书没有明确说明应允许哪些更改;因此,人们可能会假设一切都被允许。

实际上,当前的PDF查看器,尤其是主流的Adobe Reader,采用不同的方式,并推断出一组允许的更改。如果Adobe Reader(参见this answer了解详细信息)与 DocMDP 相同, P = 3 加上签名字段。 (假设作者没有真正考虑签名用例,因此可能忘记添加空签名字段;否则,允许更改的集合被认为是适当的。)

因此,也没有附加文件。

如果要处理多个附件和多个签名,您可以考虑通过创建新PDF来补充已签名的PDF,将原始PDF和新文件添加为附件(并设置enw PDF以显示原始PDF默认情况下),然后签署整个构造。

PS:关于您的实际尝试:当您尝试操作已签名的文档DOC-signed.pdf时,您似乎已经开始使用PDFBox读取和写入它;我假设这是因为DOC-signed.pdf 不是 DOC-signed-signed.pdf的起始部分,但后一个文档确实包含新附件和增量更新中的第二个签名。

这导致原始文件在内部重新组织,并且原始签名在此过程中被破坏。您应该首先创建文件的相同副本,然后将第二个签名添加为增量更新。