| /* |
| * Copyright (C) 2016 Canon Inc. |
| * |
| * Redistribution and use in source and binary forms, with or without |
| * modification, are permitted, provided that the following conditions |
| * are required to be met: |
| * |
| * 1. Redistributions of source code must retain the above copyright |
| * notice, this list of conditions and the following disclaimer. |
| * 2. Redistributions in binary form must reproduce the above copyright |
| * notice, this list of conditions and the following disclaimer in the |
| * documentation and/or other materials provided with the distribution. |
| * 3. Neither the name of Canon Inc. nor the names of |
| * its contributors may be used to endorse or promote products derived |
| * from this software without specific prior written permission. |
| * |
| * THIS SOFTWARE IS PROVIDED BY CANON INC. AND ITS CONTRIBUTORS "AS IS" AND ANY |
| * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
| * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
| * DISCLAIMED. IN NO EVENT SHALL CANON INC. AND ITS CONTRIBUTORS BE LIABLE FOR |
| * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL |
| * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR |
| * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER |
| * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, |
| * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
| * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
| */ |
| |
| #pragma once |
| |
| #include "FetchBodyOwner.h" |
| #include "FetchHeaders.h" |
| #include "ResourceResponse.h" |
| #include <runtime/TypedArrays.h> |
| |
| namespace JSC { |
| class ExecState; |
| class JSValue; |
| }; |
| |
| namespace WebCore { |
| |
| class FetchRequest; |
| class ReadableStreamSource; |
| |
| class FetchResponse final : public FetchBodyOwner { |
| public: |
| using Type = ResourceResponse::Type; |
| |
| struct Init { |
| unsigned short status { 200 }; |
| String statusText { ASCIILiteral("OK") }; |
| std::optional<FetchHeaders::Init> headers; |
| }; |
| |
| static Ref<FetchResponse> create(ScriptExecutionContext& context) { return adoptRef(*new FetchResponse(context, std::nullopt, FetchHeaders::create(FetchHeaders::Guard::Response), ResourceResponse())); } |
| static Ref<FetchResponse> error(ScriptExecutionContext&); |
| static ExceptionOr<Ref<FetchResponse>> redirect(ScriptExecutionContext&, const String& url, int status); |
| |
| static Ref<FetchResponse> create(ScriptExecutionContext& context, std::optional<FetchBody>&& body, Ref<FetchHeaders>&& headers, ResourceResponse&& response) { return adoptRef(*new FetchResponse(context, WTFMove(body), WTFMove(headers), WTFMove(response))); } |
| |
| using NotificationCallback = WTF::Function<void(ExceptionOr<FetchResponse&>&&)>; |
| static void fetch(ScriptExecutionContext&, FetchRequest&, NotificationCallback&&); |
| |
| void consume(unsigned, Ref<DeferredPromise>&&); |
| #if ENABLE(STREAMS_API) |
| void startConsumingStream(unsigned); |
| void consumeChunk(Ref<JSC::Uint8Array>&&); |
| void finishConsumingStream(Ref<DeferredPromise>&&); |
| #endif |
| |
| ExceptionOr<void> setStatus(int status, const String& statusText); |
| void initializeWith(FetchBody::Init&&); |
| void setBodyAsReadableStream(); |
| |
| Type type() const { return m_response.type(); } |
| const String& url() const; |
| bool redirected() const { return m_response.isRedirected(); } |
| int status() const { return m_response.httpStatusCode(); } |
| bool ok() const { return m_response.isSuccessful(); } |
| const String& statusText() const { return m_response.httpStatusText(); } |
| |
| const FetchHeaders& headers() const { return m_headers; } |
| FetchHeaders& headers() { return m_headers; } |
| Ref<FetchResponse> cloneForJS(); |
| |
| #if ENABLE(STREAMS_API) |
| ReadableStreamSource* createReadableStreamSource(); |
| void consumeBodyAsStream(); |
| void feedStream(); |
| void cancel(); |
| #endif |
| |
| using ResponseData = Variant<std::nullptr_t, Ref<FormData>, Ref<SharedBuffer>>; |
| ResponseData consumeBody(); |
| void setBodyData(ResponseData&&); |
| |
| bool isLoading() const { return !!m_bodyLoader; } |
| |
| using ConsumeDataCallback = WTF::Function<void(ExceptionOr<RefPtr<SharedBuffer>>&&)>; |
| void consumeBodyWhenLoaded(ConsumeDataCallback&&); |
| |
| const ResourceResponse& resourceResponse() const { return m_response; } |
| |
| // FIXME: Remove this method and use FetchBodyOwner one once we have full support in DOM ReadableStream. |
| bool hasReadableStreamBody() const final { return m_isReadableStream; } |
| |
| private: |
| FetchResponse(ScriptExecutionContext&, std::optional<FetchBody>&&, Ref<FetchHeaders>&&, ResourceResponse&&); |
| |
| void stop() final; |
| const char* activeDOMObjectName() const final; |
| bool canSuspendForDocumentSuspension() const final; |
| |
| #if ENABLE(STREAMS_API) |
| void closeStream(); |
| #endif |
| |
| class BodyLoader final : public FetchLoaderClient { |
| public: |
| BodyLoader(FetchResponse&, NotificationCallback&&); |
| ~BodyLoader(); |
| |
| bool start(ScriptExecutionContext&, const FetchRequest&); |
| void stop(); |
| |
| void setConsumeDataCallback(ConsumeDataCallback&& consumeDataCallback) { m_consumeDataCallback = WTFMove(consumeDataCallback); } |
| |
| #if ENABLE(STREAMS_API) |
| RefPtr<SharedBuffer> startStreaming(); |
| #endif |
| |
| private: |
| // FetchLoaderClient API |
| void didSucceed() final; |
| void didFail(const ResourceError&) final; |
| void didReceiveResponse(const ResourceResponse&) final; |
| void didReceiveData(const char*, size_t) final; |
| |
| FetchResponse& m_response; |
| NotificationCallback m_responseCallback; |
| ConsumeDataCallback m_consumeDataCallback; |
| std::unique_ptr<FetchLoader> m_loader; |
| }; |
| |
| ResourceResponse m_response; |
| std::optional<BodyLoader> m_bodyLoader; |
| mutable String m_responseURL; |
| bool m_shouldExposeBody { true }; |
| // FIXME: Remove that flag once we have full support in DOM ReadableStream. |
| bool m_isReadableStream { false }; |
| |
| FetchBodyConsumer m_consumer { FetchBodyConsumer::Type::ArrayBuffer }; |
| }; |
| |
| } // namespace WebCore |