【问题标题】:Sending a blob to a servlet through ajax通过 ajax 将 blob 发送到 servlet
【发布时间】:2013-02-09 23:45:06
【问题描述】:

编辑:整个问题原来是网络问题,但如果您看到任何关于如何优化流程的想法,我仍然会很感激。

我对 Servlet 还很陌生,在我的旅程中不久,我遇到了一个与性能有关的问题。我正在尝试通过 Google Chrome 浏览器中的 XHR 对象发送视频文件。视频文件存储在 Blob 对象中。我在我的 JavaScript 脚本中使用了这个函数:

function upload(blob) {
  var xhr = new XMLHttpRequest();
  xhr.open('POST', '/Test/Odbieracz', true);
  xhr.onload = function(e) { console.log("loaded"); };
  xhr.onreadystatechange = function(){
      console.log("state: " + xhr.readyState);
  };
  // Listen to the upload progress.
  xhr.upload.onprogress = function(e) { console.log("uploading..."); };
  xhr.setRequestHeader("Content-Type", "video/webm");
  xhr.send(blob);
}

效果很好,因为 Blob 到达了我使用这段代码处理它的 Servlet:

byte[] buffer = new byte[16 * 1024];

InputStream input = request.getInputStream();       
OutputStream output = new FileOutputStream("costam0.webm");
int bytesRead;
while ((bytesRead = input.read(buffer)) != -1){
    System.out.println(bytesRead);
    output.write(buffer, 0, bytesRead);
}
output.close();
input.close();

它也会保存文件。

我确实遇到的问题是它非常非常慢,根据我的计算它可以处理大约 42kB/s,这对于与视频文件有关的 Web 服务来说非常慢。我已经在这里坐了好几个小时,试图找到一种方法来加速它,或者至少找到瓶颈,但不幸的是我不知道它可能在哪里。

我怀疑是浏览器导致了延迟,我在我的 Servlet 中使用了不同的 InputStream 导致了一个本地文件(我试图通过 XHR 上传的同一个文件)并且它在处理它时完全没有问题,不到一秒钟。服务器位于我的本地主机上,所以我认为网络一点也不落后。

如果有人之前遇到过这个问题,我会很感激任何指点。

【问题讨论】:

    标签: java ajax jakarta-ee servlets xmlhttprequest


    【解决方案1】:

    一些想法:

    增加缓冲区大小:也许:

    byte[] buffer = new byte[1024 * 1024];
    

    不要经常写输出文件。 Java 必须在缓冲区的其余部分等待时执行昂贵的 I/O 操作。权衡是,如果您正在处理小文件,您将浪费一些内存。

    使用BufferedOutputStream: 原因同上。强烈建议在编写非常大的文件时使用 BufferedOutputStream。您甚至不必担心在每个循环期间进行编写。只需在循环完成后调用 buffOut.flush() 进行一次写入。示例:

    BufferedOutputStream buffOut = new BufferedOutputStream(new FileOutputStream("costam0.webm"));       
    int bytesRead;
    while ((bytesRead = input.read(buffer)) != -1){
        System.out.println(bytesRead);
        output.write(buffer, 0, bytesRead);
    }
    buffOUt.flush()
    

    您是否在调用 println 时计算了这些计算?不要那样做。您确认该过程有效,只是速度很慢。无需每次都调用 println。

    另外,你是如何“计算”速度的?

    【讨论】:

    • 非常感谢您的回复,但毕竟是网络问题 - 我已经重新启动了调制解调器,一切都很好。我会使用你的提示来提高效率。我计算速度的方法是使用请求开始和结束时的时间戳,我基本上将文件大小除以经过的秒数。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-08-21
    • 2014-09-15
    • 2013-08-10
    • 2015-10-09
    • 2019-05-02
    • 2017-01-26
    • 1970-01-01
    相关资源
    最近更新 更多