使用jQuery UI进度条和ajax与Chrome时的奇怪行为

时间:2022-11-24 13:40:18

Recently I am trying the jQuery UI progress bar with ajax for building a file upload progress bar.

最近我正在尝试使用ajax构建文件上传进度条的jQuery UI进度条。

It works like charm in IE and firefox, but the behavior in Chrome is very weird, which makes me think I have done something wrong in the coding part.

它在IE和Firefox中的功能就像魅力一样,但Chrome中的行为非常奇怪,这让我觉得我在编码部分做错了。

My design is to loop the ajax function to retrieve the upload bytes read from a servlet, and it works in IE and firefox.

我的设计是循环ajax函数来检索从servlet读取的上传字节,它在IE和Firefox中工作。

However, when running in Chrome, the ajax function can only retrieve the upload bytes read one time only, aka the loop only success for the first time.

但是,在Chrome中运行时,ajax函数只能检索一次读取的上传字节,也就是第一次仅循环成功。

使用jQuery UI进度条和ajax与Chrome时的奇怪行为

At the bottom left corner of the Chrome browser, the upload percent counter shows the upload is still running, which makes me think the problem is related to the ajax call.

在Chrome浏览器的左下角,上传百分比计数器显示上传仍在运行,这让我觉得问题与ajax调用有关。

I have tried to print the error message from ajax, but turns out there is no error message.

我试图从ajax打印错误消息,但事实证明没有错误消息。

使用jQuery UI进度条和ajax与Chrome时的奇怪行为

Please find below my source codes:

请在下面找到我的源代码:

ajax:

       function doProgressLoop() {
            setTimeout("getProgress()", 1500);
            setTimeout("doProgressLoop()", 2000);
        }

        function getProgress() {
            jQuery.ajax({
                type: "POST",
                url: "/processUpload",
                dataType: "text",
                data: "",
                success: function(data) {
                    console.log(data);
                    if(data != "null" && parseInt(data) < 100) {
                        progressbar.progressbar("value", parseInt(data));
                    }
                },
                error: function(jqXHR, textStatus, errorThrown) {
                    alert(textStatus + ": " + errorThrown);
                    console.log(textStatus + ": " + errorThrown);
                }
            });
        }

        function fSubmit() {
            jQuery("#submit").attr("disabled", "disabled");
            progressbar.show();
            doProgressLoop();
            setTimeout("jQuery('#hiddenSubmit').click()", 2000);
        }

Servlet:

public void doPost(HttpServletRequest request, HttpServletResponse response) throws IOException {

        response.setContentType("text/html");
        response.setHeader("Cache-Control", "no-cache");
        PrintWriter out = response.getWriter();

        HttpSession session = request.getSession(true);

        if (session == null) {
            System.out.println("HTTPSession is null");
            out.println("HTTPSession: null");
            return;
        }

        ProgressEntity entity = (ProgressEntity) session.getAttribute("upload_file");

        if(entity == null) {
            logger.info("entity is null");
            out.println("null");
        } else {
            logger.info("entity: " + entity.getPercentDone());
            out.println(String.valueOf(entity.getPercentDone()));
        }

    }

ProgressListener:

public class UploadProgressListener implements ProgressListener {

private HttpSession session;
private int percentDone = 0;
private long bytesRead;
private long contentLength;
private int items;

private static final Logger logger = Logger.getLogger(UploadProgressListener.class);

public UploadProgressListener(HttpSession session) {
    this.session = session;
    ProgressEntity entity = new ProgressEntity();
    session.setAttribute("upload_file", entity);
}

public void update(long bytesRead, long contentLength, int items) {

    ProgressEntity entity = (ProgressEntity) session.getAttribute("upload_file");

    entity.setBytesRead(bytesRead);
    entity.setContentLength(contentLength);
    entity.setItems(items);

    session.setAttribute("upload_file", entity);

    this.bytesRead = bytesRead;
    this.contentLength = contentLength;
    this.items = items;

}

public long getBytesRead() {
    return this.bytesRead;
}

}

MultipartResolver:

