Here is the test code:
package test;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Collections;
import java.util.GregorianCalendar;
import java.util.List;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDDocumentNameDictionary;
import org.apache.pdfbox.pdmodel.PDEmbeddedFilesNameTreeNode;
import org.apache.pdfbox.pdmodel.common.PDNameTreeNode;
import
org.apache.pdfbox.pdmodel.common.filespecification.PDComplexFileSpecification;
import org.apache.pdfbox.pdmodel.common.filespecification.PDEmbeddedFile;
public class TestAddAttchmentPdfBox {
public static void main(String[] args) throws Exception {
String filePath = "yourPath";
byte[] originalPdfFile = readFileByteArray(filePath + "278418_Verbale.pdf");
String[] attachmentsFileName = {
"145_schizzo-01.pdf",
"145_schizzo-02.pdf",
"145_schizzo-03.pdf",
"145_schizzo-04.pdf",
"145_schizzo-05.pdf",
"145_schizzo-06.pdf",
"145_schizzo-07.pdf",
"145_schizzo-08.pdf",
"145_schizzo-09.pdf",
"145_schizzo-10.pdf",
"145_schizzo-11.pdf",
"145_schizzo-12.pdf",
"145_schizzo-13.pdf",
"145_schizzo-14.pdf",
};
List<Attachment> attachments = new ArrayList<Attachment>();
load(attachments,attachmentsFileName,filePath);
byte[] pdfFileWithAttachment =
addAttachmentsToPdf(originalPdfFile,attachments);
saveToFileByteArray(pdfFileWithAttachment,filePath + "result.pdf");
}
private static void load(List<Attachment> attachments, String[]
attachmentsFileName, String filePath) throws IOException {
for (String fileName : attachmentsFileName) {
Attachment att = new Attachment();
att.setFileName(fileName);
att.setFile(readFileByteArray(filePath + fileName));
attachments.add(att);
}
}
public static byte[] addAttachmentsToPdf(byte[] originalPdfFile,
List<Attachment> attachments) throws Exception {
PDDocument doc = PDDocument.load(new ByteArrayInputStream(originalPdfFile));
PDEmbeddedFilesNameTreeNode efTree;
int attCounter = 0;
for (Attachment att : attachments) {
String attName = att.getFileName();
if (attName == null || attName.length() == 0)
attName = "no_name_"+ attCounter;
if (doc.getDocumentCatalog().getNames() == null ||
doc.getDocumentCatalog().getNames().getEmbeddedFiles() == null)
efTree = new PDEmbeddedFilesNameTreeNode();
else
efTree = doc.getDocumentCatalog().getNames().getEmbeddedFiles();
//first create the file specification, which holds the embedded file
PDComplexFileSpecification fs = new PDComplexFileSpecification();
fs.setFile(attName);
InputStream is = new ByteArrayInputStream(att.getFile());
PDEmbeddedFile ef = new PDEmbeddedFile(doc, is);
//set some of the attributes of the embedded file
//ef.setSubtype("test/plain");
ef.setSize(att.getFile().length);
ef.setCreationDate(new GregorianCalendar());
fs.setEmbeddedFile(ef);
// create a new tree node and add the embedded file
PDEmbeddedFilesNameTreeNode treeNode = new PDEmbeddedFilesNameTreeNode();
treeNode.setNames(Collections.singletonMap( "My first attachment" +
attCounter++, fs ));
// add the new node as kid to the root node
List<PDNameTreeNode> kids = efTree.getKids();
if (kids == null)
kids = new ArrayList<PDNameTreeNode>();
kids.add(treeNode);
efTree.setKids(kids);
// add the tree to the document catalog
PDDocumentNameDictionary names = new
PDDocumentNameDictionary(doc.getDocumentCatalog());
names.setEmbeddedFiles( efTree );
doc.getDocumentCatalog().setNames(names);
}
ByteArrayOutputStream baos = new ByteArrayOutputStream();
doc.save(baos);
return baos.toByteArray();
}
// ========================================================
// ================ UTILITY METHODS =======================
// ========================================================
public static byte[] readFileByteArray(String fileName) throws IOException {
File file = new File(fileName);
FileInputStream fis = new FileInputStream(file);
byte fileContent[] = new byte[(int) file.length()];
fis.read(fileContent);
return fileContent;
}
public static void saveToFileByteArray(byte[] byteArray, String fileName)
throws IOException {
File file = new File(fileName);
FileOutputStream fos = new FileOutputStream(file);
fos.write(byteArray);
fos.close();
}
}
class Attachment {
private String fileName;
private byte[] file;
public String getFileName() {
return fileName;
}
public void setFileName(String fileName) {
this.fileName = fileName;
}
public byte[] getFile() {
return file;
}
public void setFile(byte[] file) {
this.file = file;
}
}
On Mon, Dec 1, 2014 at 12:22 PM, Marco Rossi <[email protected]> wrote:
> Hi Tilman,
> in attachment the test code (you can try with any file to attach) .
> Actually I found that the problem must be the Adobe Acrobat Reader, with
> Foxit Reader there isn't problems.
>
> Unfortunately, almost everyone is using adobe ... :-(
>
> Marco
>
> On Fri, Nov 28, 2014 at 6:57 PM, Tilman Hausherr <[email protected]>
> wrote:
>
>> Hi,
>>
>> Could you upload the PDF file somewhere, and post the code you used here?
>>
>> "but I can open / save only the first 10 item" - I assume you mean within
>> Adobe Reader?
>>
>> Tilman
>>
>> Am 28.11.2014 um 12:48 schrieb Marco Rossi:
>>
>> Hi,
>>> I need to create a pdf file with 21 attachment; the file is created
>>> without
>>> errors, but I can open / save only the first 10 item. For the others I
>>> see
>>> only the name.
>>>
>>> It's possible to bypass this limit?
>>>
>>> Thanks in advance,
>>> Marco
>>>
>>>
>>
>