Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(732)

Side by Side Diff: Source/modules/fetch/Body.cpp

Issue 1173173006: [2c] Replace Body::readAsyncFromBlob with readAsyncFromFetchDataConsumerHandle (Closed) Base URL: https://chromium.googlesource.com/chromium/blink.git@master
Patch Set: Rebase Body::didFetchDataLoadFailed() change. Created 5 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « Source/modules/fetch/Body.h ('k') | Source/modules/serviceworkers/RespondWithObserver.cpp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "config.h" 5 #include "config.h"
6 #include "modules/fetch/Body.h" 6 #include "modules/fetch/Body.h"
7 7
8 #include "bindings/core/v8/ExceptionState.h" 8 #include "bindings/core/v8/ExceptionState.h"
9 #include "bindings/core/v8/ScriptPromiseResolver.h" 9 #include "bindings/core/v8/ScriptPromiseResolver.h"
10 #include "bindings/core/v8/ScriptState.h" 10 #include "bindings/core/v8/ScriptState.h"
11 #include "bindings/core/v8/V8ArrayBuffer.h" 11 #include "bindings/core/v8/V8ArrayBuffer.h"
12 #include "bindings/core/v8/V8ThrowException.h" 12 #include "bindings/core/v8/V8ThrowException.h"
13 #include "core/dom/DOMArrayBuffer.h" 13 #include "core/dom/DOMArrayBuffer.h"
14 #include "core/dom/DOMTypedArray.h" 14 #include "core/dom/DOMTypedArray.h"
15 #include "core/fileapi/Blob.h" 15 #include "core/fileapi/Blob.h"
16 #include "core/fileapi/FileReaderLoader.h" 16 #include "core/fileapi/FileReaderLoader.h"
17 #include "core/fileapi/FileReaderLoaderClient.h" 17 #include "core/fileapi/FileReaderLoaderClient.h"
18 #include "core/frame/UseCounter.h" 18 #include "core/frame/UseCounter.h"
19 #include "core/streams/ReadableByteStream.h" 19 #include "core/streams/ReadableByteStream.h"
20 #include "core/streams/ReadableByteStreamReader.h" 20 #include "core/streams/ReadableByteStreamReader.h"
21 #include "core/streams/UnderlyingSource.h" 21 #include "core/streams/UnderlyingSource.h"
22 #include "modules/fetch/BodyStreamBuffer.h" 22 #include "modules/fetch/BodyStreamBuffer.h"
23 #include "modules/fetch/DataConsumerHandleUtil.h"
24 #include "modules/fetch/FetchBlobDataConsumerHandle.h"
23 25
24 namespace blink { 26 namespace blink {
25 27
26 class Body::BlobHandleReceiver final : public BodyStreamBuffer::BlobHandleCreato rClient { 28 class Body::BlobHandleReceiver final : public BodyStreamBuffer::BlobHandleCreato rClient {
27 public: 29 public:
28 explicit BlobHandleReceiver(Body* body) 30 explicit BlobHandleReceiver(Body* body)
29 : m_body(body) 31 : m_body(body)
30 { 32 {
31 } 33 }
32 void didCreateBlobHandle(PassRefPtr<BlobDataHandle> handle) override 34 void didCreateBlobHandle(PassRefPtr<BlobDataHandle> handle) override
(...skipping 309 matching lines...) Expand 10 before | Expand all | Expand 10 after
342 } else if (isBodyConsumed()) { 344 } else if (isBodyConsumed()) {
343 m_streamSource->createDrainingStream()->readAllAndCreateBlobHandle(mimeT ype(), new BlobHandleReceiver(this)); 345 m_streamSource->createDrainingStream()->readAllAndCreateBlobHandle(mimeT ype(), new BlobHandleReceiver(this));
344 } else if (buffer()) { 346 } else if (buffer()) {
345 buffer()->readAllAndCreateBlobHandle(mimeType(), new BlobHandleReceiver( this)); 347 buffer()->readAllAndCreateBlobHandle(mimeType(), new BlobHandleReceiver( this));
346 } else { 348 } else {
347 readAsyncFromBlob(blobDataHandle()); 349 readAsyncFromBlob(blobDataHandle());
348 } 350 }
349 return promise; 351 return promise;
350 } 352 }
351 353
352 void Body::readAsyncFromBlob(PassRefPtr<BlobDataHandle> handle) 354 void Body::readAsyncFromFetchDataConsumerHandle(FetchDataConsumerHandle* handle, const String& mimeType)
353 { 355 {
354 FileReaderLoader::ReadType readType = FileReaderLoader::ReadAsText; 356 ASSERT(!m_fetchDataLoader);
355 RefPtr<BlobDataHandle> blobHandle = handle; 357
356 if (!blobHandle)
357 blobHandle = BlobDataHandle::create(BlobData::create(), 0);
358 switch (m_responseType) { 358 switch (m_responseType) {
359 case ResponseAsArrayBuffer: 359 case ResponseAsArrayBuffer:
360 readType = FileReaderLoader::ReadAsArrayBuffer; 360 m_fetchDataLoader = FetchDataLoader::createLoaderAsArrayBuffer();
361 break; 361 break;
362
363 case ResponseAsJSON:
364 case ResponseAsText:
365 m_fetchDataLoader = FetchDataLoader::createLoaderAsString();
366 break;
367
362 case ResponseAsBlob: 368 case ResponseAsBlob:
363 if (blobHandle->size() != kuint64max) { 369 m_fetchDataLoader = FetchDataLoader::createLoaderAsBlobHandle(mimeType);
364 // If the size of |blobHandle| is set correctly, creates Blob from
365 // it.
366 if (blobHandle->type() != mimeType()) {
367 // A new BlobDataHandle is created to override the Blob's type.
368 m_resolver->resolve(Blob::create(BlobDataHandle::create(blobHand le->uuid(), mimeType(), blobHandle->size())));
369 } else {
370 m_resolver->resolve(Blob::create(blobHandle));
371 }
372 m_stream->close();
373 m_resolver.clear();
374 return;
375 }
376 // If the size is not set, read as ArrayBuffer and create a new blob to
377 // get the size.
378 // FIXME: This workaround is not good for performance.
379 // When we will stop using Blob as a base system of Body to support
380 // stream, this problem should be solved.
381 readType = FileReaderLoader::ReadAsArrayBuffer;
382 break; 370 break;
371
383 case ResponseAsFormData: 372 case ResponseAsFormData:
384 // FIXME: Implement this. 373 // FIXME: Implement this.
385 ASSERT_NOT_REACHED(); 374 ASSERT_NOT_REACHED();
386 break; 375 return;
387 case ResponseAsJSON: 376
388 case ResponseAsText:
389 break;
390 default: 377 default:
391 ASSERT_NOT_REACHED(); 378 ASSERT_NOT_REACHED();
379 return;
392 } 380 }
393 381
394 m_loader = adoptPtr(new FileReaderLoader(readType, this)); 382 if (handle)
395 m_loader->start(m_resolver->scriptState()->executionContext(), blobHandle); 383 m_fetchDataLoader->start(handle, this);
384 else
385 m_fetchDataLoader->start(createFetchDataConsumerHandleFromWebHandle(crea teDoneDataConsumerHandle()).get(), this);
yhirano 2015/06/25 04:37:08 |handle| will never be null.
hiroshige 2015/06/25 05:39:17 Done.
386 }
396 387
397 return; 388
389 void Body::readAsyncFromBlob(PassRefPtr<BlobDataHandle> handle)
390 {
391 readAsyncFromFetchDataConsumerHandle(FetchBlobDataConsumerHandle::create(exe cutionContext(), handle).get(), mimeType());
398 } 392 }
399 393
400 ScriptPromise Body::arrayBuffer(ScriptState* scriptState) 394 ScriptPromise Body::arrayBuffer(ScriptState* scriptState)
401 { 395 {
402 return readAsync(scriptState, ResponseAsArrayBuffer); 396 return readAsync(scriptState, ResponseAsArrayBuffer);
403 } 397 }
404 398
405 ScriptPromise Body::blob(ScriptState* scriptState) 399 ScriptPromise Body::blob(ScriptState* scriptState)
406 { 400 {
407 return readAsync(scriptState, ResponseAsBlob); 401 return readAsync(scriptState, ResponseAsBlob);
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after
469 m_streamSource->startStream(m_stream); 463 m_streamSource->startStream(m_stream);
470 } 464 }
471 465
472 BodyStreamBuffer* Body::createDrainingStream() 466 BodyStreamBuffer* Body::createDrainingStream()
473 { 467 {
474 return m_streamSource->createDrainingStream(); 468 return m_streamSource->createDrainingStream();
475 } 469 }
476 470
477 void Body::stop() 471 void Body::stop()
478 { 472 {
479 // Canceling the load will call didFail which will remove the resolver. 473 if (m_fetchDataLoader) {
480 if (m_loader) 474 m_fetchDataLoader->cancel();
481 m_loader->cancel(); 475 m_fetchDataLoader.clear();
476 }
482 } 477 }
483 478
484 bool Body::hasPendingActivity() const 479 bool Body::hasPendingActivity() const
485 { 480 {
486 if (executionContext()->activeDOMObjectsAreStopped()) 481 if (executionContext()->activeDOMObjectsAreStopped())
487 return false; 482 return false;
488 if (m_resolver) 483 if (m_resolver)
489 return true; 484 return true;
490 if (m_stream->isLocked()) 485 if (m_stream->isLocked())
491 return true; 486 return true;
492 return false; 487 return false;
493 } 488 }
494 489
495 Body::ReadableStreamSource* Body::createBodySource(PassRefPtr<BlobDataHandle> ha ndle) 490 Body::ReadableStreamSource* Body::createBodySource(PassRefPtr<BlobDataHandle> ha ndle)
496 { 491 {
497 return new ReadableStreamSource(executionContext(), handle); 492 return new ReadableStreamSource(executionContext(), handle);
498 } 493 }
499 494
500 Body::ReadableStreamSource* Body::createBodySource(BodyStreamBuffer* buffer) 495 Body::ReadableStreamSource* Body::createBodySource(BodyStreamBuffer* buffer)
501 { 496 {
502 return new ReadableStreamSource(executionContext(), buffer); 497 return new ReadableStreamSource(executionContext(), buffer);
503 } 498 }
504 499
505 DEFINE_TRACE(Body) 500 DEFINE_TRACE(Body)
506 { 501 {
502 visitor->trace(m_fetchDataLoader);
507 visitor->trace(m_resolver); 503 visitor->trace(m_resolver);
508 visitor->trace(m_stream); 504 visitor->trace(m_stream);
509 visitor->trace(m_streamSource); 505 visitor->trace(m_streamSource);
510 ActiveDOMObject::trace(visitor); 506 ActiveDOMObject::trace(visitor);
507 FetchDataLoader::Client::trace(visitor);
511 } 508 }
512 509
513 Body::Body(ExecutionContext* context) 510 Body::Body(ExecutionContext* context)
514 : ActiveDOMObject(context) 511 : ActiveDOMObject(context)
515 , m_bodyUsed(false) 512 , m_bodyUsed(false)
516 , m_responseType(ResponseType::ResponseUnknown) 513 , m_responseType(ResponseType::ResponseUnknown)
517 , m_streamSource(new ReadableStreamSource(context)) 514 , m_streamSource(new ReadableStreamSource(context))
518 , m_stream(new ReadableByteStream(m_streamSource, new ReadableByteStream::St rictStrategy)) 515 , m_stream(new ReadableByteStream(m_streamSource, new ReadableByteStream::St rictStrategy))
519 { 516 {
520 m_streamSource->startStream(m_stream); 517 m_streamSource->startStream(m_stream);
521 } 518 }
522 519
523 void Body::resolveJSON(const String& string) 520 void Body::resolveJSON(const String& string)
524 { 521 {
525 ASSERT(m_responseType == ResponseAsJSON); 522 ASSERT(m_responseType == ResponseAsJSON);
526 ScriptState::Scope scope(m_resolver->scriptState()); 523 ScriptState::Scope scope(m_resolver->scriptState());
527 v8::Isolate* isolate = m_resolver->scriptState()->isolate(); 524 v8::Isolate* isolate = m_resolver->scriptState()->isolate();
528 v8::Local<v8::String> inputString = v8String(isolate, string); 525 v8::Local<v8::String> inputString = v8String(isolate, string);
529 v8::TryCatch trycatch; 526 v8::TryCatch trycatch;
530 v8::Local<v8::Value> parsed; 527 v8::Local<v8::Value> parsed;
531 if (v8Call(v8::JSON::Parse(isolate, inputString), parsed, trycatch)) 528 if (v8Call(v8::JSON::Parse(isolate, inputString), parsed, trycatch))
532 m_resolver->resolve(parsed); 529 m_resolver->resolve(parsed);
533 else 530 else
534 m_resolver->reject(trycatch.Exception()); 531 m_resolver->reject(trycatch.Exception());
535 } 532 }
536 533
537 // FileReaderLoaderClient functions. 534 // FetchDataLoader::Client functions.
538 void Body::didStartLoading() { } 535 void Body::didFetchDataLoadFailed()
539 void Body::didReceiveData() { }
540 void Body::didFinishLoading()
541 { 536 {
542 if (!executionContext() || executionContext()->activeDOMObjectsAreStopped()) 537 ASSERT(m_fetchDataLoader);
543 return; 538 m_fetchDataLoader.clear();
544 539
545 switch (m_responseType) {
546 case ResponseAsArrayBuffer:
547 m_resolver->resolve(m_loader->arrayBufferResult());
548 break;
549 case ResponseAsBlob: {
550 ASSERT(blobDataHandle()->size() == kuint64max);
551 OwnPtr<BlobData> blobData = BlobData::create();
552 RefPtr<DOMArrayBuffer> buffer = m_loader->arrayBufferResult();
553 blobData->appendBytes(buffer->data(), buffer->byteLength());
554 blobData->setContentType(mimeType());
555 const size_t length = blobData->length();
556 m_resolver->resolve(Blob::create(BlobDataHandle::create(blobData.release (), length)));
557 break;
558 }
559 case ResponseAsFormData:
560 ASSERT_NOT_REACHED();
561 break;
562 case ResponseAsJSON:
563 resolveJSON(m_loader->stringResult());
564 break;
565 case ResponseAsText:
566 m_resolver->resolve(m_loader->stringResult());
567 break;
568 default:
569 ASSERT_NOT_REACHED();
570 }
571 m_streamSource->close();
572 m_resolver.clear();
573 }
574
575 void Body::didFail(FileError::ErrorCode code)
576 {
577 if (!executionContext() || executionContext()->activeDOMObjectsAreStopped()) 540 if (!executionContext() || executionContext()->activeDOMObjectsAreStopped())
578 return; 541 return;
579 542
580 m_streamSource->error(); 543 m_streamSource->error();
581 if (m_resolver) { 544 if (m_resolver) {
582 // FIXME: We should reject the promise. 545 if (!m_resolver->executionContext() || m_resolver->executionContext()->a ctiveDOMObjectsAreStopped()) {
583 m_resolver->resolve(""); 546 m_resolver.clear();
547 return;
548 }
549 ScriptState* state = m_resolver->scriptState();
550 ScriptState::Scope scope(state);
551 m_resolver->reject(V8ThrowException::createTypeError(state->isolate(), " Failed to fetch"));
hiroshige 2015/06/23 13:14:26 didFetchDataLoadFailed() can be called e.g. in htt
584 m_resolver.clear(); 552 m_resolver.clear();
585 } 553 }
586 } 554 }
587 555
556 void Body::didFetchDataLoadedBlobHandle(PassRefPtr<BlobDataHandle> blobDataHandl e)
557 {
558 ASSERT(m_fetchDataLoader);
559 m_fetchDataLoader.clear();
560
561 if (!executionContext() || executionContext()->activeDOMObjectsAreStopped())
562 return;
563
564 ASSERT(m_responseType == ResponseAsBlob);
565 m_resolver->resolve(Blob::create(blobDataHandle));
566 m_streamSource->close();
567 m_resolver.clear();
568 }
569
570 void Body::didFetchDataLoadedArrayBuffer(PassRefPtr<DOMArrayBuffer> arrayBuffer)
571 {
572 ASSERT(m_fetchDataLoader);
573 m_fetchDataLoader.clear();
574
575 if (!executionContext() || executionContext()->activeDOMObjectsAreStopped())
576 return;
577
578 ASSERT(m_responseType == ResponseAsArrayBuffer);
579 m_resolver->resolve(arrayBuffer);
580 m_streamSource->close();
581 m_resolver.clear();
582 }
583
584 void Body::didFetchDataLoadedString(const String& str)
585 {
586 ASSERT(m_fetchDataLoader);
587 m_fetchDataLoader.clear();
588
589 if (!executionContext() || executionContext()->activeDOMObjectsAreStopped())
590 return;
591
592 switch (m_responseType) {
593 case ResponseAsJSON:
594 resolveJSON(str);
595 break;
596 case ResponseAsText:
597 m_resolver->resolve(str);
598 break;
599 default:
600 ASSERT_NOT_REACHED();
601 }
602
603 m_streamSource->close();
604 m_resolver.clear();
605 }
606
588 void Body::didBlobHandleReceiveError(DOMException* exception) 607 void Body::didBlobHandleReceiveError(DOMException* exception)
589 { 608 {
590 if (!m_resolver) 609 if (!m_resolver)
591 return; 610 return;
592 m_streamSource->error(); 611 m_streamSource->error();
593 m_resolver->reject(exception); 612 m_resolver->reject(exception);
594 m_resolver.clear(); 613 m_resolver.clear();
595 } 614 }
596 615
597 } // namespace blink 616 } // namespace blink
OLDNEW
« no previous file with comments | « Source/modules/fetch/Body.h ('k') | Source/modules/serviceworkers/RespondWithObserver.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698