Skip to content

Commit e447d56

Browse files
author
bors-servo
authored
Auto merge of #13597 - servo:fetch, r=<try>
Provide the fetched data to fetch() consumers.
2 parents 8a3af9d + 7ac1910 commit e447d56

File tree

52 files changed

+76
-87
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

52 files changed

+76
-87
lines changed

components/script/body.rs

Lines changed: 35 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ use std::rc::Rc;
2424
use std::str;
2525
use url::form_urlencoded;
2626

27+
#[derive(Copy, Clone, JSTraceable, HeapSizeOf)]
2728
pub enum BodyType {
2829
Blob,
2930
FormData,
@@ -49,41 +50,50 @@ pub fn consume_body<T: BodyOperations + Reflectable>(object: &T, body_type: Body
4950
"The response's stream is disturbed or locked".to_string()));
5051
}
5152

53+
object.set_body_promise(&promise, body_type);
54+
5255
// Steps 2-4
5356
// TODO: Body does not yet have a stream.
5457

58+
consume_body_with_promise(object, body_type, &promise);
59+
60+
promise
61+
}
62+
63+
// https://fetch.spec.whatwg.org/#concept-body-consume-body
64+
#[allow(unrooted_must_root)]
65+
pub fn consume_body_with_promise<T: BodyOperations + Reflectable>(object: &T,
66+
body_type: BodyType,
67+
promise: &Promise) {
5568
// Step 5
56-
let pkg_data_results = run_package_data_algorithm(object,
57-
object.take_body(),
58-
body_type,
59-
object.get_mime_type());
60-
61-
let cx = promise.global().r().get_cx();
62-
match pkg_data_results {
63-
Ok(results) => {
64-
match results {
65-
FetchedData::Text(s) => promise.resolve_native(cx, &USVString(s)),
66-
FetchedData::Json(j) => promise.resolve_native(cx, &j),
67-
FetchedData::BlobData(b) => promise.resolve_native(cx, &b),
68-
FetchedData::FormData(f) => promise.resolve_native(cx, &f),
69-
};
70-
},
71-
Err(err) => promise.reject_error(cx, err),
69+
if let Some(body) = object.take_body() {
70+
let pkg_data_results = run_package_data_algorithm(object,
71+
body,
72+
body_type,
73+
object.get_mime_type());
74+
75+
let cx = promise.global().r().get_cx();
76+
match pkg_data_results {
77+
Ok(results) => {
78+
match results {
79+
FetchedData::Text(s) => promise.resolve_native(cx, &USVString(s)),
80+
FetchedData::Json(j) => promise.resolve_native(cx, &j),
81+
FetchedData::BlobData(b) => promise.resolve_native(cx, &b),
82+
FetchedData::FormData(f) => promise.resolve_native(cx, &f),
83+
};
84+
},
85+
Err(err) => promise.reject_error(cx, err),
86+
}
7287
}
73-
promise
7488
}
7589

7690
// https://fetch.spec.whatwg.org/#concept-body-package-data
7791
#[allow(unsafe_code)]
7892
fn run_package_data_algorithm<T: BodyOperations + Reflectable>(object: &T,
79-
bytes: Option<Vec<u8>>,
93+
bytes: Vec<u8>,
8094
body_type: BodyType,
8195
mime_type: Ref<Vec<u8>>)
8296
-> Fallible<FetchedData> {
83-
let bytes = match bytes {
84-
Some(b) => b,
85-
_ => vec![],
86-
};
8797
let cx = object.global().r().get_cx();
8898
let mime = &*mime_type;
8999
match body_type {
@@ -156,6 +166,9 @@ fn run_form_data_algorithm(root: GlobalRef, bytes: Vec<u8>, mime: &[u8]) -> Fall
156166

157167
pub trait BodyOperations {
158168
fn get_body_used(&self) -> bool;
169+
fn set_body_promise(&self, p: &Rc<Promise>, body_type: BodyType);
170+
/// Returns `Some(_)` if the body is complete, `None` if there is more to
171+
/// come.
159172
fn take_body(&self) -> Option<Vec<u8>>;
160173
fn is_locked(&self) -> bool;
161174
fn get_mime_type(&self) -> Ref<Vec<u8>>;

components/script/dom/request.rs

Lines changed: 11 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,8 @@ pub struct Request {
4747
body_used: Cell<bool>,
4848
headers: MutNullableHeap<JS<Headers>>,
4949
mime_type: DOMRefCell<Vec<u8>>,
50+
#[ignore_heap_size_of = "Rc"]
51+
body_promise: DOMRefCell<Option<(Rc<Promise>, BodyType)>>,
5052
}
5153

5254
impl Request {
@@ -62,6 +64,7 @@ impl Request {
6264
body_used: Cell::new(false),
6365
headers: Default::default(),
6466
mime_type: DOMRefCell::new("".to_string().into_bytes()),
67+
body_promise: DOMRefCell::new(None),
6568
}
6669
}
6770

@@ -662,20 +665,19 @@ impl BodyOperations for Request {
662665
self.BodyUsed()
663666
}
664667

668+
fn set_body_promise(&self, p: &Rc<Promise>, body_type: BodyType) {
669+
self.body_used.set(true);
670+
assert!(mem::replace(&mut *self.body_promise.borrow_mut(), Some((p.clone(), body_type))).is_none());
671+
}
672+
665673
fn is_locked(&self) -> bool {
666674
self.locked()
667675
}
668676

669677
fn take_body(&self) -> Option<Vec<u8>> {
670-
let ref mut net_traits_req = *self.request.borrow_mut();
671-
let body: Option<Vec<u8>> = mem::replace(&mut *net_traits_req.body.borrow_mut(), None);
672-
match body {
673-
Some(_) => {
674-
self.body_used.set(true);
675-
body
676-
},
677-
_ => None,
678-
}
678+
let request = self.request.borrow_mut();
679+
let body = request.body.borrow_mut().take();
680+
Some(body.unwrap_or(vec![]))
679681
}
680682

681683
fn get_mime_type(&self) -> Ref<Vec<u8>> {

components/script/dom/response.rs

Lines changed: 23 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
* License, v. 2.0. If a copy of the MPL was not distributed with this
33
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
44

5-
use body::{BodyOperations, BodyType, consume_body};
5+
use body::{BodyOperations, BodyType, consume_body, consume_body_with_promise};
66
use core::cell::Cell;
77
use dom::bindings::cell::DOMRefCell;
88
use dom::bindings::codegen::Bindings::HeadersBinding::HeadersMethods;
@@ -44,6 +44,8 @@ pub struct Response {
4444
url_list: DOMRefCell<Vec<Url>>,
4545
// For now use the existing NetTraitsResponseBody enum
4646
body: DOMRefCell<NetTraitsResponseBody>,
47+
#[ignore_heap_size_of = "Rc"]
48+
body_promise: DOMRefCell<Option<(Rc<Promise>, BodyType)>>,
4749
}
4850

4951
impl Response {
@@ -59,6 +61,7 @@ impl Response {
5961
url: DOMRefCell::new(None),
6062
url_list: DOMRefCell::new(vec![]),
6163
body: DOMRefCell::new(NetTraitsResponseBody::Empty),
64+
body_promise: DOMRefCell::new(None),
6265
}
6366
}
6467

@@ -194,18 +197,25 @@ impl BodyOperations for Response {
194197
self.BodyUsed()
195198
}
196199

200+
fn set_body_promise(&self, p: &Rc<Promise>, body_type: BodyType) {
201+
self.body_used.set(true);
202+
assert!(mem::replace(&mut *self.body_promise.borrow_mut(), Some((p.clone(), body_type))).is_none());
203+
}
204+
197205
fn is_locked(&self) -> bool {
198206
self.locked()
199207
}
200208

201209
fn take_body(&self) -> Option<Vec<u8>> {
202-
let body: NetTraitsResponseBody = mem::replace(&mut *self.body.borrow_mut(), NetTraitsResponseBody::Empty);
210+
let body = mem::replace(&mut *self.body.borrow_mut(), NetTraitsResponseBody::Empty);
203211
match body {
204-
NetTraitsResponseBody::Done(bytes) | NetTraitsResponseBody::Receiving(bytes) => {
205-
self.body_used.set(true);
212+
NetTraitsResponseBody::Done(bytes) => {
206213
Some(bytes)
207214
},
208-
_ => None,
215+
body => {
216+
mem::replace(&mut *self.body.borrow_mut(), body);
217+
None
218+
},
209219
}
210220
}
211221

@@ -366,4 +376,12 @@ impl Response {
366376
pub fn set_final_url(&self, final_url: Url) {
367377
*self.url.borrow_mut() = Some(final_url);
368378
}
379+
380+
#[allow(unrooted_must_root)]
381+
pub fn finish(&self, body: Vec<u8>) {
382+
*self.body.borrow_mut() = NetTraitsResponseBody::Done(body);
383+
if let Some((p, body_type)) = self.body_promise.borrow_mut().take() {
384+
consume_body_with_promise(self, body_type, &p);
385+
}
386+
}
369387
}

components/script/fetch.rs

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -24,13 +24,15 @@ use net_traits::CoreResourceMsg::Fetch as NetTraitsFetch;
2424
use net_traits::request::Request as NetTraitsRequest;
2525
use net_traits::request::RequestInit as NetTraitsRequestInit;
2626
use network_listener::{NetworkListener, PreInvoke};
27+
use std::mem;
2728
use std::rc::Rc;
2829
use std::sync::{Arc, Mutex};
2930
use url::Url;
3031

3132
struct FetchContext {
3233
fetch_promise: Option<TrustedPromise>,
3334
response_object: Trusted<Response>,
35+
body: Vec<u8>,
3436
}
3537

3638
fn from_referrer_to_referrer_url(request: &NetTraitsRequest) -> Option<Url> {
@@ -89,6 +91,7 @@ pub fn Fetch(global: GlobalRef, input: RequestOrUSVString, init: &RequestInit) -
8991
let fetch_context = Arc::new(Mutex::new(FetchContext {
9092
fetch_promise: Some(TrustedPromise::new(promise.clone())),
9193
response_object: Trusted::new(&*response),
94+
body: vec![],
9295
}));
9396
let listener = NetworkListener {
9497
context: fetch_context,
@@ -153,12 +156,13 @@ impl FetchResponseListener for FetchContext {
153156
self.fetch_promise = Some(TrustedPromise::new(promise));
154157
}
155158

156-
fn process_response_chunk(&mut self, _chunk: Vec<u8>) {
157-
// TODO when body is implemented
158-
// ... this will append the chunk to Response's body.
159+
fn process_response_chunk(&mut self, mut chunk: Vec<u8>) {
160+
self.body.append(&mut chunk);
159161
}
160162

161163
fn process_response_eof(&mut self, _response: Result<(), NetworkError>) {
164+
let response = self.response_object.root();
165+
response.finish(mem::replace(&mut self.body, vec![]));
162166
// TODO
163167
// ... trailerObject is not supported in Servo yet.
164168
}

tests/wpt/metadata/referrer-policy/no-referrer-when-downgrade/http-rp/cross-origin/http-http/fetch-request/__dir__.ini

Lines changed: 0 additions & 1 deletion
This file was deleted.

tests/wpt/metadata/referrer-policy/no-referrer-when-downgrade/http-rp/cross-origin/http-https/fetch-request/__dir__.ini

Lines changed: 0 additions & 1 deletion
This file was deleted.

tests/wpt/metadata/referrer-policy/no-referrer-when-downgrade/http-rp/same-origin/http-http/fetch-request/__dir__.ini

Lines changed: 0 additions & 1 deletion
This file was deleted.

tests/wpt/metadata/referrer-policy/no-referrer-when-downgrade/http-rp/same-origin/http-https/fetch-request/__dir__.ini

Lines changed: 0 additions & 1 deletion
This file was deleted.

tests/wpt/metadata/referrer-policy/no-referrer/http-rp/cross-origin/http-http/fetch-request/__dir__.ini

Lines changed: 0 additions & 1 deletion
This file was deleted.

tests/wpt/metadata/referrer-policy/no-referrer/http-rp/cross-origin/http-https/fetch-request/__dir__.ini

Lines changed: 0 additions & 1 deletion
This file was deleted.

0 commit comments

Comments
 (0)