| /* |
| * Copyright (C) 2009 Google Inc. All rights reserved. |
| * |
| * Redistribution and use in source and binary forms, with or without |
| * modification, are permitted provided that the following conditions are |
| * met: |
| * |
| * * Redistributions of source code must retain the above copyright |
| * notice, this list of conditions and the following disclaimer. |
| * * 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. |
| * * Neither the name of Google 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 THE COPYRIGHT HOLDERS AND 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 THE COPYRIGHT |
| * OWNER OR 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. |
| */ |
| |
| #include "third_party/blink/public/platform/web_url_request.h" |
| |
| #include <memory> |
| |
| #include "base/time/time.h" |
| #include "net/base/load_flags.h" |
| #include "services/network/public/cpp/features.h" |
| #include "services/network/public/cpp/optional_trust_token_params.h" |
| #include "third_party/blink/public/mojom/fetch/fetch_api_request.mojom-blink.h" |
| #include "third_party/blink/public/platform/url_conversion.h" |
| #include "third_party/blink/public/platform/web_http_body.h" |
| #include "third_party/blink/public/platform/web_http_header_visitor.h" |
| #include "third_party/blink/public/platform/web_security_origin.h" |
| #include "third_party/blink/public/platform/web_url.h" |
| #include "third_party/blink/public/platform/web_url_request_extra_data.h" |
| #include "third_party/blink/renderer/platform/loader/fetch/resource_request.h" |
| #include "third_party/blink/renderer/platform/loader/fetch/trust_token_params_conversion.h" |
| #include "third_party/blink/renderer/platform/network/encoded_form_data.h" |
| #include "third_party/blink/renderer/platform/weborigin/referrer.h" |
| #include "third_party/blink/renderer/platform/weborigin/security_origin.h" |
| #include "third_party/blink/renderer/platform/wtf/allocator/allocator.h" |
| |
| using blink::mojom::FetchCacheMode; |
| |
| namespace blink { |
| |
| // This is complementary to ConvertRequestPriorityToResourceLoadPriority, |
| // defined in third_party/blink/renderer/core/fetch/fetch_request_data.cc. |
| net::RequestPriority WebURLRequest::ConvertToNetPriority( |
| WebURLRequest::Priority priority) { |
| switch (priority) { |
| case WebURLRequest::Priority::kVeryHigh: |
| return net::HIGHEST; |
| |
| case WebURLRequest::Priority::kHigh: |
| return net::MEDIUM; |
| |
| case WebURLRequest::Priority::kMedium: |
| return net::LOW; |
| |
| case WebURLRequest::Priority::kLow: |
| return net::LOWEST; |
| |
| case WebURLRequest::Priority::kVeryLow: |
| return net::IDLE; |
| |
| case WebURLRequest::Priority::kUnresolved: |
| default: |
| NOTREACHED(); |
| } |
| } |
| |
| WebURLRequest::~WebURLRequest() = default; |
| |
| WebURLRequest::WebURLRequest() |
| : owned_resource_request_(std::make_unique<ResourceRequest>()), |
| resource_request_(owned_resource_request_.get()) {} |
| |
| WebURLRequest::WebURLRequest(WebURLRequest&& src) { |
| *this = std::move(src); |
| } |
| |
| WebURLRequest& WebURLRequest::operator=(WebURLRequest&& src) { |
| if (this == &src) { |
| return *this; |
| } |
| if (src.owned_resource_request_) { |
| owned_resource_request_ = std::move(src.owned_resource_request_); |
| resource_request_ = owned_resource_request_.get(); |
| } else { |
| owned_resource_request_ = std::make_unique<ResourceRequest>(); |
| resource_request_ = owned_resource_request_.get(); |
| CopyFrom(src); |
| } |
| src.resource_request_ = nullptr; |
| return *this; |
| } |
| |
| WebURLRequest::WebURLRequest(const WebURL& url) : WebURLRequest() { |
| SetUrl(url); |
| } |
| |
| void WebURLRequest::CopyFrom(const WebURLRequest& r) { |
| // Copying subclasses that have different m_resourceRequest ownership |
| // semantics via this operator is just not supported. |
| DCHECK(owned_resource_request_); |
| DCHECK_EQ(owned_resource_request_.get(), resource_request_); |
| DCHECK(owned_resource_request_->IsNull()); |
| DCHECK(this != &r); |
| resource_request_->CopyHeadFrom(*r.resource_request_); |
| resource_request_->SetHttpBody(r.resource_request_->HttpBody()); |
| } |
| |
| bool WebURLRequest::IsNull() const { |
| return resource_request_->IsNull(); |
| } |
| |
| WebURL WebURLRequest::Url() const { |
| return resource_request_->Url(); |
| } |
| |
| void WebURLRequest::SetUrl(const WebURL& url) { |
| resource_request_->SetUrl(url); |
| } |
| |
| const net::SiteForCookies& WebURLRequest::SiteForCookies() const { |
| return resource_request_->SiteForCookies(); |
| } |
| |
| void WebURLRequest::SetSiteForCookies( |
| const net::SiteForCookies& site_for_cookies) { |
| resource_request_->SetSiteForCookies(site_for_cookies); |
| } |
| |
| std::optional<WebSecurityOrigin> WebURLRequest::TopFrameOrigin() const { |
| const SecurityOrigin* origin = resource_request_->TopFrameOrigin(); |
| return origin ? std::optional<WebSecurityOrigin>(origin) |
| : std::optional<WebSecurityOrigin>(); |
| } |
| |
| void WebURLRequest::SetTopFrameOrigin(const WebSecurityOrigin& origin) { |
| resource_request_->SetTopFrameOrigin(origin); |
| } |
| |
| WebSecurityOrigin WebURLRequest::RequestorOrigin() const { |
| return resource_request_->RequestorOrigin(); |
| } |
| |
| WebSecurityOrigin WebURLRequest::IsolatedWorldOrigin() const { |
| return resource_request_->IsolatedWorldOrigin(); |
| } |
| |
| void WebURLRequest::SetRequestorOrigin( |
| const WebSecurityOrigin& requestor_origin) { |
| resource_request_->SetRequestorOrigin(requestor_origin); |
| } |
| |
| mojom::FetchCacheMode WebURLRequest::GetCacheMode() const { |
| return resource_request_->GetCacheMode(); |
| } |
| |
| void WebURLRequest::SetCacheMode(mojom::FetchCacheMode cache_mode) { |
| resource_request_->SetCacheMode(cache_mode); |
| } |
| |
| base::TimeDelta WebURLRequest::TimeoutInterval() const { |
| return resource_request_->TimeoutInterval(); |
| } |
| |
| WebString WebURLRequest::HttpMethod() const { |
| return resource_request_->HttpMethod(); |
| } |
| |
| void WebURLRequest::SetHttpMethod(const WebString& http_method) { |
| resource_request_->SetHttpMethod(http_method); |
| } |
| |
| WebString WebURLRequest::HttpContentType() const { |
| return resource_request_->HttpContentType(); |
| } |
| |
| bool WebURLRequest::IsFormSubmission() const { |
| return resource_request_->IsFormSubmission(); |
| } |
| |
| WebString WebURLRequest::HttpHeaderField(const WebString& name) const { |
| return resource_request_->HttpHeaderField(name); |
| } |
| |
| void WebURLRequest::SetHttpHeaderField(const WebString& name, |
| const WebString& value) { |
| CHECK(!EqualIgnoringAsciiCase(name, "referer")); |
| resource_request_->SetHttpHeaderField(name, value); |
| } |
| |
| void WebURLRequest::AddHttpHeaderField(const WebString& name, |
| const WebString& value) { |
| resource_request_->AddHttpHeaderField(name, value); |
| } |
| |
| void WebURLRequest::ClearHttpHeaderField(const WebString& name) { |
| resource_request_->ClearHttpHeaderField(name); |
| } |
| |
| void WebURLRequest::VisitHttpHeaderFields(WebHTTPHeaderVisitor* visitor) const { |
| const HTTPHeaderMap& map = resource_request_->HttpHeaderFields(); |
| for (HTTPHeaderMap::const_iterator it = map.begin(); it != map.end(); ++it) |
| visitor->VisitHeader(it->key, it->value); |
| } |
| |
| WebHTTPBody WebURLRequest::HttpBody() const { |
| return WebHTTPBody(resource_request_->HttpBody()); |
| } |
| |
| void WebURLRequest::SetHttpBody(const WebHTTPBody& http_body) { |
| resource_request_->SetHttpBody(http_body); |
| } |
| |
| bool WebURLRequest::ReportUploadProgress() const { |
| return resource_request_->ReportUploadProgress(); |
| } |
| |
| void WebURLRequest::SetReportUploadProgress(bool report_upload_progress) { |
| resource_request_->SetReportUploadProgress(report_upload_progress); |
| } |
| |
| mojom::blink::RequestContextType WebURLRequest::GetRequestContext() const { |
| return resource_request_->GetRequestContext(); |
| } |
| |
| network::mojom::RequestDestination WebURLRequest::GetRequestDestination() |
| const { |
| return resource_request_->GetRequestDestination(); |
| } |
| |
| void WebURLRequest::SetReferrerString(const WebString& referrer) { |
| resource_request_->SetReferrerString(referrer); |
| } |
| |
| void WebURLRequest::SetReferrerPolicy( |
| network::mojom::ReferrerPolicy referrer_policy) { |
| resource_request_->SetReferrerPolicy(referrer_policy); |
| } |
| |
| WebString WebURLRequest::ReferrerString() const { |
| return resource_request_->ReferrerString(); |
| } |
| |
| network::mojom::ReferrerPolicy WebURLRequest::GetReferrerPolicy() const { |
| return resource_request_->GetReferrerPolicy(); |
| } |
| |
| bool WebURLRequest::HasUserGesture() const { |
| return resource_request_->HasUserGesture(); |
| } |
| |
| bool WebURLRequest::HasTextFragmentToken() const { |
| return resource_request_->HasTextFragmentToken(); |
| } |
| |
| void WebURLRequest::SetHasUserGesture(bool has_user_gesture) { |
| resource_request_->SetHasUserGesture(has_user_gesture); |
| } |
| |
| void WebURLRequest::SetRequestContext( |
| mojom::blink::RequestContextType request_context) { |
| resource_request_->SetRequestContext(request_context); |
| } |
| |
| void WebURLRequest::SetRequestDestination( |
| network::mojom::RequestDestination destination) { |
| resource_request_->SetRequestDestination(destination); |
| } |
| |
| bool WebURLRequest::UseStreamOnResponse() const { |
| return resource_request_->UseStreamOnResponse(); |
| } |
| |
| void WebURLRequest::SetUseStreamOnResponse(bool use_stream_on_response) { |
| resource_request_->SetUseStreamOnResponse(use_stream_on_response); |
| } |
| |
| bool WebURLRequest::GetKeepalive() const { |
| return resource_request_->GetKeepalive(); |
| } |
| |
| void WebURLRequest::SetKeepalive(bool keepalive) { |
| resource_request_->SetKeepalive(keepalive); |
| } |
| |
| bool WebURLRequest::GetSkipServiceWorker() const { |
| return resource_request_->GetSkipServiceWorker(); |
| } |
| |
| void WebURLRequest::SetSkipServiceWorker(bool skip_service_worker) { |
| resource_request_->SetSkipServiceWorker(skip_service_worker); |
| } |
| |
| network::mojom::RequestMode WebURLRequest::GetMode() const { |
| return resource_request_->GetMode(); |
| } |
| |
| void WebURLRequest::SetMode(network::mojom::RequestMode mode) { |
| return resource_request_->SetMode(mode); |
| } |
| |
| bool WebURLRequest::GetFavicon() const { |
| return resource_request_->IsFavicon(); |
| } |
| |
| void WebURLRequest::SetFavicon(bool) { |
| resource_request_->SetFavicon(true); |
| } |
| |
| network::mojom::CredentialsMode WebURLRequest::GetCredentialsMode() const { |
| return resource_request_->GetCredentialsMode(); |
| } |
| |
| void WebURLRequest::SetCredentialsMode(network::mojom::CredentialsMode mode) { |
| return resource_request_->SetCredentialsMode(mode); |
| } |
| |
| network::mojom::RedirectMode WebURLRequest::GetRedirectMode() const { |
| return resource_request_->GetRedirectMode(); |
| } |
| |
| void WebURLRequest::SetRedirectMode(network::mojom::RedirectMode redirect) { |
| return resource_request_->SetRedirectMode(redirect); |
| } |
| |
| const scoped_refptr<WebURLRequestExtraData>& |
| WebURLRequest::GetURLRequestExtraData() const { |
| return resource_request_->GetURLRequestExtraData(); |
| } |
| |
| void WebURLRequest::SetURLRequestExtraData( |
| scoped_refptr<WebURLRequestExtraData> extra_data) { |
| resource_request_->SetURLRequestExtraData(std::move(extra_data)); |
| } |
| |
| bool WebURLRequest::IsDownloadToNetworkCacheOnly() const { |
| return resource_request_->IsDownloadToNetworkCacheOnly(); |
| } |
| |
| void WebURLRequest::SetDownloadToNetworkCacheOnly(bool download_to_cache_only) { |
| resource_request_->SetDownloadToNetworkCacheOnly(download_to_cache_only); |
| } |
| |
| ResourceRequest& WebURLRequest::ToMutableResourceRequest() { |
| DCHECK(resource_request_); |
| return *resource_request_; |
| } |
| |
| WebURLRequest::Priority WebURLRequest::GetPriority() const { |
| return static_cast<WebURLRequest::Priority>(resource_request_->Priority()); |
| } |
| |
| void WebURLRequest::SetPriority(WebURLRequest::Priority priority) { |
| resource_request_->SetPriority(static_cast<ResourceLoadPriority>(priority)); |
| } |
| |
| network::mojom::CorsPreflightPolicy WebURLRequest::GetCorsPreflightPolicy() |
| const { |
| return resource_request_->CorsPreflightPolicy(); |
| } |
| |
| std::optional<WebString> WebURLRequest::GetSuggestedFilename() const { |
| if (!resource_request_->GetSuggestedFilename().has_value()) |
| return std::optional<WebString>(); |
| return static_cast<WebString>( |
| resource_request_->GetSuggestedFilename().value()); |
| } |
| |
| bool WebURLRequest::IsAdResource() const { |
| return resource_request_->IsAdResource(); |
| } |
| |
| void WebURLRequest::SetUpgradeIfInsecure(bool upgrade_if_insecure) { |
| resource_request_->SetUpgradeIfInsecure(upgrade_if_insecure); |
| } |
| |
| bool WebURLRequest::UpgradeIfInsecure() const { |
| return resource_request_->UpgradeIfInsecure(); |
| } |
| |
| bool WebURLRequest::SupportsAsyncRevalidation() const { |
| return resource_request_->AllowsStaleResponse(); |
| } |
| |
| bool WebURLRequest::IsRevalidating() const { |
| return resource_request_->IsRevalidating(); |
| } |
| |
| const std::optional<base::UnguessableToken>& |
| WebURLRequest::GetDevToolsThrottlingToken() const { |
| return resource_request_->GetDevToolsThrottlingToken(); |
| } |
| |
| const WebString WebURLRequest::GetRequestedWithHeader() const { |
| return resource_request_->GetRequestedWithHeader(); |
| } |
| |
| void WebURLRequest::SetRequestedWithHeader(const WebString& value) { |
| resource_request_->SetRequestedWithHeader(value); |
| } |
| |
| const base::UnguessableToken& WebURLRequest::GetFetchWindowId() const { |
| return resource_request_->GetFetchWindowId(); |
| } |
| void WebURLRequest::SetFetchWindowId(const base::UnguessableToken& id) { |
| resource_request_->SetFetchWindowId(id); |
| } |
| |
| int WebURLRequest::GetLoadFlagsForWebUrlRequest() const { |
| int load_flags = net::LOAD_NORMAL; |
| |
| switch (resource_request_->GetCacheMode()) { |
| case FetchCacheMode::kNoStore: |
| load_flags |= net::LOAD_DISABLE_CACHE | net::LOAD_BYPASS_CACHE; |
| break; |
| case FetchCacheMode::kValidateCache: |
| load_flags |= net::LOAD_VALIDATE_CACHE; |
| break; |
| case FetchCacheMode::kBypassCache: |
| load_flags |= net::LOAD_BYPASS_CACHE; |
| break; |
| case FetchCacheMode::kForceCache: |
| load_flags |= net::LOAD_SKIP_CACHE_VALIDATION; |
| break; |
| case FetchCacheMode::kOnlyIfCached: |
| load_flags |= net::LOAD_ONLY_FROM_CACHE | net::LOAD_SKIP_CACHE_VALIDATION; |
| break; |
| case FetchCacheMode::kUnspecifiedOnlyIfCachedStrict: |
| load_flags |= net::LOAD_ONLY_FROM_CACHE; |
| break; |
| case FetchCacheMode::kDefault: |
| break; |
| case FetchCacheMode::kUnspecifiedForceCacheMiss: |
| load_flags |= net::LOAD_ONLY_FROM_CACHE | net::LOAD_BYPASS_CACHE; |
| break; |
| } |
| |
| if (resource_request_->GetRequestContext() == |
| blink::mojom::blink::RequestContextType::PREFETCH) |
| load_flags |= net::LOAD_PREFETCH; |
| |
| if (resource_request_->GetURLRequestExtraData()) { |
| if (resource_request_->GetURLRequestExtraData()->is_for_no_state_prefetch()) |
| load_flags |= net::LOAD_PREFETCH; |
| } |
| if (resource_request_->AllowsStaleResponse()) { |
| load_flags |= net::LOAD_SUPPORT_ASYNC_REVALIDATION; |
| } |
| if (resource_request_->PrefetchMaybeForTopLevelNavigation()) { |
| CHECK_EQ(resource_request_->GetRequestContext(), |
| blink::mojom::blink::RequestContextType::PREFETCH); |
| if (!resource_request_->RequestorOrigin()->IsSameOriginWith( |
| SecurityOrigin::Create(resource_request_->Url()).get())) { |
| load_flags |= net::LOAD_RESTRICTED_PREFETCH_FOR_MAIN_FRAME; |
| } |
| } |
| |
| return load_flags; |
| } |
| |
| const ResourceRequest& WebURLRequest::ToResourceRequest() const { |
| DCHECK(resource_request_); |
| return *resource_request_; |
| } |
| |
| std::optional<WebString> WebURLRequest::GetDevToolsId() const { |
| return resource_request_->GetDevToolsId(); |
| } |
| |
| bool WebURLRequest::IsFromOriginDirtyStyleSheet() const { |
| return resource_request_->IsFromOriginDirtyStyleSheet(); |
| } |
| |
| std::optional<base::UnguessableToken> WebURLRequest::RecursivePrefetchToken() |
| const { |
| return resource_request_->RecursivePrefetchToken(); |
| } |
| |
| network::OptionalTrustTokenParams WebURLRequest::TrustTokenParams() const { |
| return ConvertTrustTokenParams(resource_request_->TrustTokenParams()); |
| } |
| |
| std::optional<WebURL> WebURLRequest::WebBundleUrl() const { |
| if (resource_request_->GetWebBundleTokenParams()) { |
| return resource_request_->GetWebBundleTokenParams()->bundle_url; |
| } |
| return std::nullopt; |
| } |
| |
| std::optional<base::UnguessableToken> WebURLRequest::WebBundleToken() const { |
| if (resource_request_->GetWebBundleTokenParams()) { |
| return resource_request_->GetWebBundleTokenParams()->token; |
| } |
| return std::nullopt; |
| } |
| |
| WebURLRequest::WebURLRequest(ResourceRequest& r) : resource_request_(&r) {} |
| |
| } // namespace blink |