зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1187335 - P4 - Integrate fetch and cache with SRI & add nsIConsoleReportCollector to show console report. r=bkelly.
This commit is contained in:
Родитель
6f314fb375
Коммит
a167b66e90
|
@ -60,6 +60,7 @@ MSG_DEF(MSG_INVALID_HEADER_VALUE, 1, JSEXN_TYPEERR, "{0} is an invalid header va
|
|||
MSG_DEF(MSG_INVALID_HEADER_SEQUENCE, 0, JSEXN_TYPEERR, "Headers require name/value tuples when being initialized by a sequence.")
|
||||
MSG_DEF(MSG_PERMISSION_DENIED_TO_PASS_ARG, 1, JSEXN_TYPEERR, "Permission denied to pass cross-origin object as {0}.")
|
||||
MSG_DEF(MSG_MISSING_REQUIRED_DICTIONARY_MEMBER, 1, JSEXN_TYPEERR, "Missing required {0}.")
|
||||
MSG_DEF(MSG_REQUEST_INTEGRITY_METADATA_NOT_EMPTY, 0, JSEXN_TYPEERR, "Request integrity metadata should be an empty string when in no-cors mode.")
|
||||
MSG_DEF(MSG_INVALID_REQUEST_METHOD, 1, JSEXN_TYPEERR, "Invalid request method {0}.")
|
||||
MSG_DEF(MSG_INVALID_REQUEST_MODE, 1, JSEXN_TYPEERR, "Invalid request mode {0}.")
|
||||
MSG_DEF(MSG_INVALID_REFERRER_URL, 1, JSEXN_TYPEERR, "Invalid referrer URL {0}.")
|
||||
|
|
|
@ -66,6 +66,7 @@ struct CacheRequest
|
|||
uint32_t contentPolicyType;
|
||||
RequestCache requestCache;
|
||||
RequestRedirect requestRedirect;
|
||||
nsString integrity;
|
||||
};
|
||||
|
||||
union CacheRequestOrVoid
|
||||
|
|
|
@ -38,7 +38,7 @@ const int32_t kFirstShippedSchemaVersion = 15;
|
|||
namespace {
|
||||
|
||||
// Update this whenever the DB schema is changed.
|
||||
const int32_t kLatestSchemaVersion = 21;
|
||||
const int32_t kLatestSchemaVersion = 22;
|
||||
|
||||
// ---------
|
||||
// The following constants define the SQL schema. These are defined in the
|
||||
|
@ -105,7 +105,8 @@ const char* const kTableEntries =
|
|||
"cache_id INTEGER NOT NULL REFERENCES caches(id) ON DELETE CASCADE, "
|
||||
|
||||
"request_redirect INTEGER NOT NULL, "
|
||||
"request_referrer_policy INTEGER NOT NULL"
|
||||
"request_referrer_policy INTEGER NOT NULL, "
|
||||
"request_integrity TEXT NOT NULL"
|
||||
// New columns must be added at the end of table to migrate and
|
||||
// validate properly.
|
||||
")";
|
||||
|
@ -1661,6 +1662,7 @@ InsertEntry(mozIStorageConnection* aConn, CacheId aCacheId,
|
|||
"request_contentpolicytype, "
|
||||
"request_cache, "
|
||||
"request_redirect, "
|
||||
"request_integrity, "
|
||||
"request_body_id, "
|
||||
"response_type, "
|
||||
"response_status, "
|
||||
|
@ -1684,6 +1686,7 @@ InsertEntry(mozIStorageConnection* aConn, CacheId aCacheId,
|
|||
":request_contentpolicytype, "
|
||||
":request_cache, "
|
||||
":request_redirect, "
|
||||
":request_integrity, "
|
||||
":request_body_id, "
|
||||
":response_type, "
|
||||
":response_status, "
|
||||
|
@ -1756,6 +1759,9 @@ InsertEntry(mozIStorageConnection* aConn, CacheId aCacheId,
|
|||
rv = state->BindInt32ByName(NS_LITERAL_CSTRING("request_redirect"),
|
||||
static_cast<int32_t>(aRequest.requestRedirect()));
|
||||
|
||||
rv = state->BindStringByName(NS_LITERAL_CSTRING("request_integrity"),
|
||||
aRequest.integrity());
|
||||
|
||||
rv = BindId(state, NS_LITERAL_CSTRING("request_body_id"), aRequestBodyId);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) { return rv; }
|
||||
|
||||
|
@ -2051,6 +2057,7 @@ ReadRequest(mozIStorageConnection* aConn, EntryId aEntryId,
|
|||
"request_contentpolicytype, "
|
||||
"request_cache, "
|
||||
"request_redirect, "
|
||||
"request_integrity, "
|
||||
"request_body_id "
|
||||
"FROM entries "
|
||||
"WHERE id=:id;"
|
||||
|
@ -2117,13 +2124,16 @@ ReadRequest(mozIStorageConnection* aConn, EntryId aEntryId,
|
|||
aSavedRequestOut->mValue.requestRedirect() =
|
||||
static_cast<RequestRedirect>(requestRedirect);
|
||||
|
||||
rv = state->GetString(11, aSavedRequestOut->mValue.integrity());
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) { return rv; }
|
||||
|
||||
bool nullBody = false;
|
||||
rv = state->GetIsNull(11, &nullBody);
|
||||
rv = state->GetIsNull(12, &nullBody);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) { return rv; }
|
||||
aSavedRequestOut->mHasBodyId = !nullBody;
|
||||
|
||||
if (aSavedRequestOut->mHasBodyId) {
|
||||
rv = ExtractId(state, 11, &aSavedRequestOut->mBodyId);
|
||||
rv = ExtractId(state, 12, &aSavedRequestOut->mBodyId);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) { return rv; }
|
||||
}
|
||||
|
||||
|
@ -2479,6 +2489,7 @@ nsresult MigrateFrom17To18(mozIStorageConnection* aConn, bool& aRewriteSchema);
|
|||
nsresult MigrateFrom18To19(mozIStorageConnection* aConn, bool& aRewriteSchema);
|
||||
nsresult MigrateFrom19To20(mozIStorageConnection* aConn, bool& aRewriteSchema);
|
||||
nsresult MigrateFrom20To21(mozIStorageConnection* aConn, bool& aRewriteSchema);
|
||||
nsresult MigrateFrom21To22(mozIStorageConnection* aConn, bool& aRewriteSchema);
|
||||
|
||||
// Configure migration functions to run for the given starting version.
|
||||
Migration sMigrationList[] = {
|
||||
|
@ -2488,6 +2499,7 @@ Migration sMigrationList[] = {
|
|||
Migration(18, MigrateFrom18To19),
|
||||
Migration(19, MigrateFrom19To20),
|
||||
Migration(20, MigrateFrom20To21),
|
||||
Migration(21, MigrateFrom21To22),
|
||||
};
|
||||
|
||||
uint32_t sMigrationListLength = sizeof(sMigrationList) / sizeof(Migration);
|
||||
|
@ -2959,6 +2971,26 @@ nsresult MigrateFrom20To21(mozIStorageConnection* aConn, bool& aRewriteSchema)
|
|||
return rv;
|
||||
}
|
||||
|
||||
nsresult MigrateFrom21To22(mozIStorageConnection* aConn, bool& aRewriteSchema)
|
||||
{
|
||||
MOZ_ASSERT(!NS_IsMainThread());
|
||||
MOZ_ASSERT(aConn);
|
||||
|
||||
// Add the request_integrity column.
|
||||
nsresult rv = aConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||
"ALTER TABLE entries "
|
||||
"ADD COLUMN request_integrity TEXT NULL"
|
||||
));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) { return rv; }
|
||||
|
||||
rv = aConn->SetSchemaVersion(22);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) { return rv; }
|
||||
|
||||
aRewriteSchema = true;
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
} // anonymous namespace
|
||||
|
||||
} // namespace db
|
||||
|
|
|
@ -159,6 +159,8 @@ TypeUtils::ToCacheRequest(CacheRequest& aOut, InternalRequest* aIn,
|
|||
aOut.requestCache() = aIn->GetCacheMode();
|
||||
aOut.requestRedirect() = aIn->GetRedirectMode();
|
||||
|
||||
aOut.integrity() = aIn->GetIntegrity();
|
||||
|
||||
if (aBodyAction == IgnoreBody) {
|
||||
aOut.body() = void_t();
|
||||
return;
|
||||
|
@ -325,6 +327,7 @@ TypeUtils::ToInternalRequest(const CacheRequest& aIn)
|
|||
internalRequest->SetContentPolicyType(aIn.contentPolicyType());
|
||||
internalRequest->SetCacheMode(aIn.requestCache());
|
||||
internalRequest->SetRedirectMode(aIn.requestRedirect());
|
||||
internalRequest->SetIntegrity(aIn.integrity());
|
||||
|
||||
RefPtr<InternalHeaders> internalHeaders =
|
||||
ToInternalHeaders(aIn.headers(), aIn.headersGuard());
|
||||
|
|
|
@ -34,6 +34,7 @@
|
|||
#include "mozilla/dom/Response.h"
|
||||
#include "mozilla/dom/ScriptSettings.h"
|
||||
#include "mozilla/dom/URLSearchParams.h"
|
||||
#include "mozilla/dom/workers/ServiceWorkerManager.h"
|
||||
#include "mozilla/Telemetry.h"
|
||||
|
||||
#include "InternalRequest.h"
|
||||
|
@ -88,6 +89,9 @@ private:
|
|||
|
||||
~WorkerFetchResolver()
|
||||
{}
|
||||
|
||||
virtual void
|
||||
FlushConsoleReport() override;
|
||||
};
|
||||
|
||||
class MainThreadFetchResolver final : public FetchDriverObserver
|
||||
|
@ -95,6 +99,8 @@ class MainThreadFetchResolver final : public FetchDriverObserver
|
|||
RefPtr<Promise> mPromise;
|
||||
RefPtr<Response> mResponse;
|
||||
|
||||
nsCOMPtr<nsIDocument> mDocument;
|
||||
|
||||
NS_DECL_OWNINGTHREAD
|
||||
public:
|
||||
explicit MainThreadFetchResolver(Promise* aPromise);
|
||||
|
@ -102,8 +108,23 @@ public:
|
|||
void
|
||||
OnResponseAvailableInternal(InternalResponse* aResponse) override;
|
||||
|
||||
void SetDocument(nsIDocument* aDocument)
|
||||
{
|
||||
mDocument = aDocument;
|
||||
}
|
||||
|
||||
virtual void OnResponseEnd() override
|
||||
{
|
||||
FlushConsoleReport();
|
||||
}
|
||||
|
||||
private:
|
||||
~MainThreadFetchResolver();
|
||||
|
||||
void FlushConsoleReport() override
|
||||
{
|
||||
mReporter->FlushConsoleReports(mDocument);
|
||||
}
|
||||
};
|
||||
|
||||
class MainThreadFetchRunnable : public Runnable
|
||||
|
@ -140,6 +161,11 @@ public:
|
|||
nsCOMPtr<nsILoadGroup> loadGroup = proxy->GetWorkerPrivate()->GetLoadGroup();
|
||||
MOZ_ASSERT(loadGroup);
|
||||
fetch = new FetchDriver(mRequest, principal, loadGroup);
|
||||
nsAutoCString spec;
|
||||
if (proxy->GetWorkerPrivate()->GetBaseURI()) {
|
||||
proxy->GetWorkerPrivate()->GetBaseURI()->GetAsciiSpec(spec);
|
||||
}
|
||||
fetch->SetWorkerScript(spec);
|
||||
}
|
||||
|
||||
// ...but release it before calling Fetch, because mResolver's callback can
|
||||
|
@ -216,6 +242,7 @@ FetchRequest(nsIGlobalObject* aGlobal, const RequestOrUSVString& aInput,
|
|||
RefPtr<MainThreadFetchResolver> resolver = new MainThreadFetchResolver(p);
|
||||
RefPtr<FetchDriver> fetch = new FetchDriver(r, principal, loadGroup);
|
||||
fetch->SetDocument(doc);
|
||||
resolver->SetDocument(doc);
|
||||
aRv = fetch->Fetch(resolver);
|
||||
if (NS_WARN_IF(aRv.Failed())) {
|
||||
return nullptr;
|
||||
|
@ -401,6 +428,8 @@ WorkerFetchResolver::OnResponseEnd()
|
|||
return;
|
||||
}
|
||||
|
||||
FlushConsoleReport();
|
||||
|
||||
RefPtr<WorkerFetchResponseEndRunnable> r =
|
||||
new WorkerFetchResponseEndRunnable(mPromiseProxy);
|
||||
|
||||
|
@ -416,6 +445,44 @@ WorkerFetchResolver::OnResponseEnd()
|
|||
}
|
||||
}
|
||||
|
||||
void
|
||||
WorkerFetchResolver::FlushConsoleReport()
|
||||
{
|
||||
AssertIsOnMainThread();
|
||||
MOZ_ASSERT(mPromiseProxy);
|
||||
|
||||
if(!mReporter) {
|
||||
return;
|
||||
}
|
||||
|
||||
workers::WorkerPrivate* worker = mPromiseProxy->GetWorkerPrivate();
|
||||
if (!worker) {
|
||||
mReporter->FlushConsoleReports((nsIDocument*)nullptr);
|
||||
return;
|
||||
}
|
||||
|
||||
if (worker->IsServiceWorker()) {
|
||||
// Flush to service worker
|
||||
RefPtr<ServiceWorkerManager> swm = ServiceWorkerManager::GetInstance();
|
||||
if (!swm) {
|
||||
mReporter->FlushConsoleReports((nsIDocument*)nullptr);
|
||||
return;
|
||||
}
|
||||
|
||||
swm->FlushReportsToAllClients(worker->WorkerName(), mReporter);
|
||||
return;
|
||||
}
|
||||
|
||||
if (worker->IsSharedWorker()) {
|
||||
// Flush to shared worker
|
||||
worker->FlushReportsToSharedWorkers(mReporter);
|
||||
return;
|
||||
}
|
||||
|
||||
// Flush to dedicated worker
|
||||
mReporter->FlushConsoleReports(worker->GetDocument());
|
||||
}
|
||||
|
||||
namespace {
|
||||
nsresult
|
||||
ExtractFromArrayBuffer(const ArrayBuffer& aBuffer,
|
||||
|
|
|
@ -319,6 +319,7 @@ FetchDriver::HttpFetch()
|
|||
internalChan->SetRedirectMode(static_cast<uint32_t>(mRequest->GetRedirectMode()));
|
||||
mRequest->MaybeSkipCacheIfPerformingRevalidation();
|
||||
internalChan->SetFetchCacheMode(static_cast<uint32_t>(mRequest->GetCacheMode()));
|
||||
internalChan->SetIntegrityMetadata(mRequest->GetIntegrity());
|
||||
}
|
||||
|
||||
// Step 5. Proxy authentication will be handled by Necko.
|
||||
|
@ -397,10 +398,14 @@ FetchDriver::BeginAndGetFilteredResponse(InternalResponse* aResponse,
|
|||
|
||||
MOZ_ASSERT(filteredResponse);
|
||||
MOZ_ASSERT(mObserver);
|
||||
mObserver->OnResponseAvailable(filteredResponse);
|
||||
#ifdef DEBUG
|
||||
mResponseAvailableCalled = true;
|
||||
#endif
|
||||
if (filteredResponse->Type() == ResponseType::Error ||
|
||||
mRequest->GetIntegrity().IsEmpty()) {
|
||||
mObserver->OnResponseAvailable(filteredResponse);
|
||||
#ifdef DEBUG
|
||||
mResponseAvailableCalled = true;
|
||||
#endif
|
||||
}
|
||||
|
||||
return filteredResponse.forget();
|
||||
}
|
||||
|
||||
|
@ -598,6 +603,30 @@ FetchDriver::OnStartRequest(nsIRequest* aRequest,
|
|||
// sure the Response is fully initialized before calling this.
|
||||
mResponse = BeginAndGetFilteredResponse(response, foundOpaqueRedirect);
|
||||
|
||||
// From "Main Fetch" step 17: SRI-part1.
|
||||
if (mResponse->Type() != ResponseType::Error &&
|
||||
!mRequest->GetIntegrity().IsEmpty() &&
|
||||
mSRIMetadata.IsEmpty()) {
|
||||
nsIConsoleReportCollector* aReporter = nullptr;
|
||||
if (mObserver) {
|
||||
aReporter = mObserver->GetReporter();
|
||||
}
|
||||
|
||||
nsAutoCString sourceUri;
|
||||
if (mDocument && mDocument->GetDocumentURI()) {
|
||||
mDocument->GetDocumentURI()->GetAsciiSpec(sourceUri);
|
||||
} else if (!mWorkerScript.IsEmpty()) {
|
||||
sourceUri.Assign(mWorkerScript);
|
||||
}
|
||||
SRICheck::IntegrityMetadata(mRequest->GetIntegrity(), sourceUri,
|
||||
aReporter, &mSRIMetadata);
|
||||
mSRIDataVerifier = new SRICheckDataVerifier(mSRIMetadata, sourceUri,
|
||||
aReporter);
|
||||
|
||||
// Do not retarget off main thread when using SRI API.
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIEventTarget> sts = do_GetService(NS_STREAMTRANSPORTSERVICE_CONTRACTID, &rv);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
FailWithNetworkError();
|
||||
|
@ -627,6 +656,46 @@ FetchDriver::OnDataAvailable(nsIRequest* aRequest,
|
|||
MOZ_ASSERT(mResponse);
|
||||
MOZ_ASSERT(mPipeOutputStream);
|
||||
|
||||
// From "Main Fetch" step 17: SRI-part2.
|
||||
if (mResponse->Type() != ResponseType::Error &&
|
||||
!mRequest->GetIntegrity().IsEmpty()) {
|
||||
MOZ_ASSERT(mSRIDataVerifier);
|
||||
|
||||
uint32_t aWrite;
|
||||
nsTArray<uint8_t> buffer;
|
||||
nsresult rv;
|
||||
buffer.SetCapacity(aCount);
|
||||
while (aCount > 0) {
|
||||
rv = aInputStream->Read(reinterpret_cast<char*>(buffer.Elements()),
|
||||
aCount, &aRead);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
rv = mSRIDataVerifier->Update(aRead, (uint8_t*)buffer.Elements());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
while (aRead > 0) {
|
||||
rv = mPipeOutputStream->Write(reinterpret_cast<char*>(buffer.Elements()),
|
||||
aRead, &aWrite);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (aRead < aWrite) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
aRead -= aWrite;
|
||||
}
|
||||
|
||||
|
||||
aCount -= aWrite;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult rv = aInputStream->ReadSegments(NS_CopySegmentToStream,
|
||||
mPipeOutputStream,
|
||||
aCount, &aRead);
|
||||
|
@ -651,12 +720,49 @@ FetchDriver::OnStopRequest(nsIRequest* aRequest,
|
|||
MOZ_ASSERT(mResponse);
|
||||
MOZ_ASSERT(!mResponse->IsError());
|
||||
|
||||
// From "Main Fetch" step 17: SRI-part3.
|
||||
if (mResponse->Type() != ResponseType::Error &&
|
||||
!mRequest->GetIntegrity().IsEmpty()) {
|
||||
MOZ_ASSERT(mSRIDataVerifier);
|
||||
|
||||
nsCOMPtr<nsIChannel> channel = do_QueryInterface(aRequest);
|
||||
|
||||
nsIConsoleReportCollector* aReporter = nullptr;
|
||||
if (mObserver) {
|
||||
aReporter = mObserver->GetReporter();
|
||||
}
|
||||
|
||||
nsAutoCString sourceUri;
|
||||
if (mDocument && mDocument->GetDocumentURI()) {
|
||||
mDocument->GetDocumentURI()->GetAsciiSpec(sourceUri);
|
||||
} else if (!mWorkerScript.IsEmpty()) {
|
||||
sourceUri.Assign(mWorkerScript);
|
||||
}
|
||||
nsresult rv = mSRIDataVerifier->Verify(mSRIMetadata, channel, sourceUri,
|
||||
aReporter);
|
||||
if (NS_FAILED(rv)) {
|
||||
FailWithNetworkError();
|
||||
// Cancel request.
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
|
||||
if (mPipeOutputStream) {
|
||||
mPipeOutputStream->Close();
|
||||
}
|
||||
}
|
||||
|
||||
if (mObserver) {
|
||||
if (mResponse->Type() != ResponseType::Error &&
|
||||
!mRequest->GetIntegrity().IsEmpty()) {
|
||||
//From "Main Fetch" step 23: Process response.
|
||||
MOZ_ASSERT(mResponse);
|
||||
mObserver->OnResponseAvailable(mResponse);
|
||||
#ifdef DEBUG
|
||||
mResponseAvailableCalled = true;
|
||||
#endif
|
||||
}
|
||||
|
||||
mObserver->OnResponseEnd();
|
||||
mObserver = nullptr;
|
||||
}
|
||||
|
|
|
@ -11,11 +11,14 @@
|
|||
#include "nsIInterfaceRequestor.h"
|
||||
#include "nsIStreamListener.h"
|
||||
#include "nsIThreadRetargetableStreamListener.h"
|
||||
#include "mozilla/ConsoleReportCollector.h"
|
||||
#include "mozilla/dom/SRICheck.h"
|
||||
#include "mozilla/RefPtr.h"
|
||||
|
||||
#include "mozilla/DebugOnly.h"
|
||||
#include "mozilla/net/ReferrerPolicy.h"
|
||||
|
||||
class nsIConsoleReportCollector;
|
||||
class nsIDocument;
|
||||
class nsIOutputStream;
|
||||
class nsILoadGroup;
|
||||
|
@ -35,7 +38,8 @@ class InternalResponse;
|
|||
class FetchDriverObserver
|
||||
{
|
||||
public:
|
||||
FetchDriverObserver() : mGotResponseAvailable(false)
|
||||
FetchDriverObserver() : mReporter(new ConsoleReportCollector())
|
||||
, mGotResponseAvailable(false)
|
||||
{ }
|
||||
|
||||
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(FetchDriverObserver);
|
||||
|
@ -48,12 +52,19 @@ public:
|
|||
virtual void OnResponseEnd()
|
||||
{ };
|
||||
|
||||
nsIConsoleReportCollector* GetReporter() const
|
||||
{
|
||||
return mReporter;
|
||||
}
|
||||
|
||||
virtual void FlushConsoleReport() = 0;
|
||||
protected:
|
||||
virtual ~FetchDriverObserver()
|
||||
{ };
|
||||
|
||||
virtual void OnResponseAvailableInternal(InternalResponse* aResponse) = 0;
|
||||
|
||||
nsCOMPtr<nsIConsoleReportCollector> mReporter;
|
||||
private:
|
||||
bool mGotResponseAvailable;
|
||||
};
|
||||
|
@ -78,6 +89,13 @@ public:
|
|||
void
|
||||
SetDocument(nsIDocument* aDocument);
|
||||
|
||||
void
|
||||
SetWorkerScript(const nsACString& aWorkerScirpt)
|
||||
{
|
||||
MOZ_ASSERT(!aWorkerScirpt.IsEmpty());
|
||||
mWorkerScript = aWorkerScirpt;
|
||||
}
|
||||
|
||||
private:
|
||||
nsCOMPtr<nsIPrincipal> mPrincipal;
|
||||
nsCOMPtr<nsILoadGroup> mLoadGroup;
|
||||
|
@ -86,6 +104,9 @@ private:
|
|||
nsCOMPtr<nsIOutputStream> mPipeOutputStream;
|
||||
RefPtr<FetchDriverObserver> mObserver;
|
||||
nsCOMPtr<nsIDocument> mDocument;
|
||||
nsAutoPtr<SRICheckDataVerifier> mSRIDataVerifier;
|
||||
SRIMetadata mSRIMetadata;
|
||||
nsCString mWorkerScript;
|
||||
|
||||
#ifdef DEBUG
|
||||
bool mResponseAvailableCalled;
|
||||
|
|
|
@ -41,6 +41,7 @@ InternalRequest::GetRequestConstructorCopy(nsIGlobalObject* aGlobal, ErrorResult
|
|||
copy->mReferrer = mReferrer;
|
||||
copy->mReferrerPolicy = mReferrerPolicy;
|
||||
copy->mEnvironmentReferrerPolicy = mEnvironmentReferrerPolicy;
|
||||
copy->mIntegrity = mIntegrity;
|
||||
|
||||
copy->mContentPolicyType = mContentPolicyTypeOverridden ?
|
||||
mContentPolicyType :
|
||||
|
@ -91,6 +92,7 @@ InternalRequest::InternalRequest(const InternalRequest& aOther)
|
|||
, mResponseTainting(aOther.mResponseTainting)
|
||||
, mCacheMode(aOther.mCacheMode)
|
||||
, mRedirectMode(aOther.mRedirectMode)
|
||||
, mIntegrity(aOther.mIntegrity)
|
||||
, mAuthenticationFlag(aOther.mAuthenticationFlag)
|
||||
, mForceOriginHeader(aOther.mForceOriginHeader)
|
||||
, mPreserveContentCodings(aOther.mPreserveContentCodings)
|
||||
|
|
|
@ -128,7 +128,8 @@ public:
|
|||
RequestCredentials aRequestCredentials,
|
||||
const nsAString& aReferrer,
|
||||
ReferrerPolicy aReferrerPolicy,
|
||||
nsContentPolicyType aContentPolicyType)
|
||||
nsContentPolicyType aContentPolicyType,
|
||||
const nsAString& aIntegrity)
|
||||
: mMethod(aMethod)
|
||||
, mHeaders(aHeaders)
|
||||
, mContentPolicyType(aContentPolicyType)
|
||||
|
@ -140,6 +141,7 @@ public:
|
|||
, mResponseTainting(LoadTainting::Basic)
|
||||
, mCacheMode(aCacheMode)
|
||||
, mRedirectMode(aRequestRedirect)
|
||||
, mIntegrity(aIntegrity)
|
||||
, mAuthenticationFlag(false)
|
||||
, mForceOriginHeader(false)
|
||||
, mPreserveContentCodings(false)
|
||||
|
@ -361,6 +363,19 @@ public:
|
|||
mRedirectMode = aRedirectMode;
|
||||
}
|
||||
|
||||
const nsString&
|
||||
GetIntegrity() const
|
||||
{
|
||||
return mIntegrity;
|
||||
}
|
||||
|
||||
void
|
||||
SetIntegrity(const nsAString& aIntegrity)
|
||||
{
|
||||
MOZ_ASSERT(mIntegrity.IsEmpty());
|
||||
mIntegrity.Assign(aIntegrity);
|
||||
}
|
||||
|
||||
nsContentPolicyType
|
||||
ContentPolicyType() const
|
||||
{
|
||||
|
@ -520,6 +535,8 @@ private:
|
|||
RequestCache mCacheMode;
|
||||
RequestRedirect mRedirectMode;
|
||||
|
||||
nsString mIntegrity;
|
||||
|
||||
MOZ_INIT_OUTSIDE_CTOR bool mAuthenticationFlag;
|
||||
MOZ_INIT_OUTSIDE_CTOR bool mForceOriginHeader;
|
||||
MOZ_INIT_OUTSIDE_CTOR bool mPreserveContentCodings;
|
||||
|
|
|
@ -459,6 +459,10 @@ Request::Constructor(const GlobalObject& aGlobal,
|
|||
request->SetRedirectMode(aInit.mRedirect.Value());
|
||||
}
|
||||
|
||||
if (aInit.mIntegrity.WasPassed()) {
|
||||
request->SetIntegrity(aInit.mIntegrity.Value());
|
||||
}
|
||||
|
||||
// Request constructor step 14.
|
||||
if (aInit.mMethod.WasPassed()) {
|
||||
nsAutoCString method(aInit.mMethod.Value());
|
||||
|
@ -508,6 +512,11 @@ Request::Constructor(const GlobalObject& aGlobal,
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
if (!request->GetIntegrity().IsEmpty()) {
|
||||
aRv.ThrowTypeError<MSG_REQUEST_INTEGRITY_METADATA_NOT_EMPTY>();
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
requestHeaders->SetGuard(HeadersGuardEnum::Request_no_cors, aRv);
|
||||
if (aRv.Failed()) {
|
||||
return nullptr;
|
||||
|
|
|
@ -81,6 +81,12 @@ public:
|
|||
return mRequest->GetRedirectMode();
|
||||
}
|
||||
|
||||
void
|
||||
GetIntegrity(nsAString& aIntegrity) const
|
||||
{
|
||||
aIntegrity = mRequest->GetIntegrity();
|
||||
}
|
||||
|
||||
RequestContext
|
||||
Context() const
|
||||
{
|
||||
|
|
|
@ -25,6 +25,7 @@ interface Request {
|
|||
readonly attribute RequestCredentials credentials;
|
||||
readonly attribute RequestCache cache;
|
||||
readonly attribute RequestRedirect redirect;
|
||||
readonly attribute DOMString integrity;
|
||||
|
||||
[Throws,
|
||||
NewObject] Request clone();
|
||||
|
@ -45,6 +46,7 @@ dictionary RequestInit {
|
|||
RequestCredentials credentials;
|
||||
RequestCache cache;
|
||||
RequestRedirect redirect;
|
||||
DOMString integrity;
|
||||
};
|
||||
|
||||
// Gecko currently does not ship RequestContext, so please don't use it in IDL
|
||||
|
|
|
@ -1257,6 +1257,7 @@ class FetchEventRunnable : public ExtendableFunctionalEventWorkerRunnable
|
|||
nsCOMPtr<nsIInputStream> mUploadStream;
|
||||
nsCString mReferrer;
|
||||
ReferrerPolicy mReferrerPolicy;
|
||||
nsString mIntegrity;
|
||||
public:
|
||||
FetchEventRunnable(WorkerPrivate* aWorkerPrivate,
|
||||
KeepAliveToken* aKeepAliveToken,
|
||||
|
@ -1382,6 +1383,8 @@ public:
|
|||
internalChannel->GetFetchCacheMode(&cacheMode);
|
||||
mCacheMode = static_cast<RequestCache>(cacheMode);
|
||||
|
||||
internalChannel->GetIntegrityMetadata(mIntegrity);
|
||||
|
||||
mRequestCredentials = InternalRequest::MapChannelToRequestCredentials(channel);
|
||||
|
||||
rv = httpChannel->VisitNonDefaultRequestHeaders(this);
|
||||
|
@ -1480,7 +1483,8 @@ private:
|
|||
mRequestCredentials,
|
||||
NS_ConvertUTF8toUTF16(mReferrer),
|
||||
mReferrerPolicy,
|
||||
mContentPolicyType);
|
||||
mContentPolicyType,
|
||||
mIntegrity);
|
||||
internalReq->SetBody(mUploadStream);
|
||||
// For Telemetry, note that this Request object was created by a Fetch event.
|
||||
internalReq->SetCreatedByFetchEvent();
|
||||
|
|
|
@ -2485,6 +2485,20 @@ HttpBaseChannel::SetFetchCacheMode(uint32_t aFetchCacheMode)
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
HttpBaseChannel::SetIntegrityMetadata(const nsAString& aIntegrityMetadata)
|
||||
{
|
||||
mIntegrityMetadata = aIntegrityMetadata;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
HttpBaseChannel::GetIntegrityMetadata(nsAString& aIntegrityMetadata)
|
||||
{
|
||||
aIntegrityMetadata = mIntegrityMetadata;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// HttpBaseChannel::nsISupportsPriority
|
||||
//-----------------------------------------------------------------------------
|
||||
|
@ -3086,6 +3100,9 @@ HttpBaseChannel::SetupReplacementChannel(nsIURI *newURI,
|
|||
|
||||
// Preserve Cache mode flag.
|
||||
httpInternal->SetFetchCacheMode(mFetchCacheMode);
|
||||
|
||||
// Preserve Integrity metadata.
|
||||
httpInternal->SetIntegrityMetadata(mIntegrityMetadata);
|
||||
}
|
||||
|
||||
// transfer application cache information
|
||||
|
|
|
@ -234,6 +234,8 @@ public:
|
|||
NS_IMETHOD GetProxyURI(nsIURI **proxyURI) override;
|
||||
virtual void SetCorsPreflightParameters(const nsTArray<nsCString>& unsafeHeaders) override;
|
||||
NS_IMETHOD GetConnectionInfoHashKey(nsACString& aConnectionInfoHashKey) override;
|
||||
NS_IMETHOD GetIntegrityMetadata(nsAString& aIntegrityMetadata) override;
|
||||
NS_IMETHOD SetIntegrityMetadata(const nsAString& aIntegrityMetadata) override;
|
||||
|
||||
inline void CleanRedirectCacheChainIfNecessary()
|
||||
{
|
||||
|
@ -540,6 +542,8 @@ protected:
|
|||
bool mForceMainDocumentChannel;
|
||||
|
||||
nsID mChannelId;
|
||||
|
||||
nsString mIntegrityMetadata;
|
||||
};
|
||||
|
||||
// Share some code while working around C++'s absurd inability to handle casting
|
||||
|
|
|
@ -287,6 +287,11 @@ interface nsIHttpChannelInternal : nsISupports
|
|||
[infallible]
|
||||
attribute boolean blockAuthPrompt;
|
||||
|
||||
/**
|
||||
* Set to indicate Request.integrity.
|
||||
*/
|
||||
attribute AString integrityMetadata;
|
||||
|
||||
/**
|
||||
* The connection info's hash key. We use it to test connection separation.
|
||||
*/
|
||||
|
|
Загрузка…
Ссылка в новой задаче