Backed out 5 changesets (bug 1351231) for causing fetch related failures. CLOSED TREE
Backed out changeset da5c4a821428 (bug 1351231) Backed out changeset 66b279e5a513 (bug 1351231) Backed out changeset 3eb8fdd0ba6d (bug 1351231) Backed out changeset a1fcf22a2a0e (bug 1351231) Backed out changeset fd2a843599d1 (bug 1351231)
This commit is contained in:
@@ -3,9 +3,7 @@
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "FetchLog.h"
|
||||
#include "FetchParent.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsIContentSecurityPolicy.h"
|
||||
#include "nsICookieJarSettings.h"
|
||||
#include "nsILoadGroup.h"
|
||||
#include "nsILoadInfo.h"
|
||||
@@ -18,18 +16,14 @@
|
||||
#include "nsXULAppAPI.h"
|
||||
#include "mozilla/BasePrincipal.h"
|
||||
#include "mozilla/ClearOnShutdown.h"
|
||||
#include "mozilla/SchedulerGroup.h"
|
||||
#include "mozilla/ScopeExit.h"
|
||||
#include "mozilla/UniquePtr.h"
|
||||
#include "mozilla/dom/ClientInfo.h"
|
||||
#include "mozilla/dom/FetchService.h"
|
||||
#include "mozilla/dom/InternalRequest.h"
|
||||
#include "mozilla/dom/InternalResponse.h"
|
||||
#include "mozilla/dom/PerformanceStorage.h"
|
||||
#include "mozilla/dom/PerformanceTiming.h"
|
||||
#include "mozilla/dom/ServiceWorkerDescriptor.h"
|
||||
#include "mozilla/ipc/BackgroundUtils.h"
|
||||
#include "mozilla/net/CookieJarSettings.h"
|
||||
|
||||
namespace mozilla::dom {
|
||||
|
||||
@@ -39,9 +33,8 @@ mozilla::LazyLogModule gFetchLog("Fetch");
|
||||
|
||||
FetchServicePromises::FetchServicePromises()
|
||||
: mAvailablePromise(
|
||||
MakeRefPtr<FetchServiceResponseAvailablePromise::Private>(__func__)),
|
||||
mEndPromise(
|
||||
MakeRefPtr<FetchServiceResponseEndPromise::Private>(__func__)) {
|
||||
new FetchServiceResponseAvailablePromise::Private(__func__)),
|
||||
mEndPromise(new FetchServiceResponseEndPromise::Private(__func__)) {
|
||||
mAvailablePromise->UseSynchronousTaskDispatch(__func__);
|
||||
mEndPromise->UseSynchronousTaskDispatch(__func__);
|
||||
}
|
||||
@@ -86,26 +79,25 @@ void FetchServicePromises::RejectResponseEndPromise(
|
||||
|
||||
// FetchInstance
|
||||
|
||||
nsresult FetchService::FetchInstance::Initialize(FetchArgs&& aArgs) {
|
||||
FetchService::FetchInstance::FetchInstance(SafeRefPtr<InternalRequest> aRequest)
|
||||
: mRequest(std::move(aRequest)) {}
|
||||
|
||||
FetchService::FetchInstance::~FetchInstance() = default;
|
||||
|
||||
nsresult FetchService::FetchInstance::Initialize(nsIChannel* aChannel) {
|
||||
MOZ_ASSERT(XRE_IsParentProcess());
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
MOZ_ASSERT(!aArgs.is<UnknownArgs>() && mArgs.is<UnknownArgs>());
|
||||
|
||||
mArgs = std::move(aArgs);
|
||||
|
||||
// Get needed information for FetchDriver from passed-in channel.
|
||||
if (mArgs.is<NavigationPreloadArgs>()) {
|
||||
mRequest = mArgs.as<NavigationPreloadArgs>().mRequest.clonePtr();
|
||||
nsIChannel* channel = mArgs.as<NavigationPreloadArgs>().mChannel;
|
||||
FETCH_LOG(("FetchInstance::Initialize [%p] request[%p], channel[%p]", this,
|
||||
mRequest.unsafeGetRawPtr(), channel));
|
||||
if (aChannel) {
|
||||
FETCH_LOG(("FetchInstance::Initialize [%p] aChannel[%p]", this, aChannel));
|
||||
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsILoadInfo> loadInfo = channel->LoadInfo();
|
||||
nsCOMPtr<nsILoadInfo> loadInfo = aChannel->LoadInfo();
|
||||
MOZ_ASSERT(loadInfo);
|
||||
|
||||
nsCOMPtr<nsIURI> channelURI;
|
||||
rv = channel->GetURI(getter_AddRefs(channelURI));
|
||||
rv = aChannel->GetURI(getter_AddRefs(channelURI));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
@@ -113,7 +105,7 @@ nsresult FetchService::FetchInstance::Initialize(FetchArgs&& aArgs) {
|
||||
nsIScriptSecurityManager* securityManager =
|
||||
nsContentUtils::GetSecurityManager();
|
||||
if (securityManager) {
|
||||
securityManager->GetChannelResultPrincipal(channel,
|
||||
securityManager->GetChannelResultPrincipal(aChannel,
|
||||
getter_AddRefs(mPrincipal));
|
||||
}
|
||||
|
||||
@@ -122,7 +114,7 @@ nsresult FetchService::FetchInstance::Initialize(FetchArgs&& aArgs) {
|
||||
}
|
||||
|
||||
// Get loadGroup from channel
|
||||
rv = channel->GetLoadGroup(getter_AddRefs(mLoadGroup));
|
||||
rv = aChannel->GetLoadGroup(getter_AddRefs(mLoadGroup));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
@@ -142,28 +134,10 @@ nsresult FetchService::FetchInstance::Initialize(FetchArgs&& aArgs) {
|
||||
// Get PerformanceStorage from channel
|
||||
mPerformanceStorage = loadInfo->GetPerformanceStorage();
|
||||
} else {
|
||||
mIsWorkerFetch = true;
|
||||
mRequest = mArgs.as<WorkerFetchArgs>().mRequest.clonePtr();
|
||||
|
||||
FETCH_LOG(("FetchInstance::Initialize [%p] request[%p]", this,
|
||||
mRequest.unsafeGetRawPtr()));
|
||||
|
||||
auto principalOrErr =
|
||||
PrincipalInfoToPrincipal(mArgs.as<WorkerFetchArgs>().mPrincipalInfo);
|
||||
if (principalOrErr.isErr()) {
|
||||
return principalOrErr.unwrapErr();
|
||||
}
|
||||
mPrincipal = principalOrErr.unwrap();
|
||||
nsresult rv = NS_NewLoadGroup(getter_AddRefs(mLoadGroup), mPrincipal);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (mArgs.as<WorkerFetchArgs>().mCookieJarSettings.isSome()) {
|
||||
net::CookieJarSettings::Deserialize(
|
||||
mArgs.as<WorkerFetchArgs>().mCookieJarSettings.ref(),
|
||||
getter_AddRefs(mCookieJarSettings));
|
||||
}
|
||||
// TODO:
|
||||
// Get information from InternalRequest and PFetch IPC parameters.
|
||||
// This will be implemented in bug 1351231.
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
@@ -196,21 +170,6 @@ RefPtr<FetchServicePromises> FetchService::FetchInstance::Fetch() {
|
||||
false // IsTrackingFetch
|
||||
);
|
||||
|
||||
if (mIsWorkerFetch) {
|
||||
auto& args = mArgs.as<WorkerFetchArgs>();
|
||||
mFetchDriver->SetWorkerScript(args.mWorkerScript);
|
||||
MOZ_ASSERT(args.mClientInfo.isSome());
|
||||
mFetchDriver->SetClientInfo(args.mClientInfo.ref());
|
||||
mFetchDriver->SetController(args.mController);
|
||||
if (args.mCSPEventListener) {
|
||||
mFetchDriver->SetCSPEventListener(args.mCSPEventListener);
|
||||
}
|
||||
}
|
||||
|
||||
mFetchDriver->EnableNetworkInterceptControl();
|
||||
|
||||
mPromises = MakeRefPtr<FetchServicePromises>();
|
||||
|
||||
// Call FetchDriver::Fetch to start fetching.
|
||||
// Pass AbortSignalImpl as nullptr since we no need support AbortSignalImpl
|
||||
// with FetchService. AbortSignalImpl related information should be passed
|
||||
@@ -223,6 +182,8 @@ RefPtr<FetchServicePromises> FetchService::FetchInstance::Fetch() {
|
||||
return FetchService::NetworkErrorResponse(rv);
|
||||
}
|
||||
|
||||
mPromises = MakeRefPtr<FetchServicePromises>();
|
||||
|
||||
return mPromises;
|
||||
}
|
||||
|
||||
@@ -236,155 +197,74 @@ void FetchService::FetchInstance::Cancel() {
|
||||
mFetchDriver->RunAbortAlgorithm();
|
||||
}
|
||||
|
||||
MOZ_ASSERT(mPromises);
|
||||
if (mPromises) {
|
||||
mPromises->ResolveResponseAvailablePromise(
|
||||
InternalResponse::NetworkError(NS_ERROR_DOM_ABORT_ERR), __func__);
|
||||
|
||||
mPromises->ResolveResponseAvailablePromise(
|
||||
InternalResponse::NetworkError(NS_ERROR_DOM_ABORT_ERR), __func__);
|
||||
|
||||
mPromises->ResolveResponseEndPromise(
|
||||
ResponseEndArgs(FetchDriverObserver::eAborted, Nothing()), __func__);
|
||||
mPromises->ResolveResponseEndPromise(
|
||||
ResponseEndArgs(FetchDriverObserver::eAborted, Nothing()), __func__);
|
||||
mPromises = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
void FetchService::FetchInstance::OnResponseEnd(
|
||||
FetchDriverObserver::EndReason aReason,
|
||||
JS::Handle<JS::Value> aReasonDetails) {
|
||||
FETCH_LOG(("FetchInstance::OnResponseEnd [%p] %s", this,
|
||||
aReason == eAborted ? "eAborted" : "eNetworking"));
|
||||
|
||||
// Get response timing form FetchDriver
|
||||
Maybe<ResponseTiming> responseTiming;
|
||||
ResponseTiming timing;
|
||||
UniquePtr<PerformanceTimingData> performanceTiming(
|
||||
mFetchDriver->GetPerformanceTimingData(timing.initiatorType(),
|
||||
timing.entryName()));
|
||||
if (performanceTiming != nullptr) {
|
||||
timing.timingData() = performanceTiming->ToIPC();
|
||||
if (!mIsWorkerFetch) {
|
||||
// Force replace initiatorType for ServiceWorkerNavgationPreload.
|
||||
timing.initiatorType() = u"navigation"_ns;
|
||||
}
|
||||
responseTiming = Some(timing);
|
||||
}
|
||||
|
||||
if (mIsWorkerFetch) {
|
||||
FlushConsoleReport();
|
||||
nsCOMPtr<nsIRunnable> r = NS_NewRunnableFunction(
|
||||
__func__, [endArgs = ResponseEndArgs(aReason, responseTiming),
|
||||
actorID = mArgs.as<WorkerFetchArgs>().mActorID]() {
|
||||
FETCH_LOG(("FetchParent::OnResponseEnd, Runnable"));
|
||||
RefPtr<FetchParent> actor = FetchParent::GetActorByID(actorID);
|
||||
if (actor) {
|
||||
actor->OnResponseEnd(std::move(endArgs));
|
||||
}
|
||||
});
|
||||
MOZ_ALWAYS_SUCCEEDS(mArgs.as<WorkerFetchArgs>().mEventTarget->Dispatch(
|
||||
r, nsIThread::DISPATCH_NORMAL));
|
||||
}
|
||||
|
||||
MOZ_ASSERT(mPromises);
|
||||
|
||||
// Resolve the ResponseEndPromise
|
||||
mPromises->ResolveResponseEndPromise(ResponseEndArgs(aReason, responseTiming),
|
||||
__func__);
|
||||
|
||||
FETCH_LOG(("FetchInstance::OnResponseEnd [%p]", this));
|
||||
if (aReason == eAborted) {
|
||||
FETCH_LOG(("FetchInstance::OnResponseEnd end with eAborted"));
|
||||
if (mPromises) {
|
||||
mPromises->ResolveResponseEndPromise(
|
||||
ResponseEndArgs(FetchDriverObserver::eAborted, Nothing()), __func__);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
// Remove the FetchInstance from FetchInstanceTable
|
||||
RefPtr<FetchService> fetchService = FetchService::GetInstance();
|
||||
MOZ_ASSERT(fetchService);
|
||||
auto entry = fetchService->mFetchInstanceTable.Lookup(mPromises);
|
||||
if (entry) {
|
||||
if (mPromises) {
|
||||
// Remove the FetchInstance from FetchInstanceTable
|
||||
RefPtr<FetchService> fetchService = FetchService::GetInstance();
|
||||
MOZ_ASSERT(fetchService);
|
||||
auto entry = fetchService->mFetchInstanceTable.Lookup(mPromises);
|
||||
MOZ_ASSERT(entry);
|
||||
entry.Remove();
|
||||
FETCH_LOG(
|
||||
("FetchInstance::OnResponseEnd entry of responsePromise[%p] is "
|
||||
("FetchInstance::OnResponseEnd entry[%p] of FetchInstance[%p] is "
|
||||
"removed",
|
||||
mPromises.get()));
|
||||
mPromises.get(), this));
|
||||
|
||||
// Get PerformanceTimingData from FetchDriver.
|
||||
ResponseTiming timing;
|
||||
UniquePtr<PerformanceTimingData> performanceTiming(
|
||||
mFetchDriver->GetPerformanceTimingData(timing.initiatorType(),
|
||||
timing.entryName()));
|
||||
if (performanceTiming != nullptr) {
|
||||
timing.timingData() = performanceTiming->ToIPC();
|
||||
}
|
||||
|
||||
timing.initiatorType() = u"navigation"_ns;
|
||||
|
||||
// Resolve the ResponseEndPromise
|
||||
mPromises->ResolveResponseEndPromise(ResponseEndArgs(aReason, Some(timing)),
|
||||
__func__);
|
||||
// Release promises
|
||||
mPromises = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
void FetchService::FetchInstance::OnResponseAvailableInternal(
|
||||
SafeRefPtr<InternalResponse> aResponse) {
|
||||
FETCH_LOG(("FetchInstance::OnResponseAvailableInternal [%p]", this));
|
||||
mResponse = std::move(aResponse);
|
||||
|
||||
nsCOMPtr<nsIInputStream> body;
|
||||
mResponse->GetUnfilteredBody(getter_AddRefs(body));
|
||||
FETCH_LOG(
|
||||
("FetchInstance::OnResponseAvailableInternal [%p] response body: %p",
|
||||
this, body.get()));
|
||||
|
||||
if (mIsWorkerFetch) {
|
||||
nsCOMPtr<nsIRunnable> r = NS_NewRunnableFunction(
|
||||
__func__, [response = mResponse.clonePtr(),
|
||||
actorID = mArgs.as<WorkerFetchArgs>().mActorID]() mutable {
|
||||
FETCH_LOG(("FetchInstance::OnResponseAvailableInternal Runnable"));
|
||||
RefPtr<FetchParent> actor = FetchParent::GetActorByID(actorID);
|
||||
if (actor) {
|
||||
actor->OnResponseAvailableInternal(std::move(response));
|
||||
}
|
||||
});
|
||||
MOZ_ALWAYS_SUCCEEDS(mArgs.as<WorkerFetchArgs>().mEventTarget->Dispatch(
|
||||
r, nsIThread::DISPATCH_NORMAL));
|
||||
}
|
||||
|
||||
MOZ_ASSERT(mPromises);
|
||||
|
||||
// Resolve the ResponseAvailablePromise
|
||||
mPromises->ResolveResponseAvailablePromise(mResponse.clonePtr(), __func__);
|
||||
}
|
||||
|
||||
bool FetchService::FetchInstance::NeedOnDataAvailable() {
|
||||
if (mArgs.is<WorkerFetchArgs>()) {
|
||||
return mArgs.as<WorkerFetchArgs>().mNeedOnDataAvailable;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void FetchService::FetchInstance::OnDataAvailable() {
|
||||
FETCH_LOG(("FetchInstance::OnDataAvailable [%p]", this));
|
||||
|
||||
if (!NeedOnDataAvailable()) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mIsWorkerFetch) {
|
||||
nsCOMPtr<nsIRunnable> r = NS_NewRunnableFunction(
|
||||
__func__, [actorID = mArgs.as<WorkerFetchArgs>().mActorID]() {
|
||||
FETCH_LOG(("FetchParent::OnDataAvailable, Runnable"));
|
||||
RefPtr<FetchParent> actor = FetchParent::GetActorByID(actorID);
|
||||
if (actor) {
|
||||
actor->OnDataAvailable();
|
||||
}
|
||||
});
|
||||
MOZ_ALWAYS_SUCCEEDS(mArgs.as<WorkerFetchArgs>().mEventTarget->Dispatch(
|
||||
r, nsIThread::DISPATCH_NORMAL));
|
||||
if (mPromises) {
|
||||
// Resolve the ResponseAvailablePromise
|
||||
mPromises->ResolveResponseAvailablePromise(std::move(aResponse), __func__);
|
||||
}
|
||||
}
|
||||
|
||||
void FetchService::FetchInstance::FlushConsoleReport() {
|
||||
FETCH_LOG(("FetchInstance::FlushConsoleReport [%p]", this));
|
||||
|
||||
if (mIsWorkerFetch) {
|
||||
if (!mReporter) {
|
||||
return;
|
||||
}
|
||||
nsTArray<net::ConsoleReportCollected> reports;
|
||||
mReporter->StealConsoleReports(reports);
|
||||
nsCOMPtr<nsIRunnable> r = NS_NewRunnableFunction(
|
||||
__func__, [actorID = mArgs.as<WorkerFetchArgs>().mActorID,
|
||||
consoleReports = std::move(reports)]() {
|
||||
FETCH_LOG(("FetchParent::FlushConsolReport, Runnable"));
|
||||
RefPtr<FetchParent> actor = FetchParent::GetActorByID(actorID);
|
||||
if (actor) {
|
||||
actor->OnFlushConsoleReport(std::move(consoleReports));
|
||||
}
|
||||
});
|
||||
MOZ_ALWAYS_SUCCEEDS(mArgs.as<WorkerFetchArgs>().mEventTarget->Dispatch(
|
||||
r, nsIThread::DISPATCH_NORMAL));
|
||||
}
|
||||
}
|
||||
// TODO:
|
||||
// Following methods would not be used for navigation preload, but would be used
|
||||
// with PFetch. They will be implemented in bug 1351231.
|
||||
bool FetchService::FetchInstance::NeedOnDataAvailable() { return false; }
|
||||
void FetchService::FetchInstance::OnDataAvailable() {}
|
||||
void FetchService::FetchInstance::FlushConsoleReport() {}
|
||||
|
||||
// FetchService
|
||||
|
||||
@@ -502,30 +382,31 @@ NS_IMETHODIMP FetchService::Observe(nsISupports* aSubject, const char* aTopic,
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
RefPtr<FetchServicePromises> FetchService::Fetch(FetchArgs&& aArgs) {
|
||||
RefPtr<FetchServicePromises> FetchService::Fetch(
|
||||
SafeRefPtr<InternalRequest> aRequest, nsIChannel* aChannel) {
|
||||
MOZ_ASSERT(XRE_IsParentProcess());
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
FETCH_LOG(("FetchService::Fetch (%s)", aArgs.is<NavigationPreloadArgs>()
|
||||
? "NavigationPreload"
|
||||
: "WorkerFetch"));
|
||||
FETCH_LOG(("FetchService::Fetch aRequest[%p], aChannel[%p], mOffline: %s",
|
||||
aRequest.unsafeGetRawPtr(), aChannel,
|
||||
mOffline ? "true" : "false"));
|
||||
|
||||
if (mOffline) {
|
||||
FETCH_LOG(("FetchService::Fetch network offline"));
|
||||
return NetworkErrorResponse(NS_ERROR_OFFLINE);
|
||||
}
|
||||
|
||||
// Create FetchInstance
|
||||
RefPtr<FetchInstance> fetch = MakeRefPtr<FetchInstance>();
|
||||
RefPtr<FetchInstance> fetch = MakeRefPtr<FetchInstance>(aRequest.clonePtr());
|
||||
|
||||
// Call FetchInstance::Initialize() to get needed information for FetchDriver,
|
||||
nsresult rv = fetch->Initialize(std::move(aArgs));
|
||||
nsresult rv = fetch->Initialize(aChannel);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return NetworkErrorResponse(rv);
|
||||
}
|
||||
|
||||
// Call FetchInstance::Fetch() to start an asynchronous fetching.
|
||||
RefPtr<FetchServicePromises> promises = fetch->Fetch();
|
||||
MOZ_ASSERT(promises);
|
||||
|
||||
if (!promises->GetResponseAvailablePromise()->IsResolved()) {
|
||||
// Insert the created FetchInstance into FetchInstanceTable.
|
||||
@@ -546,7 +427,7 @@ RefPtr<FetchServicePromises> FetchService::Fetch(FetchArgs&& aArgs) {
|
||||
return promises;
|
||||
}
|
||||
|
||||
void FetchService::CancelFetch(const RefPtr<FetchServicePromises>&& aPromises) {
|
||||
void FetchService::CancelFetch(RefPtr<FetchServicePromises>&& aPromises) {
|
||||
MOZ_ASSERT(XRE_IsParentProcess());
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
MOZ_ASSERT(aPromises);
|
||||
@@ -557,6 +438,7 @@ void FetchService::CancelFetch(const RefPtr<FetchServicePromises>&& aPromises) {
|
||||
// Notice any modifications here before entry.Remove() probably should be
|
||||
// reflected to Observe() offline case.
|
||||
entry.Data()->Cancel();
|
||||
|
||||
entry.Remove();
|
||||
FETCH_LOG(
|
||||
("FetchService::CancelFetch entry [%p] removed", aPromises.get()));
|
||||
|
||||
Reference in New Issue
Block a user