workspace-uploader/src/main/java/org/gcube/portlets/widgets/workspaceuploader/server/upload/AbstractUploadProgressListe...

260 lines
6.5 KiB
Java

package org.gcube.portlets.widgets.workspaceuploader.server.upload;
import java.io.Serializable;
import javax.servlet.http.HttpSession;
import org.apache.commons.fileupload.ProgressListener;
import org.gcube.portlets.widgets.workspaceuploader.shared.UploadProgress;
import org.gcube.portlets.widgets.workspaceuploader.shared.event.UploadProgressChangeEvent;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
* The listener interface for receiving uploadProgress events. The class that is
* interested in processing a uploadProgress event implements this interface,
* and the object created with that class is registered with a component using
* the component's <code>addUploadProgressListener<code> method. When
* the uploadProgress event occurs, that object's appropriate
* method is invoked.
*
* @see UploadProgressEvent
*/
public abstract class AbstractUploadProgressListener implements
ProgressListener, Serializable {
/**
*
*/
private static final long serialVersionUID = 9039352626573789199L;
private static final double COMPLETE_PERECENTAGE = 100d;
private int percentage = -1;
private UploadProgress uploadProgress;
private int percentageOffset = 0;
private double completePercentage = COMPLETE_PERECENTAGE;
private static Logger logger = LoggerFactory
.getLogger(AbstractUploadProgressListener.class);
protected RuntimeException exception = null;
protected boolean exceptionTrhown = false;
protected String sessionId;
public static AbstractUploadProgressListener current(String sessionId) {
throw new RuntimeException(
"Implement the static method 'current' in your customized class");
}
protected Long bytesRead = 0L, contentLength = 0L;
private String clientUploadKey;
// protected static HttpServletRequest request;
protected String sessionKey;
private HttpSession session;
/**
* Save itself in session or cache.
*/
public abstract void save();
/**
* Remove itself from session or cache.
*/
public abstract void remove();
/**
* Instantiates a new upload progress listener.
*
* @param request
* the request
* @param uploadProgress
* the upload progress
* @param percentageOffset
* the percentage offset
* @param completePercentage
* the complete percentage
*/
public AbstractUploadProgressListener(HttpSession session,
String clientUploadKey, int percentageOffset,
double completePercentage) {
this.sessionId = session.getId();
this.session = session;
this.clientUploadKey = clientUploadKey;
this.sessionKey = sessionId + ":" + clientUploadKey;
this.uploadProgress = new UploadProgress();
this.percentageOffset = percentageOffset;
this.completePercentage = completePercentage;
logger.debug("Session key: " + sessionKey);
save();
}
/**
* @return the session
*/
public HttpSession getSession() {
return session;
}
/*
* (non-Javadoc)
*
* @see org.apache.commons.fileupload.ProgressListener#update(long, long,
* int)
*/
@Override
public void update(final long bytesRead, final long totalBytes, final int items) {
if (exceptionTrhown) {
return;
}
// If other request has set an exception, it is thrown so the
// commons-fileupload's
// parser stops and the connection is closed.
if (isCanceled()) {
String eName = exception.getClass().getName()
.replaceAll("^.+\\.", "");
logger.info(AbstractUploadProgressListener.class.getName() + " "
+ sessionKey + " The upload has been canceled after "
+ bytesRead + " bytes received, raising an exception ("
+ eName + ") to close the socket");
exceptionTrhown = true;
throw exception;
}
this.bytesRead = bytesRead;
this.contentLength = totalBytes;
int percentage = percentageOffset
+ ((int) Math.floor(((double) bytesRead / (double) totalBytes)
* completePercentage));
if (this.percentage == percentage)
return;
this.percentage = percentage;
UploadProgressChangeEvent event = new UploadProgressChangeEvent();
event.setReadPercentage(percentage);
event.setReadTime(System.currentTimeMillis());
// logger.trace("Updating percentage.. "+percentage);
synchronized (this.uploadProgress) {
// logger.trace("Adding event: "+event);
this.uploadProgress.add(event);
// this.uploadProgress.notifyAll();
}
}
/**
* @return the bytesRead
*/
public Long getBytesRead() {
return bytesRead;
}
/**
* @return the contentLength
*/
public Long getContentLength() {
return contentLength;
}
/**
* Gets the upload progress.
*
* @return the uploadProgress
*/
public UploadProgress getUploadProgress() {
return uploadProgress;
}
/**
* Get the exception.
*
* @return the exception
*/
public RuntimeException getException() {
return exception;
}
/**
* Return true if the process has been canceled due to an error or by the
* user.
*
* @return boolean
*/
public boolean isCanceled() {
return exception != null;
}
/**
* Set the exception which cancels the upload.
*
*/
public void setException(RuntimeException e) {
logger.info("Set RuntimeException to cancel upload");
exception = e;
save();
}
/**
* @return the percentage
*/
public int getPercentage() {
return percentage;
}
/**
* @return the clientUploadKey
*/
public String getClientUploadKey() {
return clientUploadKey;
}
/**
* Gets the session key.
*
* @param httpSessionId
* the http session id
* @param clientUploadKey
* the client upload key
* @return the session key
*/
public static String getSessionKey(String httpSessionId, String clientUploadKey) {
return httpSessionId + ":" + clientUploadKey;
}
/* (non-Javadoc)
* @see java.lang.Object#toString()
*/
@Override
public String toString() {
StringBuilder builder = new StringBuilder();
builder.append("AbstractUploadProgressListener [percentage=");
builder.append(percentage);
builder.append(", percentageOffset=");
builder.append(percentageOffset);
builder.append(", completePercentage=");
builder.append(completePercentage);
builder.append(", exception=");
builder.append(exception);
builder.append(", exceptionTrhown=");
builder.append(exceptionTrhown);
builder.append(", sessionId=");
builder.append(sessionId);
builder.append(", bytesRead=");
builder.append(bytesRead);
builder.append(", contentLength=");
builder.append(contentLength);
builder.append(", clientUploadKey=");
builder.append(clientUploadKey);
builder.append(", sessionKey=");
builder.append(sessionKey);
builder.append("]");
return builder.toString();
}
}