我有一个程序可以生成包含大量数据的报告。我使用 Apache POI SXSSF 生成 xlsx 文件,一切正常。 http://poi.apache.org/spreadsheet/index.html
我在他们的文档中找不到的是如何使用密码保护整个工作簿。我希望这样,如果有人尝试打开该文件,他们需要输入密码才能查看数据。
请记住,这与密码保护单个工作表不同,他们仍然能够打开文件并查看数据,但具有只读访问权限。
我在 SXSSFWorkbook 文档中没有找到任何内容:https://poi.apache.org/apidocs/org/apache/poi/xssf/streaming/SXSSFWorkbook.html
看起来 XSSFWorkbook 有一个名为 setWorkbookPassword 的方法,但 SXSSF 不存在该方法,并且在 SXSSFWorkbook 上不起作用。 https://poi.apache.org/apidocs/org/apache/poi/xssf/usermodel/XSSFWorkbook.html#setWorkbookPassword(java.lang.String,%20org.apache.poi.poifs.crypt.HashAlgorithm)
有人知道如何做到这一点吗?还将考虑替代解决方法。
提前致谢。
更新
我考虑过可能使用启用宏的工作簿和脚本来对其进行密码保护,如此处建议的那样。 Java Apache Poi SXSSF 与 Excel 宏
我使用此处的 VBA 代码来执行此操作:http://analysistabs.com/excel-vba/protect-unprotect-workbook/,然后在创建 Excel 文件时使用该文件作为模板,但当我尝试使用宏,结果发现这还不够。某些计算机安全设置设置为“高”并且将禁用宏,因此当我打开文件时,我确实收到了输入密码的提示,但随后我还收到了一条警告消息,指出宏已被禁用,并且我能够查看工作簿内容。
有什么建议吗?
“...我在他们的文档中找不到如何密码保护...”???
您有看到poi主页左侧菜单中的菜单项“加密支持”吗?
要在打开(即读取)文件时请求密码提示,您需要对其进行加密 - 请参阅并且 stackoverflow 喜欢将所有内容集中在一处 - 这是代码:
// create a new POIFSFileSystem, which is the container for
// encrypted OOXML-based files
POIFSFileSystem fs = new POIFSFileSystem();
EncryptionInfo info = new EncryptionInfo(EncryptionMode.agile);
// setup the encryption
Encryptor enc = info.getEncryptor();
enc.confirmPassword("foobaa");
// after writing to the SXSSF workbook you need the content
// as a stream
InputStream is = <open the SXSSF workbook as stream>
OutputStream os = enc.getDataStream(fs);
// copy the stream to the OutputStream
IOUtils.copy(is, os);
// Write out the encrypted version
FileOutputStream fos = new FileOutputStream("...");
fs.writeFilesystem(fos);
fos.close();
/**
* create a new POIFSFileSystem, which is the container to encrypt xml based files.
* Setup encryption and pass your respected password.
* Take encrypted output stream and Encrypt the work book.
* Finally write the encrypted version of workbook to Filesystem
*/
public static void getExcelEncryption(XSSFWorkbook workbook,HttpServletResponse response,String password) {
try (POIFSFileSystem fs = new POIFSFileSystem()) {
EncryptionInfo info = new EncryptionInfo(EncryptionMode.agile);
Encryptor enc = info.getEncryptor();
String paswordForExcel = !password.isEmpty() ? password : "";
enc.confirmPassword(paswordForExcel);
try (OutputStream os = enc.getDataStream(fs)) {
workbook.write(os);
} catch (Exception e) {
logger.error("OutputStream error while encrypting excel : {}",e.getMessage());
}
fs.writeFilesystem(response.getOutputStream());
} catch (Exception e) {
logger.error("POIFSFileSystem error while encrypting excel : {}",e.getMessage());
}
}