From dc690653da22343aeb5ea47cea52f5a71d900a06 Mon Sep 17 00:00:00 2001 From: Gregory Terzian Date: Fri, 5 Jun 2020 15:08:57 +0800 Subject: [PATCH 1/2] update XHR send to use XMLHttpRequestBodyInit --- .../script/dom/webidls/XMLHttpRequest.webidl | 7 +++- components/script/dom/xmlhttprequest.rs | 40 +++++-------------- 2 files changed, 16 insertions(+), 31 deletions(-) diff --git a/components/script/dom/webidls/XMLHttpRequest.webidl b/components/script/dom/webidls/XMLHttpRequest.webidl index 097b4f7177c..2c043b9407a 100644 --- a/components/script/dom/webidls/XMLHttpRequest.webidl +++ b/components/script/dom/webidls/XMLHttpRequest.webidl @@ -12,8 +12,11 @@ * http://www.openwebfoundation.org/legal/the-owf-1-0-agreements/owfa-1-0. */ +// https://fetch.spec.whatwg.org/#typedefdef-xmlhttprequestbodyinit +typedef (Blob or BufferSource or FormData or DOMString or URLSearchParams) XMLHttpRequestBodyInit; + // https://fetch.spec.whatwg.org/#bodyinit -typedef (Blob or BufferSource or FormData or DOMString or URLSearchParams or ReadableStream) BodyInit; +typedef (ReadableStream or XMLHttpRequestBodyInit) BodyInit; enum XMLHttpRequestResponseType { "", @@ -54,7 +57,7 @@ interface XMLHttpRequest : XMLHttpRequestEventTarget { attribute boolean withCredentials; readonly attribute XMLHttpRequestUpload upload; [Throws] - void send(optional (Document or BodyInit)? data = null); + void send(optional (Document or XMLHttpRequestBodyInit)? data = null); void abort(); // response diff --git a/components/script/dom/xmlhttprequest.rs b/components/script/dom/xmlhttprequest.rs index 553cfcb40b0..03a5f5c7bff 100644 --- a/components/script/dom/xmlhttprequest.rs +++ b/components/script/dom/xmlhttprequest.rs @@ -8,7 +8,7 @@ use crate::dom::bindings::cell::DomRefCell; use crate::dom::bindings::codegen::Bindings::WindowBinding::WindowMethods; use crate::dom::bindings::codegen::Bindings::XMLHttpRequestBinding::XMLHttpRequestMethods; use crate::dom::bindings::codegen::Bindings::XMLHttpRequestBinding::XMLHttpRequestResponseType; -use crate::dom::bindings::codegen::UnionTypes::DocumentOrBodyInit; +use crate::dom::bindings::codegen::UnionTypes::DocumentOrXMLHttpRequestBodyInit; use crate::dom::bindings::conversions::ToJSValConvertible; use crate::dom::bindings::error::{Error, ErrorResult, Fallible}; use crate::dom::bindings::inheritance::Castable; @@ -547,7 +547,7 @@ impl XMLHttpRequestMethods for XMLHttpRequest { } // https://xhr.spec.whatwg.org/#the-send()-method - fn Send(&self, data: Option) -> ErrorResult { + fn Send(&self, data: Option) -> ErrorResult { // Step 1, 2 if self.ready_state.get() != XMLHttpRequestState::Opened || self.send_flag.get() { return Err(Error::InvalidState); @@ -560,7 +560,7 @@ impl XMLHttpRequestMethods for XMLHttpRequest { }; // Step 4 (first half) let mut extracted_or_serialized = match data { - Some(DocumentOrBodyInit::Document(ref doc)) => { + Some(DocumentOrXMLHttpRequestBodyInit::Document(ref doc)) => { let bytes = Vec::from(serialize_document(&doc)?.as_ref()); let content_type = if doc.is_html_document() { "text/html;charset=UTF-8" @@ -577,7 +577,7 @@ impl XMLHttpRequestMethods for XMLHttpRequest { source: BodySource::Object, }) }, - Some(DocumentOrBodyInit::Blob(ref b)) => { + Some(DocumentOrXMLHttpRequestBodyInit::Blob(ref b)) => { let extracted_body = b.extract(&self.global()).expect("Couldn't extract body."); if !extracted_body.in_memory() && self.sync.get() { warn!("Sync XHR with not in-memory Blob as body not supported"); @@ -586,20 +586,20 @@ impl XMLHttpRequestMethods for XMLHttpRequest { Some(extracted_body) } }, - Some(DocumentOrBodyInit::FormData(ref formdata)) => Some( + Some(DocumentOrXMLHttpRequestBodyInit::FormData(ref formdata)) => Some( formdata .extract(&self.global()) .expect("Couldn't extract body."), ), - Some(DocumentOrBodyInit::String(ref str)) => { + Some(DocumentOrXMLHttpRequestBodyInit::String(ref str)) => { Some(str.extract(&self.global()).expect("Couldn't extract body.")) }, - Some(DocumentOrBodyInit::URLSearchParams(ref urlsp)) => Some( + Some(DocumentOrXMLHttpRequestBodyInit::URLSearchParams(ref urlsp)) => Some( urlsp .extract(&self.global()) .expect("Couldn't extract body."), ), - Some(DocumentOrBodyInit::ArrayBuffer(ref typedarray)) => { + Some(DocumentOrXMLHttpRequestBodyInit::ArrayBuffer(ref typedarray)) => { let bytes = typedarray.to_vec(); let total_bytes = bytes.len(); let global = self.global(); @@ -611,7 +611,7 @@ impl XMLHttpRequestMethods for XMLHttpRequest { source: BodySource::Object, }) }, - Some(DocumentOrBodyInit::ArrayBufferView(ref typedarray)) => { + Some(DocumentOrXMLHttpRequestBodyInit::ArrayBufferView(ref typedarray)) => { let bytes = typedarray.to_vec(); let total_bytes = bytes.len(); let global = self.global(); @@ -623,25 +623,6 @@ impl XMLHttpRequestMethods for XMLHttpRequest { source: BodySource::Object, }) }, - Some(DocumentOrBodyInit::ReadableStream(ref stream)) => { - if self.sync.get() { - warn!("Sync XHR with ReadableStream as body not supported"); - None - } else { - if stream.is_locked() || stream.is_disturbed() { - return Err(Error::Type( - "The body's stream is disturbed or locked".to_string(), - )); - } - - Some(ExtractedBody { - stream: stream.clone(), - total_bytes: None, - content_type: None, - source: BodySource::Null, - }) - } - }, None => None, }; @@ -725,7 +706,8 @@ impl XMLHttpRequestMethods for XMLHttpRequest { match content_type { Some(content_type) => { let encoding = match data { - Some(DocumentOrBodyInit::String(_)) | Some(DocumentOrBodyInit::Document(_)) => + Some(DocumentOrXMLHttpRequestBodyInit::String(_)) | + Some(DocumentOrXMLHttpRequestBodyInit::Document(_)) => // XHR spec differs from http, and says UTF-8 should be in capitals, // instead of "utf-8", which is what Hyper defaults to. So not // using content types provided by Hyper. From a97d2e3b9b3f4754f2d36648220bb6bc621fe0e7 Mon Sep 17 00:00:00 2001 From: Gregory Terzian Date: Tue, 9 Jun 2020 13:17:24 +0800 Subject: [PATCH 2/2] xhr: update test-suite to reflect use of XMLHttpRequestBodyInit --- tests/wpt/metadata/MANIFEST.json | 40 +------------------ .../xhr/send-data-es-object.any.js | 1 + .../xhr/send-data-readablestream.any.js | 27 ------------- .../xhr/setrequestheader-content-type.htm | 18 --------- 4 files changed, 3 insertions(+), 83 deletions(-) delete mode 100644 tests/wpt/web-platform-tests/xhr/send-data-readablestream.any.js diff --git a/tests/wpt/metadata/MANIFEST.json b/tests/wpt/metadata/MANIFEST.json index 7b48dd98d38..41b591ff632 100644 --- a/tests/wpt/metadata/MANIFEST.json +++ b/tests/wpt/metadata/MANIFEST.json @@ -527006,7 +527006,7 @@ ] ], "send-data-es-object.any.js": [ - "c6fe5de260c212013052f66636b92fb07aa82373", + "92286bca6dd00b82b78de39fcf7988ba1c424d07", [ "xhr/send-data-es-object.any.html", { @@ -527055,42 +527055,6 @@ } ] ], - "send-data-readablestream.any.js": [ - "c53b1071828f95669d41a967c51bd352b389bebb", - [ - "xhr/send-data-readablestream.any.html", - { - "script_metadata": [ - [ - "global", - "window,dedicatedworker,sharedworker" - ] - ] - } - ], - [ - "xhr/send-data-readablestream.any.sharedworker.html", - { - "script_metadata": [ - [ - "global", - "window,dedicatedworker,sharedworker" - ] - ] - } - ], - [ - "xhr/send-data-readablestream.any.worker.html", - { - "script_metadata": [ - [ - "global", - "window,dedicatedworker,sharedworker" - ] - ] - } - ] - ], "send-data-sharedarraybuffer.any.js": [ "912f622697d538edbbc038f7ec76c2e63ee6ffa0", [ @@ -527442,7 +527406,7 @@ ] ], "setrequestheader-content-type.htm": [ - "8608c5967d6b29ba4f9d09ae7bf395a6b26876c2", + "07238391eb5cc8639edbe996208a18b6d9d26b04", [ null, { diff --git a/tests/wpt/web-platform-tests/xhr/send-data-es-object.any.js b/tests/wpt/web-platform-tests/xhr/send-data-es-object.any.js index c6fe5de260c..92286bca6dd 100644 --- a/tests/wpt/web-platform-tests/xhr/send-data-es-object.any.js +++ b/tests/wpt/web-platform-tests/xhr/send-data-es-object.any.js @@ -27,6 +27,7 @@ function do_test(obj, expected, name) { do_test({}, '[object Object]', 'sending a plain empty object') do_test(Math, '[object Math]', 'sending the ES Math object') do_test(new XMLHttpRequest, '[object XMLHttpRequest]', 'sending a new XHR instance') +do_test(new ReadableStream, '[object ReadableStream]', 'sending a new ReadableStream instance') do_test({toString:function(){}}, 'undefined', 'sending object that stringifies to undefined') do_test({toString:function(){return null}}, 'null', 'sending object that stringifies to null') var ancestor = {toString: function(){ diff --git a/tests/wpt/web-platform-tests/xhr/send-data-readablestream.any.js b/tests/wpt/web-platform-tests/xhr/send-data-readablestream.any.js deleted file mode 100644 index c53b1071828..00000000000 --- a/tests/wpt/web-platform-tests/xhr/send-data-readablestream.any.js +++ /dev/null @@ -1,27 +0,0 @@ -// META: global=window,dedicatedworker,sharedworker - -function assert_xhr(stream) { - const client = new XMLHttpRequest(); - client.open("POST", "..."); - assert_throws_js(TypeError, () => client.send(stream)); -} - -test(() => { - const stream = new ReadableStream(); - stream.getReader(); - assert_xhr(stream); -}, "XMLHttpRequest: send() with a stream on which getReader() is called"); - -test(() => { - const stream = new ReadableStream(); - stream.getReader().read(); - assert_xhr(stream); -}, "XMLHttpRequest: send() with a stream on which read() is called"); - -promise_test(async () => { - const stream = new ReadableStream({ pull: c => c.enqueue(new Uint8Array()) }), - reader = stream.getReader(); - await reader.read(); - reader.releaseLock(); - assert_xhr(stream); -}, "XMLHttpRequest: send() with a stream on which read() and releaseLock() are called"); diff --git a/tests/wpt/web-platform-tests/xhr/setrequestheader-content-type.htm b/tests/wpt/web-platform-tests/xhr/setrequestheader-content-type.htm index 8608c5967d6..07238391eb5 100644 --- a/tests/wpt/web-platform-tests/xhr/setrequestheader-content-type.htm +++ b/tests/wpt/web-platform-tests/xhr/setrequestheader-content-type.htm @@ -215,24 +215,6 @@ // https://fetch.spec.whatwg.org/#bodyinit, so the user's must be changed to match it // as per https://xhr.spec.whatwg.org/#the-send%28%29-method step 4. ) - request( - function _ReadableStream() { return new ReadableStream() }, - {"Content-Type": ""}, - "", - 'ReadableStream request respects setRequestHeader("")' - ) - request( - function _ReadableStream() { return new ReadableStream() }, - {}, - undefined, - "ReadableStream request with under type sends no Content-Type without setRequestHeader() call" - ) - request( - function _ReadableStream() { return new ReadableStream() }, - {"Content-Type": "application/xml;charset=ASCII"}, - "application/xml;charset=ASCII", - "ReadableStream request keeps setRequestHeader() Content-Type and charset" - )