当我尝试上传一个大文件时,Chrome扩展崩溃 [英] chrome extension crashes when i try to upload a big file

查看:432
本文介绍了当我尝试上传一个大文件时,Chrome扩展崩溃的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

该扩展在执行此类代码时崩溃:

  / *此对象在内容脚本中创建并传递给后台脚本* / 
var myurl = URL.createObjectURL(document.getElementById('myfile')。files [0]);

/ *来自后台脚本的代码块,如果文件大小为<< 50MB,如果更大,则扩展会崩溃* /
var x = new XMLHttpRequest();
x.onload = function(){
var uploadfile = new Uint8Array(x.response);


var somearray1 = [...];
var somearray2 = [...];

var size = somearray1.length + uploadfile.length + somearray2.length;

var u8array = new Uint8Array(size);
var i = 0; (i = 0; i u8array [i] = somearray1.charCodeAt(i)& 0xFF的;


for(var j = 0; j< uploadfile.length; i ++,j ++)
u8array [i] = ufile [j]; (i = 0; i u8array [i] = somearray2.charCodeAt(i)& 0xFF的;


var req = new XMLHttpRequest();

req.open(POST,Url);
req.setRequestHeader(Content-Type,'multipart / form-data; boundary = --_ BOUNDARY_');
req.send(u8array);

};
x.open('GET',myurl);
x.responseType ='arraybuffer';
x.send();

我想上传一个200MB大小的文件,并且崩溃了扩展名。
请帮我理解一些示例代码,如果它错了,我现在正在做的方式是如何正确上传它的。

解决方案

您的扩展程序崩溃是因为您的上传数据效率低下,导致内存不足。



您不应该将文件加载到内存中,而是传递文件对象为XMLHttpRequest,以便Chrome可以以上载表单的形式传输文件内容。这可以通过 FormData 对象。

最简单的方法是将表单上载到内容脚本中而不是背景页面上,因为它不是轻松地将 File 传递到后台。

  //在a内容脚本:
var myfile = document.getElementById('myfile')。files [0];
var form = new FormData();
form.append('myfile',myfile);
//使用form.append(... key ...,... value ...)添加更多键值对;

//上传
var x = new XMLHttpRequest();
x.open('POST','http://example.com/');
x.send(form);

这是通过XMLHttpRequest流式处理文件所需的全部内容。将使用multipart / form-data算法对 FormData 对象进行序列化和上传。有关更多详细信息,请参阅 http://www.w3.org/TR/ XMLHttpRequest2 /#the-send-method



如果您不想在内容脚本中上传(因为您希望上传在页面关闭,那么你必须通过Shared Worker(作为蹦床)将 File 对象传递给后台页面。如果你想了解更多关于这个选项的信息,请阅读 chrome.runtime是否支持发布消息可转让的物品?


The extension crashes when it executes such code:

/*this object is created in content script and passed t background script*/
var myurl = URL.createObjectURL(document.getElementById('myfile').files[0]);

/*code block from background script, it work good if file size is < 50MB, if bigger then extension will crash*/
var x = new XMLHttpRequest();
x.onload = function() {
       var uploadfile = new Uint8Array(x.response);


        var somearray1 = [...];
        var somearray2 = [...];

        var size = somearray1.length + uploadfile.length + somearray2.length;

        var u8array = new Uint8Array(size);
        var i = 0;

         for (i = 0; i < somearray1.length; i++) 
         u8array[i] = somearray1.charCodeAt(i) & 0xff;


        for (var j = 0; j < uploadfile.length; i++, j++) 
        u8array[i] = ufile[j];

        for (i = 0; i < somearray2.length; i++) 
         u8array[i] = somearray2.charCodeAt(i) & 0xff;


        var req = new XMLHttpRequest();

        req.open("POST", Url);
        req.setRequestHeader("Content-Type",  'multipart/form-data; boundary=--_BOUNDARY_');
        req.send(u8array);

  };
x.open('GET', myurl); 
x.responseType = 'arraybuffer';
x.send();

I want to upload a file of 200MB size, and it crashes the extension. Please help me understand with some sample code how to upload it correctly if it is wrong the way i'm doing now.

解决方案

Your extension crashes because it runs out of memory due to your inefficient way of uploading data.

You should not load the file in memory, but pass the file object to XMLHttpRequest so that Chrome can stream the file contents in the upload form. This can be done with the FormData object.

The easiest way of doing this is to upload the form in a content script instead of a background page, because it is not easy to pass a File to the background.

// In a content script:
var myfile = document.getElementById('myfile').files[0];
var form = new FormData();
form.append('myfile', myfile);
// Add more key-value pairs using form.append(...key..., ...value...);

// Upload
var x = new XMLHttpRequest();
x.open('POST', 'http://example.com/');
x.send(form);

This is all it takes to stream files through XMLHttpRequest. The FormData object will be serialized and uploaded using the multipart/form-data algorithm. For more details, see http://www.w3.org/TR/XMLHttpRequest2/#the-send-method.

If you don't want to upload in a content script (because you want the upload to continue even after the page closes, then you have to pass the File object to the background page via a Shared Worker (that acts as a trampoline). If you want to learn more about this option, read Does chrome.runtime support posting messages with transferable objects?.

这篇关于当我尝试上传一个大文件时,Chrome扩展崩溃的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