undeleted temp files in the temp directory
Posted: Tue Jul 06, 2010 6:15 am
While using the createImagePart method of the BinaryPartAbstractImage class a tmp file is created which is not deleted after it's usage.
Therefore the temp directory, of the user who is executing the jvm in which docx4j is used, is flooded if the method is used frequently.
- Used jar file: http://dev.plutext.org/docx4j/docx4j-nightly-20100630.jar
- Package containing the mentioned class: org.docx4j.openpackaging.parts.WordprocessingML
"Bug" - Enviroment:
- User: smokie
- OS Windows 7 x64
- Tempdir = C:\Users\smokie\AppData\Local\Temp
(Could also reproduce the bug under WIN XP / Just the temp dirs location differs)
Buggy-Code:
Fix is probably (recently I have had a similar error/problem):
FileInputStream fis = new FileInputStream(tmpImageFile); //reuse
imagePart.setBinaryData( fis );
fis.close();
imagePart.rel = sourcePart.addTargetPart(imagePart, proposedRelId);
imagePart.setImageInfo(info);
// Delete the tmp file
//tmpImageFile.delete();
if (!tmpImageFile.delete()) { code which handels / reports that the file couldn't be deleted}
I would have attached a patch but I wasn't able to test the fix, because I wasn't able to build the project from source.
Thanks for developing such a nice opensource framework and I hope this post is helping to improve it.
so long
Nicola Coretti
Therefore the temp directory, of the user who is executing the jvm in which docx4j is used, is flooded if the method is used frequently.
- Used jar file: http://dev.plutext.org/docx4j/docx4j-nightly-20100630.jar
- Package containing the mentioned class: org.docx4j.openpackaging.parts.WordprocessingML
"Bug" - Enviroment:
- User: smokie
- OS Windows 7 x64
- Tempdir = C:\Users\smokie\AppData\Local\Temp
(Could also reproduce the bug under WIN XP / Just the temp dirs location differs)
- Code: Select all
import java.io.File;
import java.io.FileInputStream;
import java.io.InputStream;
import org.docx4j.dml.wordprocessingDrawing.Inline;
import org.docx4j.jaxb.Context;
import org.docx4j.openpackaging.packages.WordprocessingMLPackage;
import org.docx4j.openpackaging.parts.WordprocessingML.BinaryPartAbstractImage;
import org.docx4j.utils.BufferUtil;
import org.docx4j.wml.Drawing;
import org.docx4j.wml.P;
import org.docx4j.wml.R;
public class Main {
/**
* Just a simple example which is reproducing an bug in the docx4j framework.
*/
public static void main(String[] args) throws Exception {
// Create the package
WordprocessingMLPackage wordMLPackage = WordprocessingMLPackage.createPackage();
// file object pointing to the picture which i wana use
File myImage = new File("C:\\Users\\smokie\\Pictures\\me.jpg");
// open an input stream to get the bytes of the picture
InputStream inputStream = new FileInputStream(myImage);
// get the bytes of the picture
byte[] imageBytes = BufferUtil.getBytesFromInputStream(inputStream);
// the next line of code will produce the "error"
// the method call will create a temp file in the users temp dir which is not removed!!
BinaryPartAbstractImage imagePart = BinaryPartAbstractImage.createImagePart(wordMLPackage, imageBytes);
// close the input stream
inputStream.close();
// put the picture into the document
Inline inlineImage = imagePart.createImageInline("filenameHint", "altText", 1, 2, false);
P p = Context.getWmlObjectFactory().createP();
R r = Context.getWmlObjectFactory().createR();
Drawing drawing = Context.getWmlObjectFactory().createDrawing();
drawing.getAnchorOrInline().add(inlineImage);
r.getRunContent().add(drawing);
p.getParagraphContent().add(r);
wordMLPackage.getMainDocumentPart().addObject(p);
// Save the document
wordMLPackage.save(new java.io.File("C:\\Users\\smokie\\DocxWithImage.docx") );
}
}
Buggy-Code:
- Code: Select all
/**
* Create an image part from the provided byte array, attach it to the source part
* (eg the main document part, a header part etc), and return it.
*
* @param wordMLPackage
* @param sourcePart
* @param bytes
* @return
* @throws Exception
*/
public static BinaryPartAbstractImage createImagePart(
WordprocessingMLPackage wordMLPackage,
Part sourcePart, byte[] bytes) throws Exception {
// Whatever image type this is, we're going to need
// to know its dimensions.
// For that we use ImageInfo, which can only
// load an image from a URI.
// So first, write the bytes to a temp file
File tmpImageFile = File.createTempFile("img", ".img");
FileOutputStream fos = new FileOutputStream(tmpImageFile);
fos.write(bytes);
fos.close();
log.debug("created tmp file: " + tmpImageFile.getAbsolutePath() );
ImageInfo info = ensureFormatIsSupported(tmpImageFile.getAbsolutePath(), tmpImageFile, bytes);
// In the absence of an exception, tmpImageFile now contains an image
// Word will accept
ContentTypeManager ctm = wordMLPackage.getContentTypeManager();
String proposedRelId = sourcePart.getRelationshipsPart().getNextId();
// In order to ensure unique part name,
// idea is to use the relId, which ought to be unique
BinaryPartAbstractImage imagePart =
(BinaryPartAbstractImage)ctm.newPartForContentType(
info.getMimeType(),
IMAGE_PREFIX + proposedRelId );
log.debug("created part " + imagePart.getClass().getName() +
" with name " + imagePart.getPartName().toString() );
FileInputStream fis = new FileInputStream(tmpImageFile); //reuse
imagePart.setBinaryData( fis );
imagePart.rel = sourcePart.addTargetPart(imagePart, proposedRelId);
imagePart.setImageInfo(info);
// Delete the tmp file
tmpImageFile.delete();
return imagePart;
}
Fix is probably (recently I have had a similar error/problem):
FileInputStream fis = new FileInputStream(tmpImageFile); //reuse
imagePart.setBinaryData( fis );
fis.close();
imagePart.rel = sourcePart.addTargetPart(imagePart, proposedRelId);
imagePart.setImageInfo(info);
// Delete the tmp file
//tmpImageFile.delete();
if (!tmpImageFile.delete()) { code which handels / reports that the file couldn't be deleted}
I would have attached a patch but I wasn't able to test the fix, because I wasn't able to build the project from source.
Thanks for developing such a nice opensource framework and I hope this post is helping to improve it.
so long
Nicola Coretti