mirror of
https://github.com/zhigang1992/react-native.git
synced 2026-04-24 04:16:00 +08:00
XHR: support typed arrays for request payloads
Summary: Support `xhr.send(data)` for typed arrays. **Test plan:** run UIExplorer example on iOS and Android. Closes https://github.com/facebook/react-native/pull/11904 Differential Revision: D4425551 fbshipit-source-id: 065ab5873407a406ca4a831068ab138606c3361b
This commit is contained in:
committed by
Facebook Github Bot
parent
116916b98d
commit
16bb6e87ba
@@ -16,9 +16,14 @@
|
||||
const FormData = require('FormData');
|
||||
const NativeEventEmitter = require('NativeEventEmitter');
|
||||
const RCTNetworkingNative = require('NativeModules').Networking;
|
||||
const convertRequestBody = require('convertRequestBody');
|
||||
|
||||
import type {RequestBody} from 'convertRequestBody';
|
||||
|
||||
type Header = [string, string];
|
||||
|
||||
// Convert FormData headers to arrays, which are easier to consume in
|
||||
// native on Android.
|
||||
function convertHeadersMapToArray(headers: Object): Array<Header> {
|
||||
const headerArray = [];
|
||||
for (const name in headers) {
|
||||
@@ -47,16 +52,19 @@ class RCTNetworking extends NativeEventEmitter {
|
||||
trackingName: string,
|
||||
url: string,
|
||||
headers: Object,
|
||||
data: string | FormData | {uri: string},
|
||||
data: RequestBody,
|
||||
responseType: 'text' | 'base64',
|
||||
incrementalUpdates: boolean,
|
||||
timeout: number,
|
||||
callback: (requestId: number) => any
|
||||
) {
|
||||
const body =
|
||||
typeof data === 'string' ? {string: data} :
|
||||
data instanceof FormData ? {formData: getParts(data)} :
|
||||
data;
|
||||
const body = convertRequestBody(data);
|
||||
if (body && body.formData) {
|
||||
body.formData = body.formData.map((part) => ({
|
||||
...part,
|
||||
headers: convertHeadersMapToArray(part.headers),
|
||||
}));
|
||||
}
|
||||
const requestId = generateRequestId();
|
||||
RCTNetworkingNative.sendRequest(
|
||||
method,
|
||||
@@ -80,11 +88,4 @@ class RCTNetworking extends NativeEventEmitter {
|
||||
}
|
||||
}
|
||||
|
||||
function getParts(data) {
|
||||
return data.getParts().map((part) => {
|
||||
part.headers = convertHeadersMapToArray(part.headers);
|
||||
return part;
|
||||
});
|
||||
}
|
||||
|
||||
module.exports = new RCTNetworking();
|
||||
|
||||
@@ -14,6 +14,9 @@
|
||||
const FormData = require('FormData');
|
||||
const NativeEventEmitter = require('NativeEventEmitter');
|
||||
const RCTNetworkingNative = require('NativeModules').Networking;
|
||||
const convertRequestBody = require('convertRequestBody');
|
||||
|
||||
import type {RequestBody} from 'convertRequestBody';
|
||||
|
||||
class RCTNetworking extends NativeEventEmitter {
|
||||
|
||||
@@ -26,16 +29,13 @@ class RCTNetworking extends NativeEventEmitter {
|
||||
trackingName: string,
|
||||
url: string,
|
||||
headers: Object,
|
||||
data: string | FormData | {uri: string},
|
||||
data: RequestBody,
|
||||
responseType: 'text' | 'base64',
|
||||
incrementalUpdates: boolean,
|
||||
timeout: number,
|
||||
callback: (requestId: number) => any
|
||||
) {
|
||||
const body =
|
||||
typeof data === 'string' ? {string: data} :
|
||||
data instanceof FormData ? {formData: data.getParts()} :
|
||||
data;
|
||||
const body = convertRequestBody(data);
|
||||
RCTNetworkingNative.sendRequest({
|
||||
method,
|
||||
url,
|
||||
|
||||
@@ -303,6 +303,11 @@ RCT_EXPORT_MODULE()
|
||||
if (body) {
|
||||
return callback(nil, @{@"body": body});
|
||||
}
|
||||
NSString *base64String = [RCTConvert NSString:query[@"base64"]];
|
||||
if (base64String) {
|
||||
NSData *data = [[NSData alloc] initWithBase64EncodedString:base64String options:0];
|
||||
return callback(nil, @{@"body": data});
|
||||
}
|
||||
NSURLRequest *request = [RCTConvert NSURLRequest:query[@"uri"]];
|
||||
if (request) {
|
||||
|
||||
|
||||
40
Libraries/Network/convertRequestBody.js
Normal file
40
Libraries/Network/convertRequestBody.js
Normal file
@@ -0,0 +1,40 @@
|
||||
/**
|
||||
* Copyright (c) 2015-present, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
* @providesModule convertRequestBody
|
||||
* @flow
|
||||
*/
|
||||
'use strict';
|
||||
|
||||
const binaryToBase64 = require('binaryToBase64');
|
||||
|
||||
const FormData = require('FormData');
|
||||
|
||||
export type RequestBody =
|
||||
string
|
||||
| FormData
|
||||
| {uri: string}
|
||||
| ArrayBuffer
|
||||
| $ArrayBufferView
|
||||
;
|
||||
|
||||
function convertRequestBody(body: RequestBody): Object {
|
||||
if (typeof body === 'string') {
|
||||
return {string: body};
|
||||
}
|
||||
if (body instanceof FormData) {
|
||||
return {formData: body.getParts()};
|
||||
}
|
||||
if (body instanceof ArrayBuffer || ArrayBuffer.isView(body)) {
|
||||
// $FlowFixMe: no way to assert that 'body' is indeed an ArrayBufferView
|
||||
return {base64: binaryToBase64(body)};
|
||||
}
|
||||
return body;
|
||||
}
|
||||
|
||||
module.exports = convertRequestBody;
|
||||
Reference in New Issue
Block a user