Jersey: how to get temporary file

I use Jersey with flash uploader and the problem I met is that I need to determine “file partialy uploaded” situation ’cause user has an opportunity to cancel it at any time. All solutions that I found for this problem were on PHP (look for The uploaded file was only partially uploaded text). I didn’t find any standart technics how to get size of uploaded file (uploaded file’s input stream doesn’t has such information) to compare it with actual file size. So I used a “little reflection magic” to get it. ’cause classes that we’ll use to get information is private for org.jvnet.mimepull package we need to create out util class in exactly the same package. Then we can use reflection to get any infomation that we need.

Listing of TemporaryFileUtil class:

package org.jvnet.mimepull;
 
import java.io.File;
import java.lang.reflect.Field;
 
public class TemporaryFileUtil {
 
    // -------------------------------------------------------
    // -                        LOGIC                        -
    // -------------------------------------------------------
 
    private static Object readFieldValue(String fieldName, Object o) throws Exception {
        Field field = o.getClass().getDeclaredField(fieldName);
        field.setAccessible(true);
        return field.get(o);
    }
 
    private static File getFile(DataHead dataHead) {
        try {
            DataFile dataFile = (DataFile) dataHead.getClass().getDeclaredField("dataFile").get(dataHead);
 
            if (dataFile != null) {
                WeakDataFile weakDataFile = (WeakDataFile) readFieldValue("weak", dataFile);
                return (File) readFieldValue("file", weakDataFile);
            }
        } catch (Exception ignored) {
        }
 
        return null;
    }
 
    public static long getSize(MIMEPart part) {
        try {
            DataHead dataHead = (DataHead) readFieldValue("dataHead", part);
            File file = getFile(dataHead);
 
            if (file != null) {
                // Temporary file was created for uploaded file.
                return file.length();
            } else {
                // Uploaded file stored in memory.
                return (Long) readFieldValue("inMemory", dataHead);
            }
        } catch (Exception ignored) {
        }
 
        return -1;
    }
 
}

Usage example:

@POST
@Path("/upload-new-file/")
@Consumes(MediaType.MULTIPART_FORM_DATA)
@Produces(MediaType.TEXT_HTML)
public String uploadNewMusicFile(@FormDataParam("Filedata") FormDataBodyPart newFileBodyPart) {
    if (isFilePartiallyUploaded(newFileBodyPart)) {
        return null;
    }
 
    ...
}
 
protected boolean isFilePartiallyUploaded(FormDataBodyPart bodyPart) {
    FormDataMultiPart multiPart = (FormDataMultiPart) bodyPart.getParent();
 
    // This information is provides by Flash object and attaches to request's data.
    long realFileSize = Long.valueOf(multiPart.getField("Filesize").getValue());
 
    long uploadedFileSize = 0;
 
    BodyPartEntity entity = (BodyPartEntity) bodyPart.getEntity();
 
    try {
        Field mimePartField = entity.getClass().getDeclaredField("mimePart");
        mimePartField.setAccessible(true);
        MIMEPart mimePart = (MIMEPart) mimePartField.get(entity);
        uploadedFileSize = TemporaryFileUtil.getSize(mimePart);
    } catch (Exception e) {
        log.error("Can't get uploaded file size.");
        log.error(e);
        throw new RestServiceException();
    }
 
    return (realFileSize != uploadedFileSize);
}

2 thoughts on “Jersey: how to get temporary file

    1. Alexander Shchekoldin Post author

      Я ставил вот этот плагин для WordPress. Очень клёвый, поддерживает огромную кучу языков. Правда при большом количестве кода заметно грузит комп при отрисовке страницы.

      Reply

Leave a Reply

Your email address will not be published. Required fields are marked *