| // Copyright 2014 The Chromium Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #ifndef THIRD_PARTY_BLINK_RENDERER_CORE_FETCH_BODY_STREAM_BUFFER_H_ |
| #define THIRD_PARTY_BLINK_RENDERER_CORE_FETCH_BODY_STREAM_BUFFER_H_ |
| |
| #include <memory> |
| #include "base/types/pass_key.h" |
| #include "mojo/public/cpp/bindings/pending_remote.h" |
| #include "services/network/public/mojom/chunked_data_pipe_getter.mojom-blink.h" |
| #include "third_party/blink/renderer/bindings/core/v8/script_promise.h" |
| #include "third_party/blink/renderer/bindings/core/v8/script_value.h" |
| #include "third_party/blink/renderer/core/core_export.h" |
| #include "third_party/blink/renderer/core/dom/abort_signal.h" |
| #include "third_party/blink/renderer/core/dom/dom_exception.h" |
| #include "third_party/blink/renderer/core/fetch/fetch_data_loader.h" |
| #include "third_party/blink/renderer/core/streams/underlying_source_base.h" |
| #include "third_party/blink/renderer/platform/bindings/trace_wrapper_v8_reference.h" |
| #include "third_party/blink/renderer/platform/heap/handle.h" |
| #include "third_party/blink/renderer/platform/loader/fetch/bytes_consumer.h" |
| |
| namespace blink { |
| |
| class BytesUploader; |
| class EncodedFormData; |
| class ExceptionState; |
| class ReadableStream; |
| class ScriptState; |
| class ScriptCachedMetadataHandler; |
| |
| class CORE_EXPORT BodyStreamBuffer final : public UnderlyingSourceBase, |
| public BytesConsumer::Client { |
| public: |
| using PassKey = base::PassKey<BodyStreamBuffer>; |
| |
| // Create a BodyStreamBuffer for |consumer|. |
| // |consumer| must not have a client. |
| // This function must be called after entering an appropriate V8 context. |
| // |signal| should be non-null when this BodyStreamBuffer is associated with a |
| // Response that was created by fetch(). |
| static BodyStreamBuffer* Create( |
| ScriptState*, |
| BytesConsumer* consumer, |
| AbortSignal* signal, |
| ScriptCachedMetadataHandler* cached_metadata_handler, |
| scoped_refptr<BlobDataHandle> side_data_blob = nullptr); |
| |
| // Create() should be used instead of calling this constructor directly. |
| BodyStreamBuffer(PassKey, |
| ScriptState*, |
| BytesConsumer* consumer, |
| AbortSignal* signal, |
| ScriptCachedMetadataHandler* cached_metadata_handler, |
| scoped_refptr<BlobDataHandle> side_data_blob); |
| |
| BodyStreamBuffer(ScriptState*, |
| ReadableStream* stream, |
| ScriptCachedMetadataHandler* cached_metadata_handler, |
| scoped_refptr<BlobDataHandle> side_data_blob = nullptr); |
| |
| ReadableStream* Stream() { return stream_; } |
| |
| // Callable only when neither locked nor disturbed. |
| scoped_refptr<BlobDataHandle> DrainAsBlobDataHandle( |
| BytesConsumer::BlobSizePolicy); |
| scoped_refptr<EncodedFormData> DrainAsFormData(); |
| void DrainAsChunkedDataPipeGetter( |
| ScriptState*, |
| mojo::PendingReceiver<network::mojom::blink::ChunkedDataPipeGetter>); |
| void StartLoading(FetchDataLoader*, |
| FetchDataLoader::Client* /* client */, |
| ExceptionState&); |
| void Tee(BodyStreamBuffer**, BodyStreamBuffer**, ExceptionState&); |
| |
| // UnderlyingSourceBase |
| ScriptPromise pull(ScriptState*) override; |
| ScriptPromise Cancel(ScriptState*, ScriptValue reason) override; |
| bool HasPendingActivity() const override; |
| void ContextDestroyed() override; |
| |
| // BytesConsumer::Client |
| void OnStateChange() override; |
| String DebugName() const override { return "BodyStreamBuffer"; } |
| |
| bool IsStreamReadable() const; |
| bool IsStreamClosed() const; |
| bool IsStreamErrored() const; |
| bool IsStreamLocked() const; |
| bool IsStreamDisturbed() const; |
| |
| // Closes the stream if necessary, and then locks and disturbs it. Should not |
| // be called if |stream_broken_| is true. |
| void CloseAndLockAndDisturb(); |
| |
| ScriptState* GetScriptState() { return script_state_; } |
| |
| bool IsAborted(); |
| |
| // Returns the ScriptCachedMetadataHandler associated with the contents of |
| // this stream. This can return nullptr. Streams' ownership model applies, so |
| // this function is expected to be called by the owner of this stream. |
| ScriptCachedMetadataHandler* GetCachedMetadataHandler() { |
| DCHECK(!IsStreamLocked()); |
| DCHECK(!IsStreamDisturbed()); |
| return cached_metadata_handler_; |
| } |
| |
| // Take the blob representing any side data associated with this body |
| // stream. This must be called before the body is drained or begins |
| // loading. |
| scoped_refptr<BlobDataHandle> TakeSideDataBlob(); |
| scoped_refptr<BlobDataHandle> GetSideDataBlobForTest() const { |
| return side_data_blob_; |
| } |
| |
| bool IsMadeFromReadableStream() const { return made_from_readable_stream_; } |
| |
| void Trace(Visitor*) const override; |
| |
| private: |
| class LoaderClient; |
| |
| // This method exists to avoid re-entrancy inside the BodyStreamBuffer |
| // constructor. It is called by Create(). It should not be called after |
| // using the ReadableStream* constructor. |
| void Init(); |
| |
| BytesConsumer* ReleaseHandle(ExceptionState&); |
| void Abort(); |
| void Close(); |
| void GetError(); |
| void CancelConsumer(); |
| void ProcessData(); |
| void EndLoading(); |
| void StopLoading(); |
| |
| Member<ScriptState> script_state_; |
| Member<ReadableStream> stream_; |
| Member<BytesUploader> stream_uploader_; |
| Member<BytesConsumer> consumer_; |
| // We need this member to keep it alive while loading. |
| Member<FetchDataLoader> loader_; |
| // We need this to ensure that we detect that abort has been signalled |
| // correctly. |
| Member<AbortSignal> signal_; |
| // CachedMetadata handler used for loading compiled WASM code. |
| Member<ScriptCachedMetadataHandler> cached_metadata_handler_; |
| // Additional side data associated with this body stream. It should only be |
| // retained until the body is drained or starts loading. Client code, such |
| // as service workers, can call TakeSideDataBlob() prior to consumption. |
| scoped_refptr<BlobDataHandle> side_data_blob_; |
| bool stream_needs_more_ = false; |
| bool made_from_readable_stream_; |
| bool in_process_data_ = false; |
| |
| // TODO(ricea): Remove remaining uses of |stream_broken_|. |
| bool stream_broken_ = false; |
| |
| DISALLOW_COPY_AND_ASSIGN(BodyStreamBuffer); |
| }; |
| |
| } // namespace blink |
| |
| #endif // THIRD_PARTY_BLINK_RENDERER_CORE_FETCH_BODY_STREAM_BUFFER_H_ |