I'm currently working on an api which generate a pdf file with some customer report and contain some pdf atatchments related to the report. I am adding an attachment to the PDF using PDFBox library in Java by referring to the code snippet, Adding a File Attachment
I successfully attached the document created using ByteArrayInputStream to the attachment. However, when I try to open the attachment in the document using Adobe reader or any PDF viewer tool I am getting the error as in the screenshot.
If I use the ef.setSubtype("text/plain") and file extension as '.txt' I am able to open the attachment successfully. The code snippet I used is as below,
@GetMapping("/generate-pdf")
public ResponseEntity<InputStreamResource> generatePDFWithAttachment() {
try {
final PDDocument doc = new PDDocument();
PDPage page = new PDPage();
doc.addPage(page);
PDPageContentStream contentStream = new PDPageContentStream(doc, page);
contentStream.beginText();
contentStream.setFont(PDType1Font.HELVETICA, 15);
contentStream.newLineAtOffset(100, 700);
contentStream.setNonStrokingColor(Color.red);
contentStream.showText("Go to Document -> File Attachments to View Embedded Files");
Map<String, String> keyValueMap = new HashMap<>();
keyValueMap.put("file1.pdf", "test element 1");
keyValueMap.put("file2.pdf", "test element 2");
//------- start attachment section
// embedded files are stored in a named tree
// create a new tree node and add the embedded file
PDEmbeddedFilesNameTreeNode efTree = new PDEmbeddedFilesNameTreeNode();
Map<String, PDComplexFileSpecification> treeNodeMap = new HashMap<>();
for (Map.Entry<String, String> entry : keyValueMap.entrySet()) {
// first create the file specification, which holds the embedded file
PDComplexFileSpecification fs = new PDComplexFileSpecification();
fs.setFile(entry.getKey());
// create a dummy file stream, this would probably normally be a FileInputStream
byte[] data = entry.getValue().getBytes();
ByteArrayInputStream fakeFile = new ByteArrayInputStream(data);
// now lets some of the optional parameters
PDEmbeddedFile ef = new PDEmbeddedFile(doc, fakeFile);
ef.setSubtype("application/pdf");
ef.setSize(data.length);
ef.setCreationDate(Calendar.getInstance());
fs.setEmbeddedFile(ef);
treeNodeMap.put(entry.getKey(), fs);
}
efTree.setNames(treeNodeMap);
PDDocumentNameDictionary names = new PDDocumentNameDictionary(doc.getDocumentCatalog());
names.setEmbeddedFiles(efTree);
doc.getDocumentCatalog().setNames(names);
//------- end attachment section
contentStream.endText();
contentStream.close();
ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
doc.save(outputStream);
doc.close();
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_PDF);
headers.setContentDispositionFormData("attachment", "sample.pdf");
InputStreamResource resource = new InputStreamResource(new ByteArrayInputStream(outputStream.toByteArray()));
return ResponseEntity.ok()
.headers(headers)
.body(resource);
} catch (IOException e) {
System.err.println("Exception while trying to create pdf document - " + e);
}
return null;
}
I assume attachments can contain file of type .pdf. I also tried by providing the charset parameter to UTF_8 byte[] data = entry.getValue().getBytes(StandardCharsets.UTF_8); and that also didn't helps