public class ProgressUploadMultipartResolver extends CommonsMultipartResolver {

private HttpServletRequest request;
private static final Logger logger = Logger.getLogger(ProgressUploadMultipartResolver.class);

protected FileUpload newFileUpload(FileItemFactory fileItemFactory) {

    ServletFileUpload upload = new ServletFileUpload(fileItemFactory);
    upload.setSizeMax(-1);

    if(request != null) {
        HttpSession session = request.getSession();
        UploadProgressListener uploadProgressListener = new UploadProgressListener(session);
        upload.setProgressListener(uploadProgressListener);
    }

    return upload;
}

@Override
public MultipartHttpServletRequest resolveMultipart (HttpServletRequest request) throws MultipartException {
    this.request = request;
    return super.resolveMultipart(request);
}

@Override
public MultipartParsingResult parseRequest(HttpServletRequest request) throws MultipartException {
    HttpSession session = request.getSession();

    String encoding = "utf-8";
    FileUpload fileUpload = prepareFileUpload(encoding);

    UploadProgressListener uploadProgressListener = new UploadProgressListener(session);
    fileUpload.setProgressListener(uploadProgressListener);
    try {

        List<FileItem> fileItems = ((ServletFileUpload) fileUpload).parseRequest(request);
        return parseFileItems(fileItems, encoding);

    } catch(FileUploadBase.SizeLimitExceededException e) {
        e.printStackTrace();
    } catch (FileUploadException e) {
        e.printStackTrace();
    }

    return null;
}

}

Progress Info:

public class ProgressEntity {

private long bytesRead = 0L;
private long contentLength = 0L;
private int items;

public long getBytesRead() {
    return bytesRead;
}
public void setBytesRead(long bytesRead) {
    this.bytesRead = bytesRead;
}
public long getContentLength() {
    return contentLength;
}
public void setContentLength(long contentLength) {
    this.contentLength = contentLength;
}
public int getItems() {
    return items;
}
public void setItems(int items) {
    this.items = items;
}

}

Please let me know if you need me to provide any more source code.

如果您需要我提供更多源代码,请告诉我。

Thank you very much!

非常感谢你!

Update:

Please find above the Javascript functions for progress bar.

请在上面找到进度条的Javascript函数。

fSubmit() function will be called when the submit button is clicked.

单击提交按钮时将调用fSubmit()函数。

Update2:

Others java codes are added as well.

其他java代码也被添加。

1 个解决方案

#1


0  

As no one can suggest a suitable answer (maybe my question is too weird??),

因为没人能提出合适的答案(也许我的问题太奇怪了?),

here I would like to answer my own question on how I finally get it done,

在这里,我想回答一下我最终如何完成它的问题,

so that if anyone encounter similar issue, they will have one possible solution to try out.

所以,如果有人遇到类似的问题,他们将有一个可能的解决方案尝试。

The answer is very simple,

答案很简单,

I create an iframe in the jsp, and set the target of the form to that iframe,

我在jsp中创建了一个iframe,并将表单的目标设置为iframe,

then the progress bar in Chrome works like charm.

那么Chrome中的进度条就像魅力一样。

I am really too new to the field of ajax and jQuery so I don't know why just an iframe will solve this problem which bother me for a week......

我真的对ajax和jQuery这个领域太新了所以我不知道为什么只有一个iframe会解决这个困扰我一周的问题......

Although I have to deal with another problem since the end point jsp is now showing inside the iframe instead of the parent page, at least the progress bar is working across all common browsers, and the redirect issue is another mystery to solve for tomorrow......

虽然我必须处理另一个问题,因为结束点jsp现在显示在iframe而不是父页面中,至少进度条适用于所有常见的浏览器,重定向问题是明天要解决的另一个谜。 ....

Anyway hope anyone encounter this issue can try out this method, wish you good luck.

无论如何希望任何人遇到这个问题都可以尝试这种方法,祝你好运。

#1


0  

As no one can suggest a suitable answer (maybe my question is too weird??),

因为没人能提出合适的答案(也许我的问题太奇怪了?),

here I would like to answer my own question on how I finally get it done,

在这里,我想回答一下我最终如何完成它的问题,

so that if anyone encounter similar issue, they will have one possible solution to try out.

所以,如果有人遇到类似的问题,他们将有一个可能的解决方案尝试。

The answer is very simple,

答案很简单,

I create an iframe in the jsp, and set the target of the form to that iframe,

我在jsp中创建了一个iframe,并将表单的目标设置为iframe,

then the progress bar in Chrome works like charm.

那么Chrome中的进度条就像魅力一样。

I am really too new to the field of ajax and jQuery so I don't know why just an iframe will solve this problem which bother me for a week......

我真的对ajax和jQuery这个领域太新了所以我不知道为什么只有一个iframe会解决这个困扰我一周的问题......

Although I have to deal with another problem since the end point jsp is now showing inside the iframe instead of the parent page, at least the progress bar is working across all common browsers, and the redirect issue is another mystery to solve for tomorrow......

虽然我必须处理另一个问题,因为结束点jsp现在显示在iframe而不是父页面中,至少进度条适用于所有常见的浏览器,重定向问题是明天要解决的另一个谜。 ....

Anyway hope anyone encounter this issue can try out this method, wish you good luck.

无论如何希望任何人遇到这个问题都可以尝试这种方法,祝你好运。