本文主要是介绍word、pdf、excel及zip加密(含示例效果及工具类),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
基于POI、zip4j 给word、pdf、excel及zip加密
- 需求说明:
- 1、所需依赖:
- 2、文档加密方法工具类:
- 测试文档加密工具类
- 4、 zip包加密工具类
- 5、ZIP 方式1测试:
- 6:zip2加密方式测试 :
需求说明:
许多人希望能够对自己的Office文件以及压缩的ZIP文件进行加密,以防止未经授权的访问和信息泄露。然而,使用WPS、Microsoft Office软件或其它压缩工具逐一对每一个文件进行加密,实在是耗时且费力,往往让人感到疲惫与沮丧。
因此,本文将详细介绍一种更为高效的解决方案,以免大家在人力和时间上面无谓的消耗。本文的主要内容结构包括以下几个部分:
1、所需依赖
2、文档类加密工具类 + 测试示例
3、zip包加密工具类 + 测试示例
效果如下:
1、所需依赖:
提前声明(JAR包版本已经经过筛选 尽量不用对依赖做变更,不然部分方法或者类不存在)且注意各个POI依赖之间的版本信息。
<!--其他包 与主题无关 为保完整性故完整列出 --><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter</artifactId></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-test</artifactId><scope>test</scope></dependency><dependency><groupId>junit</groupId><artifactId>junit</artifactId><version>4.13.1</version><scope>test</scope></dependency><dependency><groupId>org.slf4j</groupId><artifactId>slf4j-api</artifactId><version>1.7.21</version></dependency><!-- https://mvnrepository.com/artifact/org.slf4j/slf4j-log4j12 --><dependency><groupId>org.slf4j</groupId><artifactId>slf4j-log4j12</artifactId><version>1.7.25</version><scope>compile</scope></dependency><!-- office加密所需 --><dependency><groupId>org.apache.pdfbox</groupId><artifactId>pdfbox</artifactId><version>2.0.27</version></dependency><dependency><groupId>com.itextpdf</groupId><artifactId>itext7-core</artifactId><version>7.1.11</version><type>pom</type></dependency><dependency><groupId>org.freemarker</groupId><artifactId>freemarker</artifactId></dependency><!-- Apache POI --><dependency><groupId>org.apache.poi</groupId><artifactId>poi</artifactId><version>5.2.3</version></dependency><dependency><groupId>org.apache.poi</groupId><artifactId>poi-ooxml</artifactId><version>5.2.3</version></dependency><dependency><groupId>org.apache.poi</groupId><artifactId>poi-ooxml-schemas</artifactId><version>4.1.2</version></dependency><dependency><groupId>org.apache.xmlbeans</groupId><artifactId>xmlbeans</artifactId><version>5.1.1</version></dependency><dependency><groupId>org.apache.commons</groupId><artifactId>commons-collections4</artifactId><version>4.4</version></dependency><dependency><groupId>fr.opensagres.xdocreport</groupId><artifactId>fr.opensagres.xdocreport.converter.docx.xwpf</artifactId><version>1.0.6</version></dependency><!--ZIP包加密 所需 --><dependency><groupId>net.lingala.zip4j</groupId><artifactId>zip4j</artifactId><version>2.9.1</version></dependency>
2、文档加密方法工具类:
package com.example.demo;import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.encryption.StandardProtectionPolicy;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.poifs.crypt.EncryptionInfo;
import org.apache.poi.poifs.crypt.EncryptionMode;
import org.apache.poi.poifs.crypt.Encryptor;
import org.apache.poi.poifs.crypt.standard.StandardEncryptor;
import org.apache.poi.poifs.filesystem.POIFSFileSystem;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.apache.poi.xwpf.usermodel.XWPFDocument;import java.io.*;
import java.nio.file.Files;/*** 类描述:文件加密工具类 (word、excel、pdf )* 如有新增 请补充到描述中。** @author xú* @since 1.0.0 2024-08-27 04:45:19*/
public class DocumentEncryptionUtil {private DocumentEncryptionUtil() {}/*** 方法描述:加密word文件** @param file 文件* @param password 密码* @author xú* @since 1.0.0 2024-08-27 04:46:54*/public static void encryptWordFile(File file, String password) {try (POIFSFileSystem fs = new POIFSFileSystem();FileInputStream fis = new FileInputStream(file);XWPFDocument document = new XWPFDocument(fis)) {EncryptionInfo info = new EncryptionInfo(EncryptionMode.agile);Encryptor encryptor = info.getEncryptor();encryptor.confirmPassword(password);try (OutputStream os = encryptor.getDataStream(fs)) {document.write(os);}try (FileOutputStream fos = new FileOutputStream(file)) {fs.writeFilesystem(fos);}//System.out.println("Encrypted Word file: " + file.getAbsolutePath());} catch (org.apache.pdfbox.pdmodel.encryption.InvalidPasswordException e) {//System.out.println("已加密");} catch (Exception e) {e.printStackTrace();}}/*** 方法描述:加密excel-xlsx** @param file 文件* @param password 密码* @author xú * @since 1.0.0 2024-08-27 05:10:51*/public static void encryptExcelXlsx(File file, String password) {try (POIFSFileSystem fs = new POIFSFileSystem();FileInputStream fis = new FileInputStream(file);XSSFWorkbook workbook = new XSSFWorkbook(fis)) {EncryptionInfo info = new EncryptionInfo(EncryptionMode.agile);Encryptor encryptor = info.getEncryptor();encryptor.confirmPassword(password);try (OutputStream os = encryptor.getDataStream(fs)) {workbook.write(os);}try (FileOutputStream fos = new FileOutputStream(file)) {fs.writeFilesystem(fos);}//System.out.println("Encrypted Excel file: " + file.getAbsolutePath());} catch (org.apache.pdfbox.pdmodel.encryption.InvalidPasswordException e) {//System.out.println("已加密");} catch (Exception e) {e.printStackTrace();}}/*** 方法描述:加密excel-xls** @param file 文件* @param password 密码* @author xú * @since 1.0.0 2024-08-27 05:10:45*/public static void encryptExcelXls(File file, String password) {try (POIFSFileSystem fs = new POIFSFileSystem(); FileInputStream fis = new FileInputStream(file);HSSFWorkbook workbook = new HSSFWorkbook(fis)) {EncryptionInfo info = new EncryptionInfo(EncryptionMode.standard);StandardEncryptor encryptor = (StandardEncryptor) info.getEncryptor();encryptor.confirmPassword(password);try (OutputStream os = encryptor.getDataStream(fs)) {workbook.write(os);}try (FileOutputStream fos = new FileOutputStream(file)) {fs.writeFilesystem(fos);}System.out.println("Encrypted Excel file: " + file.getAbsolutePath());} catch (Exception e) {e.printStackTrace();}}/*** 方法描述:加密pdf文件** @param file 文件* @param password 密码* @author xú* @since 1.0.0 2024-08-27 04:46:05*/public static void encryptPdfFile(File file, String password) {try (PDDocument document = PDDocument.load(file)) {// Set the encryption optionsStandardProtectionPolicy policy = new StandardProtectionPolicy(password, password, new org.apache.pdfbox.pdmodel.encryption.AccessPermission());policy.setEncryptionKeyLength(128); // You can set the key length to 128 or 256 bitsdocument.protect(policy);document.save(file);//System.out.println("Encrypted PDF file: " + file.getAbsolutePath());} catch (org.apache.pdfbox.pdmodel.encryption.InvalidPasswordException e) {//System.out.println("已加密");} catch (Exception e) {e.printStackTrace();}}
}
测试文档加密工具类
3、测试及测试结果展示:
public static void main(String[] args) {String directoryPath = "D:\\桌面\\项目文档"; // 替换为你本地的路径String backupDirectoryPath = "D:\\桌面\\备份"; // 替换为你的备份路径String password = "aaaaa111112DDD"; // 密码设置try {Files.createDirectories(Paths.get(backupDirectoryPath));Files.walkFileTree(Paths.get(directoryPath), new SimpleFileVisitor<>() {@Overridepublic FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {String fileName = file.getFileName().toString().toLowerCase();if (fileName.endsWith(".docx") || fileName.endsWith(".xlsx") || fileName.endsWith(".pdf")) {Path backupFile = Paths.get(backupDirectoryPath, file.toString().substring(directoryPath.length()));Files.createDirectories(backupFile.getParent());Files.copy(file, backupFile, StandardCopyOption.REPLACE_EXISTING);try {if (fileName.endsWith(".docx")) {encryptWordFile(file.toFile(), password);} else if (fileName.endsWith(".xlsx")) {encryptExcelFile(file.toFile(), password);} else if (fileName.endsWith(".pdf")) {encryptPdfFile(file.toFile(), password);}}catch (Exception ex){ex.printStackTrace();}System.out.println("Processed file: " + file.toString());} else {System.out.println("Skipped file: " + file.toString());}return FileVisitResult.CONTINUE;}@Overridepublic FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) throws IOException {Path backupDir = Paths.get(backupDirectoryPath, dir.toString().substring(directoryPath.length()));Files.createDirectories(backupDir);System.out.println("Directory: " + dir.toString());return FileVisitResult.CONTINUE;}});} catch (IOException e) {e.printStackTrace();}}
4、 zip包加密工具类
package com.example.demo;import net.lingala.zip4j.ZipFile;
import net.lingala.zip4j.model.FileHeader;
import net.lingala.zip4j.model.ZipParameters;
import net.lingala.zip4j.model.enums.CompressionLevel;
import net.lingala.zip4j.model.enums.CompressionMethod;
import net.lingala.zip4j.model.enums.EncryptionMethod;import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;/*** 类描述:zip包加密工具类** @author xú chūn chéng* @version 1.0.0* @since 1.0.0 2024-08-27 04:49:55*/
public class ZipEncryptionUtil {private ZipEncryptionUtil() {}/*** 方法描述:使用旧zip创建加密zip** @param oldZipFile 需要加密的zip包文件* @param password 密码* @author xú* @since 1.0.0 2024-08-27 04:49:50*/public static void createEncryptedZipWithOldZip(File oldZipFile, String password) {//创建新的加密zip文件String newZipFileName = oldZipFile.getParent() + File.separator + "encrypted_" + oldZipFile.getName();try (ZipFile newEncryptedZipFile = new ZipFile(newZipFileName, password.toCharArray())) {//设置加密的zip参数ZipParameters zipParameters = new ZipParameters();zipParameters.setCompressionMethod(CompressionMethod.DEFLATE);zipParameters.setCompressionLevel(CompressionLevel.NORMAL);zipParameters.setEncryptFiles(true);zipParameters.setEncryptionMethod(EncryptionMethod.AES);// 将旧的zip文件添加到新的加密zip文件中newEncryptedZipFile.addFile(oldZipFile, zipParameters);} catch (IOException e) {throw new RuntimeException(e);}//System.out.println("Created encrypted ZIP file: " + newZipFileName);}/*** 方法描述:加密zip文件 (会把OLD压缩文件解压开 然后重新打包加密) 慎用* ( 这种加密方式存在问题 当文件内部多层级的时候无法正常加密 且中文乱码)** @param file 文件* @param password 密码* @author xú chūn chéng* @since 1.0.0 2024-08-27 04:48:46*/public static void encryptZipFile(File file, String password) {try {File tempDir;try (ZipFile zipFile = new ZipFile(file, password.toCharArray())) {// 设置压缩文件ZipParameters zipParameters = new ZipParameters();zipParameters.setCompressionMethod(CompressionMethod.DEFLATE);zipParameters.setCompressionLevel(CompressionLevel.NORMAL);zipParameters.setEncryptFiles(true);zipParameters.setEncryptionMethod(EncryptionMethod.AES);//将所有文件解压缩到临时目录tempDir = Files.createTempDirectory("zip4j").toFile();zipFile.extractAll(tempDir.getAbsolutePath());// 从zip中删除所有文件List<FileHeader> fileHeaders = zipFile.getFileHeaders();List<FileHeader> headersToRemove = new ArrayList<>(fileHeaders); // 将要删除的文件头收集到一个新列表中for (FileHeader fileHeader : headersToRemove) {zipFile.removeFile(fileHeader);}//使用加密重新打包文件for (File extractedFile : Objects.requireNonNull(tempDir.listFiles())) {zipFile.addFile(extractedFile, zipParameters);}}//清理临时目录for (File extractedFile : Objects.requireNonNull(tempDir.listFiles())) {extractedFile.delete();}tempDir.delete();//System.out.println("Encrypted ZIP file: " + file.getAbsolutePath());} catch (IOException e) {e.printStackTrace();}}
}
5、ZIP 方式1测试:
public static void main(String[] args) {String directoryPath = "D:\\桌面\\新建文件夹\\已压缩_未归类"; // 替换为你本地的路径String backupDirectoryPath = "D:\\桌面\\备份"; // 替换为你的备份路径String password = "741841aaa333.";//密码 long maxSize = 1024L * 1024L * 1024L; // 1GBtry {Files.createDirectories(Paths.get(backupDirectoryPath));// 首先收集所有要处理的文件List<Path> filesToProcess = new ArrayList<>();Files.walkFileTree(Paths.get(directoryPath), new SimpleFileVisitor<>() {@Overridepublic FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {String fileName = file.getFileName().toString().toLowerCase();//由于超过1G的文件处理时间过长 所需对此文件大小进行限制 最大为1GBif (fileName.endsWith(".zip") && Files.size(file) <= maxSize) {filesToProcess.add(file);}return FileVisitResult.CONTINUE;}@Overridepublic FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) throws IOException {Path backupDir = Paths.get(backupDirectoryPath, dir.toString().substring(directoryPath.length()));Files.createDirectories(backupDir);return FileVisitResult.CONTINUE;}});// 然后处理收集到的文件int totalFiles = filesToProcess.size();for (int i = 0; i < totalFiles; i++) {Path file = filesToProcess.get(i);Path backupFile = Paths.get(backupDirectoryPath, file.toString().substring(directoryPath.length()));Files.createDirectories(backupFile.getParent());Files.copy(file, backupFile, StandardCopyOption.REPLACE_EXISTING);ZipEncryptionUtil.encryptZipFile(file.toFile(), password);// 记录进度System.out.printf("Processed file (%d/%d): %s%n", i + 1, totalFiles, file.toString());}} catch (IOException e) {e.printStackTrace();}}
6:zip2加密方式测试 :
需要创建一个新的 ZIP 文件,并将原有的 ZIP 文件(OLD 压缩文件)作为一个单独的文件放入新 ZIP 文件中,同时对新 ZIP 文件进行加密。
方法测试:
public static void main(String[] args) {String directoryPath = "D:\\桌面\\AAA"; // 替换为你本地的路径String backupDirectoryPath = "D:\\桌面\\备份"; // 替换为你的备份路径String password = "ssssssss.";long maxSize = 1024L * 1024L * 1024L; // 1GBtry {Files.createDirectories(Paths.get(backupDirectoryPath));// 首先收集所有要处理的文件List<Path> filesToProcess = new ArrayList<>();Files.walkFileTree(Paths.get(directoryPath), new SimpleFileVisitor<>() {@Overridepublic FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {String fileName = file.getFileName().toString().toLowerCase();if (fileName.endsWith(".zip") && Files.size(file) <= maxSize) {filesToProcess.add(file);}return FileVisitResult.CONTINUE;}@Overridepublic FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) throws IOException {Path backupDir = Paths.get(backupDirectoryPath, dir.toString().substring(directoryPath.length()));Files.createDirectories(backupDir);return FileVisitResult.CONTINUE;}});// 然后处理收集到的文件int totalFiles = filesToProcess.size();for (int i = 0; i < totalFiles; i++) {Path file = filesToProcess.get(i);Path backupFile = Paths.get(backupDirectoryPath, file.toString().substring(directoryPath.length()));Files.createDirectories(backupFile.getParent());Files.copy(file, backupFile, StandardCopyOption.REPLACE_EXISTING);ZipEncryptionUtil.createEncryptedZipWithOldZip(file.toFile(), password);// 记录进度System.out.printf("Processed file (%d/%d): %s%n", i + 1, totalFiles, file.toString());}} catch (IOException e) {e.printStackTrace();}}
这篇关于word、pdf、excel及zip加密(含示例效果及工具类)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!