使用jquery ajax下载二进制文件

我试图使用jquery ajax下载二进制音频文件。

通常我会发出这样的命令:

windows.location.href = 'http://marksdomain(dot)com/audioFile.wav' ; 

但是,最近我们的服务器等待响应的时间太长了,而且我得到了一个令人讨厌的网关超时消息。

有人建议我使用jquery-ajax,这是有道理的,因为那时我会更多地控制超时。

这是我到目前为止玩过的代码:

 $.ajax( { url: 'http://marksdomain(dot)com/audioFile.wav' , timeout: 999999 , dataType: 'binary' , processData: false // this one does not seem to do anything ? , success: function(result) { console.log(result.length); } , error: function(result, errStatus, errorMessage){ console.log(errStatus + ' -- ' + errorMessage); } 

当我省略“dataType”时,二进制文件的大小比服务器上实际大三倍。 但是,当我使dataType等于“binary”时,ajax会抛出一个错误:

 "No conversion from text to binary" 

从一些早期的post中,听起来好像jquery-ajax不能以这种方式处理二进制文件。

我确实发现了Delivery.js ,它实际上对我正在尝试的东西非常有效,但我宁愿不使用节点解决方案。

有什么建议?

只需直接使用XHR即可。 此示例取自MDN :

 var oReq = new XMLHttpRequest(); oReq.open("GET", "/myfile.png", true); oReq.responseType = "arraybuffer"; oReq.onload = function(oEvent) { var arrayBuffer = oReq.response; // if you want to access the bytes: var byteArray = new Uint8Array(arrayBuffer); // ... // If you want to use the image in your DOM: var blob = new Blob(arrayBuffer, {type: "image/png"}); var url = URL.createObjectURL(blob); someImageElement.src = url; // whatever... }; oReq.send(); 

如果必须使用jQuery,可以使用$.ajaxSetup()来修改低级设置。

例:

  // Set up AJAX settings for binary files: $.ajaxSetup({ beforeSend: function (jqXHR, settings) { if (settings.dataType === 'binary') { settings.xhr().responseType = 'arraybuffer'; } } }) // Make the actual call: let result = await $.ajax({ url: '/api/export/data', type: 'GET', contentType: 'application/json', dataType: 'binary', processData: false, headers: { token: localStorage.token, }, }); 

您可以设置$ .ajax传输来修改设置,如下所述: http : //www.henryalgus.com/reading-binary-files-using-jquery-ajax/

 // use this transport for "binary" data type $.ajaxTransport("+binary", function (options, originalOptions, jqXHR) { // check for conditions and support for blob / arraybuffer response type if (window.FormData && ((options.dataType && (options.dataType == 'binary')) || (options.data && ((window.ArrayBuffer && options.data instanceof ArrayBuffer) || (window.Blob && options.data instanceof Blob))))) { return { // create new XMLHttpRequest send: function (headers, callback) { // setup all variables var xhr = new XMLHttpRequest(), url = options.url, type = options.type, async = options.async || true, // blob or arraybuffer. Default is blob dataType = options.responseType || "blob", data = options.data || null, username = options.username || null, password = options.password || null; xhr.addEventListener('load', function () { var data = {}; data[options.dataType] = xhr.response; // make callback and send data callback(xhr.status, xhr.statusText, data, xhr.getAllResponseHeaders()); }); xhr.open(type, url, async, username, password); // setup custom headers for (var i in headers) { xhr.setRequestHeader(i, headers[i]); } xhr.responseType = dataType; xhr.send(data); }, abort: function () { jqXHR.abort(); } }; } }); 

然后进行你的ajax调用:

  return $.ajax({ url: url, method: 'GET', dataType: 'binary', processData: 'false', responseType: 'arraybuffer', headers: { 'X-Requested-With': 'XMLHttpRequest' } }).then(function (response) { var data = new Uint8Array(response); //do something with the data return data; }, function (error) { alertify.error('There was an error! Error:' + error.name + ':' + error.status) });