Apache Poi 관련 트러블 슈팅 - [POI Encryption, java.lang.NoClassDefFoundError : org/apache/poi/ss/usermodel/Date1904Support]

Denia·2023년 7월 30일
0

이슈 1 - java.lang.NoClassDefFoundError : org/apache/poi/ss/usermodel/Date1904Support

apache poi 와 apache poi-ooxml 의 버전이 맞지 않아서 발생하는 문제

해결 방법

  • build.gradle에서 두 개의 버전을 통일시킨다.
  • apache poi를 Dependency에서 제거하니 ooxml 안에 poi에 관한 의존성이 존재해서 문제 해결 [ooxml 안에 존재하는 poi 의존성은 ooxml 과 버전이 맞는 걸로 들어가 있었다.]

이슈 2 - POI Encryption 이슈

기존에 사용하던 POI 와 OOXML은 3버전대를 사용했다.
해당 라이브러리들을 4버전대로 버전업을 하니 몇가지 문제가 발생했다.

해결 방법

  1. 기존에 사용하던 코드 일부가 변경되었다. (static 상수에서 ENUM으로 모두 변경되었다.)
    • 메서드의 매개변수 자료형 타입을 보고 해당하는 ENUM을 사용하면 해결
  2. Encryption하는 코드 방식이 변경되었다.
    • 3버전대에서 사용하는 Encryption 방법 (참고 블로그)
    • 4버전대는 해당 방식을 사용 못함
      • 그래서 공식문서에 나와있는대로 다시 코드 작성

공식문서

//공식문서에 나와있는 코드

try (POIFSFileSystem fs = new POIFSFileSystem()) {
	EncryptionInfo info = new EncryptionInfo(EncryptionMode.agile);
    // EncryptionInfo info = new EncryptionInfo(EncryptionMode.agile, CipherAlgorithm.aes192, HashAlgorithm.sha384, -1, -1, null);
	Encryptor enc = info.getEncryptor();
	enc.confirmPassword("foobaa");
	// Read in an existing OOXML file and write to encrypted output stream
	// don't forget to close the output stream otherwise the padding bytes aren't added
	try (OPCPackage opc = OPCPackage.open(new File("..."), PackageAccess.READ_WRITE);
		OutputStream os = enc.getDataStream(fs)) {
			opc.save(os);
	}
	// Write out the encrypted version
	try (FileOutputStream fos = new FileOutputStream("...")) {
		fs.writeFilesystem(fos);
	}
}

//출처 : https://poi.apache.org/encryption.html

내가 짠 코드

//제가 짠 코드 - 참고만 해주세요.
            
String path = "/usr/test/";
String fileName = "example.xlsx";

try {
    Workbook wb = new XSSFWorkbook();
    Sheet sheet = wb.createSheet("sheet1");
    Row row = null;
    Cell cell = null;
    
    row = sheet.createRow(0);

    cell = row.createCell(0);
    cell.setCellValue("이름");
    cell = row.createCell(1);
    cell.setCellValue("나이");
    cell = row.createCell(2);
    cell.setCellValue("직업");

    ByteArrayOutputStream fileOut = new ByteArrayOutputStream();
    wb.write(fileOut);

    try (POIFSFileSystem fileSystem = new POIFSFileSystem()) {
        EncryptionInfo encryptionInfo = new EncryptionInfo(EncryptionMode.agile);

        Encryptor encryptor = encryptionInfo.getEncryptor();
        encryptor.confirmPassword("myPassword");

        // Read in an existing OOXML file and write to encrypted output stream
        // don't forget to close the output stream otherwise the padding bytes aren't added
        try (OPCPackage opc = OPCPackage.open(new ByteArrayInputStream(fileOut.toByteArray()));
             OutputStream os = encryptor.getDataStream(fileSystem)) {
            opc.save(os);
        }
        // Write out the encrypted version
        try (FileOutputStream fos = new FileOutputStream(path + fileName)) {
            fileSystem.writeFilesystem(fos);
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
    fileOut.close();
} catch (Exception e) {
    e.printStackTrace();
}
profile
HW -> FW -> Web

0개의 댓글

Powered by GraphCDN, the GraphQL CDN