我正在做一个实现,我们的系统生成一个PDF文件供用户下载。我们的过程和系统的关键是,这个PDF文件不应该被用户或用户计算机上的程序修改(至少,不是没有恶意的),因为文件可以在稍后上传到系统中,我们需要通过比较它的哈希值来确定文件处于它的原始状态。
我们认为我们首先禁用所有权限(CanModify,CanAssembleDocument等),然后使用所有者的密码加密文档,从而实现了这一点。这阻止了我们可以访问的所有阅读器对文件的修改。现在,我们的一个用户在Acrobat Reader中打开PDF文件并将文档“另存为”到一个新的PDF文件时,就会修改该文件。我们不能用同样的读者版本(2015.006.30497)复制这个,但他每次都可以。
对我们来说,签署PDF文档不是一种选择,至少不是使用PKI或用户可以在阅读器中看到的任何可见签名。如果有某种隐形的签约选择,那将是很好的,但我不知道如何。
下面是我们用来锁定PDF的代码。出于测试目的,我们禁用了所有权限,但没有任何效果。我们使用的是PDFBox 2.0.11。
有什么建议有什么选项可以更好地锁定文件进行修改?
public static byte[] SealFile(byte[] pdfFile, String password) throws IOException
{ PDDocument doc =PDDocument.load(pdfFile);
ByteArrayOutputStream bos= new ByteArrayOutputStream();
byte[] returnvalue =null;
int keyLength = 256;
AccessPermission ap = new AccessPermission();
//Disable all
ap.setCanModifyAnnotations(false);
ap.setCanAssembleDocument(false); .
ap.setCanFillInForm(false);
ap.setCanModify(false);
ap.setCanExtractContent(false);
ap.setCanExtractForAccessibility(false);
ap.setCanPrint(false);
//The user password is empty ("") so user can read without password. The admin password is
// set to lock/encrypt the document.
StandardProtectionPolicy spp = new StandardProtectionPolicy(password, "", ap);
spp.setEncryptionKeyLength(keyLength);
spp.setPermissions(ap);
doc.protect(spp);
doc.save(bos);
doc.close();
bos.flush();
return bos.toByteArray();
}
这将导致Adobe属性:
/*
* This method is used to add the 'appendOnly flag' to the PDF document. This flag is part of
* the AcroForm functionality that instructs a PDF reader that the file is signed and should not be
* modified during the 'saved as' function. For full description see PDF specification PDF 32000-1:2008
* (https://www.adobe.com/content/dam/acom/en/devnet/pdf/pdfs/PDF32000_2008.pdf)
* paragraph 12.7.2 Interactive Form Dictionary
*/
public static void addAcroFormSigFlags(PDDocument pdfDoc) {
PDDocumentCatalog catalog = pdfDoc.getDocumentCatalog();
PDAcroForm acroForm = catalog.getAcroForm();
if (acroForm == null) {
acroForm = new PDAcroForm(pdfDoc);
catalog.setAcroForm(acroForm);
}
// AppendOnly:
// If set, the document contains signatures that may be invalidated if the
// file is saved (wirtten) in a way that alters its previous contents, as
// opposed to an incremental update. Merely updating the file by appending
// new information to the end of the previous version is safe (see h.7,
// "Updating Example"). Conforming readers may use this flag to inform a
// user requesting a full save that signatures will be invalidated and
// require explicit confirmation before continuing with the operation
acroForm.setAppendOnly(true);
// SignatureExists: (Currently not used by us)
// If set, the document contains at least one signature field. This flag
// allows a conforming reader to enable user interface items (such as menu
// items or pushbuttons) related to signature processing without having to
// scan the entire document for the presence of signature fields.
// acroForm.setSignaturesExist(true);
// flag objects that changed (in case a 'saveIncremental' is done hereafter)
catalog.getCOSObject().setNeedToBeUpdated(true);
acroForm.getCOSObject().setNeedToBeUpdated(true);
}
即使实际签署PDF文档对您来说不是一个选项,您也可以尝试设置AcroForm标志来声明存在签名。
这将防止对这些标志敏感的程序(如Adobe Reader)将更改应用到PDF,或者至少它们应该将更改应用为增量更新,而增量更新可以通过截断文件的原始大小来撤消。
所讨论的flags条目是AcroForm字典中的SigFlags条目。
1-SignaturesExist-如果设置,文档至少包含一个签名字段。该标志允许交互式PDF处理器启用与签名处理相关的用户界面项(例如菜单项或按钮),而不必扫描整个文档以查找签名字段的存在。
2-AppendOnly-如果设置了,文档包含的签名可能会在文件以改变其先前内容的方式保存(写入)而不是增量更新时失效。仅仅通过在上一版本的末尾添加新信息来更新文件是安全的(见H.7,“更新示例”)。交互式PDF处理器可以使用该标志通知请求完全保存的用户签名将无效,并且在继续操作之前需要明确的确认。
(ISO 32000-2,表225-签名标志)
守护进程系统线程[Java2D Disposer](暂停(异常OutOfMemoryError))拥有:Win32Graphics环境(id=116)拥有:FontStrikeDisposer(id=117)D3DGraphicsDevice.getDeviceCaps(int)line: 108 D3DGraphicsDevice.createDevice(int)line: 87 Win32G
我有以下问题: 我在我的Java应用程序中使用算法“RSA/ECB/PKCS1Padding”进行加密和解密。 问候
修剪docker时遇到了问题。构建映像后,我运行“docker系统修剪-卷-a-f”,但它不会从“/var/lib/docker/overlay2”释放空间。请参阅下面 在构建映像之前,请先释放磁盘空间 塑造形象 图像生成后的大小: 它只释放了122.2MB。修剪后的尺寸: 如您所见,共有0个容器/图像: 但是"/var/lib/docker/overlay2"的大小只从3.9G减少到3.7G。如
但是当我运行redis-cli时,我仍然得到输出中的值: 为什么redis的钥匙没有被移除?供参考:所有的东西都在我的本地机器上测试,只包括Redis。
设置: 具有一个片段的活动,该片段通过单击按钮进行实例化。在fragment的构造函数中,使用了Bundle。在Bundle和ArrayList中 问题:分离片段时,字符串(姓氏)会按预期销毁,但数组列表会持续存在。因此,在调用片段的新实例时,会出现前一个ArrayList条目。回调不是问题所在。该行为也会在没有回调的情况下出现。 我已经检查了变量(和)和在点片段构造函数(),片段在方法()和片段
问题内容: 我注意到这个构造函数非常痛苦(即使在Stack Overflow上也是如此)。即使文档明确指出,人们仍会使用它: 此构造函数的结果可能无法预测 http://java.sun.com/javase/6/docs/api/java/math/BigDecimal.html#BigDecimal(double) 我什至看到JSR-13得到批准,并提出了以下建议: 可能不推荐使用的现有规范: