Отправка и получение бинарных данных

Вы читаете английскую версию этой статьи, так как пока нет перевода на данный язык. Помогите нам перевести эту статью!

Получение бинарных данных используя JavaScript arrays 

 

Свойство responseType объекта XMLHttpRequest можно задать для изменения ожидаемого типа ответа с сервера. Возможные значения: пустая строка (по умолчанию), "arraybuffer", "blob", "document", "json" и "text". Свойство response будет содержать тело сущности в соответствии с типом ответа, как ArrayBuffer, Blob, Document, JSON или string. Это значение равно null, если запрос не завершен или не был успешным.

В этом примере изображение считывается как двоичный файл и создается 8-разрядный массив целых чисел без знака из необработанных байтов. Обратите внимание, что это не будет декодировать изображение и читать пиксели. Для этого вам понадобится библиотека декодирования png.

 

var oReq = new XMLHttpRequest();
oReq.open("GET", "/myfile.png", true);
oReq.responseType = "arraybuffer";

oReq.onload = function (oEvent) {
  var arrayBuffer = oReq.response; // Note: not oReq.responseText
  if (arrayBuffer) {
    var byteArray = new Uint8Array(arrayBuffer);
    for (var i = 0; i < byteArray.byteLength; i++) {
      // do something with each byte in the array
    }
  }
};

oReq.send(null);

Альтернатива вышеуказанному методу использует интерфейс Blob для непосредственного построения Blob с данными arraybuffer.

var oReq = new XMLHttpRequest();
oReq.open("GET", "/myfile.png", true);
oReq.responseType = "arraybuffer";

oReq.onload = function(oEvent) {
  var blob = new Blob([oReq.response], {type: "image/png"});
  // ...
};

oReq.send();

Также вы можете прочитать двоичный файл как Blob, установив строку" blob " в свойство responseType.

var oReq = new XMLHttpRequest();
oReq.open("GET", "/myfile.png", true);
oReq.responseType = "blob";

oReq.onload = function(oEvent) {
  var blob = oReq.response;
  // ...
};

oReq.send();

Получение бинарных данных в старых браузерах

Функция load_binary_resource(), показанная ниже, загружает двоичные данные из указанного URL, возвращая их вызывающему объекту.

function load_binary_resource(url) {
  var req = new XMLHttpRequest();
  req.open('GET', url, false);
  //XHR binary charset opt by Marcus Granado 2006 [http://mgran.blogspot.com]
  req.overrideMimeType('text\/plain; charset=x-user-defined');
  req.send(null);
  if (req.status != 200) return '';
  return req.responseText;
}

Магия происходит в строке 5, которая переопределяет тип MIME, заставляя браузер рассматривать его как обычный текст, используя пользовательский набор символов. Это говорит браузеру не анализировать его и пропускать байты через необработанные.

var filestream = load_binary_resource(url);
var abyte = filestream.charCodeAt(x) & 0xff; // throw away high-order byte (f7)

The example above fetches the byte at offset x within the loaded binary data. The valid range for x is from 0 to filestream.length-1.

See downloading binary streams with XMLHttpRequest for a detailed explanation. See also downloading files.

Получение бинарных данных из различных источников

jBinary library for working with binary data in JavaScript allows to load data from any source with automatically detected best supported way on current browser or Node.js:

jBinary.load(url).then(function (binary) {
  // here you can use `binary` instance to parse data  
  // in any format (string, array of bytes, custom structure etc.)
});

Отправка бинарных данных

The send method of the XMLHttpRequest has been extended to enable easy transmission of binary data by accepting an ArrayBuffer, Blob, or File object.

The following example sends creates a text file on-the-fly and uses the POST method to send the "file" to the server. This example uses plain text, but you can imagine the data being a binary file instead.

var oReq = new XMLHttpRequest();
oReq.open("POST", url, true);
oReq.onload = function (oEvent) {
  // Uploaded.
};

var blob = new Blob(['abc123'], {type: 'text/plain'});

oReq.send(blob);

Sending typed arrays as binary data

You can send JavaScript typed arrays as binary data as well.

var myArray = new ArrayBuffer(512);
var longInt8View = new Uint8Array(myArray);

for (var i=0; i< longInt8View.length; i++) {
  longInt8View[i] = i % 255;
}

var xhr = new XMLHttpRequest;
xhr.open("POST", url, false);
xhr.send(myArray);

This is building a 512-byte array of 8-bit integers and sending it; you can use any binary data you'd like, of course.

Note: Support for sending ArrayBuffer objects using XMLHttpRequest was added to Gecko 9.0 (Firefox 9.0 / Thunderbird 9.0 / SeaMonkey 2.6). Add information about other browsers' support here.

Отправка форм и загрузка файлов

Please, read this paragraph.

Firefox-specific examples

This example transmits binary content asynchronously, using the POST method, and Firefox's non-standard sendAsBinary().

var req = new XMLHttpRequest();
req.open("POST", url, true);
// set headers and mime-type appropriately
req.setRequestHeader("Content-Length", 741);
req.sendAsBinary(aBody);

Line 4 sets the Content-Length header to 741, indicating that the data is 741 bytes long.  Obviously you need to change this value based on the actual size of the data being sent.

Line 5 uses the sendAsBinary() method to initiate the request.

Note: This non-standard sendAsBinary method is considered deprecated as of Gecko 31 (Firefox 31 / Thunderbird 31 / SeaMonkey 2.28) and will be removed soon. The standard send(Blob data) method can be used instead as explained above.

You can also send binary content by passing an instance of the nsIFileInputStream to send(). In that case, you don't have to set the Content-Length header yourself, as the information is fetched from the stream automatically:

// Make a stream from a file.
var stream = Components.classes["@mozilla.org/network/file-input-stream;1"]
                       .createInstance(Components.interfaces.nsIFileInputStream);
stream.init(file, 0x04 | 0x08, 0644, 0x04); // file is an nsIFile instance   

// Try to determine the MIME type of the file
var mimeType = "text\/plain";
try {
  var mimeService = Components.classes["@mozilla.org/mime;1"]
          .getService(Components.interfaces.nsIMIMEService);
  mimeType = mimeService.getTypeFromFile(file); // file is an nsIFile instance
}
catch (oEvent) { /* eat it; just use text/plain */ }

// Send    
var req = Components.classes["@mozilla.org/xmlextras/xmlhttprequest;1"]
                    .createInstance(Components.interfaces.nsIXMLHttpRequest);
req.open('PUT', url, false); /* synchronous! */
req.setRequestHeader('Content-Type', mimeType);
req.send(stream);