Diff
Modified: trunk/Source/WebCore/ChangeLog (260302 => 260303)
--- trunk/Source/WebCore/ChangeLog 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebCore/ChangeLog 2020-04-18 00:54:41 UTC (rev 260303)
@@ -1,3 +1,22 @@
+2020-04-17 Kate Cheney <[email protected]>
+
+ Enable service workers for app-bound domains
+ https://bugs.webkit.org/show_bug.cgi?id=210451
+ <rdar://problem/61479474>
+
+ Reviewed by Brent Fulgham.
+
+ SWServer now retrieves the app-bound domains from the UI Process and
+ only continues with the load if the proper entitlement is present
+ or the load is coming from an app-bound domain.
+
+ * workers/service/server/SWServer.cpp:
+ (WebCore::SWServer::addRegistrationFromStore):
+ (WebCore::SWServer::SWServer):
+ (WebCore::SWServer::validateRegistrationDomain):
+ (WebCore::SWServer::scheduleJob):
+ * workers/service/server/SWServer.h:
+
2020-04-17 Dean Jackson <[email protected]>
[WebGL] Confirm there are no errors when setting up framebuffers
Modified: trunk/Source/WebCore/workers/service/server/SWServer.cpp (260302 => 260303)
--- trunk/Source/WebCore/workers/service/server/SWServer.cpp 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebCore/workers/service/server/SWServer.cpp 2020-04-18 00:54:41 UTC (rev 260303)
@@ -155,15 +155,21 @@
{
// Pages should not have been able to make a new registration to this key while the import was still taking place.
ASSERT(!m_scopeToRegistrationMap.contains(data.registration.key));
+
+ validateRegistrationDomain(WebCore::RegistrableDomain(data.scriptURL), [this, weakThis = makeWeakPtr(this), data = "" (bool isValid) mutable {
+ if (!weakThis)
+ return;
+ if (m_hasServiceWorkerEntitlement || isValid) {
+ auto registration = makeUnique<SWServerRegistration>(*this, data.registration.key, data.registration.updateViaCache, data.registration.scopeURL, data.scriptURL);
+ registration->setLastUpdateTime(data.registration.lastUpdateTime);
+ auto registrationPtr = registration.get();
+ addRegistration(WTFMove(registration));
- auto registration = makeUnique<SWServerRegistration>(*this, data.registration.key, data.registration.updateViaCache, data.registration.scopeURL, data.scriptURL);
- registration->setLastUpdateTime(data.registration.lastUpdateTime);
- auto registrationPtr = registration.get();
- addRegistration(WTFMove(registration));
-
- auto worker = SWServerWorker::create(*this, *registrationPtr, data.scriptURL, data.script, data.contentSecurityPolicy, WTFMove(data.referrerPolicy), data.workerType, data.serviceWorkerIdentifier, WTFMove(data.scriptResourceMap));
- registrationPtr->updateRegistrationState(ServiceWorkerRegistrationState::Active, worker.ptr());
- worker->setState(ServiceWorkerState::Activated);
+ auto worker = SWServerWorker::create(*this, *registrationPtr, data.scriptURL, data.script, data.contentSecurityPolicy, WTFMove(data.referrerPolicy), data.workerType, data.serviceWorkerIdentifier, WTFMove(data.scriptResourceMap));
+ registrationPtr->updateRegistrationState(ServiceWorkerRegistrationState::Active, worker.ptr());
+ worker->setState(ServiceWorkerState::Activated);
+ }
+ });
}
void SWServer::addRegistration(std::unique_ptr<SWServerRegistration>&& registration)
@@ -305,12 +311,14 @@
m_server.removeClientServiceWorkerRegistration(*this, identifier);
}
-SWServer::SWServer(UniqueRef<SWOriginStore>&& originStore, bool processTerminationDelayEnabled, String&& registrationDatabaseDirectory, PAL::SessionID sessionID, SoftUpdateCallback&& softUpdateCallback, CreateContextConnectionCallback&& callback)
+SWServer::SWServer(UniqueRef<SWOriginStore>&& originStore, bool processTerminationDelayEnabled, String&& registrationDatabaseDirectory, PAL::SessionID sessionID, bool hasServiceWorkerEntitlement, SoftUpdateCallback&& softUpdateCallback, CreateContextConnectionCallback&& callback, AppBoundDomainsCallback&& appBoundDomainsCallback)
: m_originStore(WTFMove(originStore))
, m_sessionID(sessionID)
, m_isProcessTerminationDelayEnabled(processTerminationDelayEnabled)
, m_createContextConnectionCallback(WTFMove(callback))
, m_softUpdateCallback(WTFMove(softUpdateCallback))
+ , m_appBoundDomainsCallback(WTFMove(appBoundDomainsCallback))
+ , m_hasServiceWorkerEntitlement(hasServiceWorkerEntitlement)
{
RELEASE_LOG_IF(registrationDatabaseDirectory.isEmpty() && !m_sessionID.isEphemeral(), ServiceWorker, "No path to store the service worker registrations");
if (!m_sessionID.isEphemeral())
@@ -322,31 +330,53 @@
allServers().add(this);
}
+void SWServer::validateRegistrationDomain(WebCore::RegistrableDomain domain, CompletionHandler<void(bool)>&& completionHandler)
+{
+ if (m_hasServiceWorkerEntitlement || m_hasReceivedAppBoundDomains) {
+ completionHandler(m_appBoundDomains.contains(domain));
+ return;
+ }
+
+ m_appBoundDomainsCallback([this, weakThis = makeWeakPtr(this), domain = WTFMove(domain), completionHandler = WTFMove(completionHandler)](auto&& appBoundDomains) mutable {
+ if (!weakThis)
+ return;
+ m_hasReceivedAppBoundDomains = true;
+ m_appBoundDomains = WTFMove(appBoundDomains);
+ completionHandler(m_appBoundDomains.contains(domain));
+ });
+}
+
// https://w3c.github.io/ServiceWorker/#schedule-job-algorithm
void SWServer::scheduleJob(ServiceWorkerJobData&& jobData)
{
ASSERT(m_connections.contains(jobData.connectionIdentifier()) || jobData.connectionIdentifier() == Process::identifier());
- auto& jobQueue = *m_jobQueues.ensure(jobData.registrationKey(), [this, &jobData] {
- return makeUnique<SWServerJobQueue>(*this, jobData.registrationKey());
- }).iterator->value;
-
- if (!jobQueue.size()) {
- jobQueue.enqueueJob(WTFMove(jobData));
- jobQueue.runNextJob();
- return;
- }
- auto& lastJob = jobQueue.lastJob();
- if (jobData.isEquivalent(lastJob)) {
- // FIXME: Per the spec, check if this job is equivalent to the last job on the queue.
- // If it is, stack it along with that job. For now, we just make sure to not call soft-update too often.
- if (jobData.type == ServiceWorkerJobType::Update && jobData.connectionIdentifier() == Process::identifier())
+ validateRegistrationDomain(WebCore::RegistrableDomain(jobData.scriptURL), [this, weakThis = makeWeakPtr(this), jobData = WTFMove(jobData)] (bool isValid) mutable {
+ if (!weakThis)
return;
- }
+ if (m_hasServiceWorkerEntitlement || isValid) {
+ auto& jobQueue = *m_jobQueues.ensure(jobData.registrationKey(), [this, &jobData] {
+ return makeUnique<SWServerJobQueue>(*this, jobData.registrationKey());
+ }).iterator->value;
- jobQueue.enqueueJob(WTFMove(jobData));
- if (jobQueue.size() == 1)
- jobQueue.runNextJob();
+ if (!jobQueue.size()) {
+ jobQueue.enqueueJob(WTFMove(jobData));
+ jobQueue.runNextJob();
+ return;
+ }
+ auto& lastJob = jobQueue.lastJob();
+ if (jobData.isEquivalent(lastJob)) {
+ // FIXME: Per the spec, check if this job is equivalent to the last job on the queue.
+ // If it is, stack it along with that job. For now, we just make sure to not call soft-update too often.
+ if (jobData.type == ServiceWorkerJobType::Update && jobData.connectionIdentifier() == Process::identifier())
+ return;
+ }
+ jobQueue.enqueueJob(WTFMove(jobData));
+ if (jobQueue.size() == 1)
+ jobQueue.runNextJob();
+ } else
+ rejectJob(jobData, { TypeError, "Job rejected for non app-bound domain" });
+ });
}
void SWServer::scheduleUnregisterJob(ServiceWorkerJobDataIdentifier jobDataIdentifier, SWServerRegistration& registration, DocumentOrWorkerIdentifier contextIdentifier, URL&& clientCreationURL)
Modified: trunk/Source/WebCore/workers/service/server/SWServer.h (260302 => 260303)
--- trunk/Source/WebCore/workers/service/server/SWServer.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebCore/workers/service/server/SWServer.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -126,7 +126,8 @@
using SoftUpdateCallback = Function<void(ServiceWorkerJobData&& jobData, bool shouldRefreshCache, ResourceRequest&&, CompletionHandler<void(const ServiceWorkerFetchResult&)>&&)>;
using CreateContextConnectionCallback = Function<void(const WebCore::RegistrableDomain&, CompletionHandler<void()>&&)>;
- WEBCORE_EXPORT SWServer(UniqueRef<SWOriginStore>&&, bool processTerminationDelayEnabled, String&& registrationDatabaseDirectory, PAL::SessionID, SoftUpdateCallback&&, CreateContextConnectionCallback&&);
+ using AppBoundDomainsCallback = Function<void(CompletionHandler<void(HashSet<WebCore::RegistrableDomain>&&)>&&)>;
+ WEBCORE_EXPORT SWServer(UniqueRef<SWOriginStore>&&, bool processTerminationDelayEnabled, String&& registrationDatabaseDirectory, PAL::SessionID, bool hasServiceWorkerEntitlement, SoftUpdateCallback&&, CreateContextConnectionCallback&&, AppBoundDomainsCallback&&);
WEBCORE_EXPORT ~SWServer();
@@ -215,6 +216,8 @@
static constexpr Seconds defaultTerminationDelay = 10_s;
private:
+ void validateRegistrationDomain(WebCore::RegistrableDomain, CompletionHandler<void(bool)>&&);
+
void scriptFetchFinished(const ServiceWorkerFetchResult&);
void didResolveRegistrationPromise(Connection*, const ServiceWorkerRegistrationKey&);
@@ -269,6 +272,11 @@
HashSet<WebCore::RegistrableDomain> m_pendingConnectionDomains;
Vector<CompletionHandler<void()>> m_importCompletedCallbacks;
SoftUpdateCallback m_softUpdateCallback;
+ AppBoundDomainsCallback m_appBoundDomainsCallback;
+
+ HashSet<WebCore::RegistrableDomain> m_appBoundDomains;
+ bool m_hasServiceWorkerEntitlement { false };
+ bool m_hasReceivedAppBoundDomains { false };
};
} // namespace WebCore
Modified: trunk/Source/WebKit/ChangeLog (260302 => 260303)
--- trunk/Source/WebKit/ChangeLog 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/ChangeLog 2020-04-18 00:54:41 UTC (rev 260303)
@@ -1,3 +1,114 @@
+2020-04-17 Kate Cheney <[email protected]>
+
+ Enable service workers for app-bound domains
+ https://bugs.webkit.org/show_bug.cgi?id=210451
+ <rdar://problem/61479474>
+
+ Reviewed by Brent Fulgham.
+
+ * NetworkProcess/NetworkConnectionToWebProcess.cpp:
+ (WebKit::NetworkConnectionToWebProcess::createFetchTask):
+ (WebKit::NetworkConnectionToWebProcess::scheduleResourceLoad):
+ (WebKit::NetworkConnectionToWebProcess::swConnection):
+ (WebKit::NetworkConnectionToWebProcess::isServiceWorkerAllowed const): Deleted.
+ * NetworkProcess/NetworkConnectionToWebProcess.h:
+ Removed ASSERTS and service worker entitlement checks which are now done along with app-bound
+ domain checks in SWServer.cpp.
+
+ * NetworkProcess/NetworkProcess.cpp:
+ (WebKit::NetworkProcess::initializeNetworkProcess):
+ (WebKit::NetworkProcess::addWebsiteDataStore):
+ Remove the check for parentProcessHasServiceWorkerEntitlement() before
+ adding a serviceWorkerSession. This doesn't do anything except add an
+ entry to a map, and simplifies the case where we need a session for
+ app-bound instances which should have service workers but have no entitlement.
+
+ Pass the entitlement and a new callback to request app-bound domains
+ from the UI Process to the SWServer. This will make sure the server
+ checks for the entitlement or list of app-bound domains before completing a load.
+
+ (WebKit::NetworkProcess::registerSWServerConnection):
+ Remove unnecessary ASSERT for entitlement.
+
+ * NetworkProcess/NetworkProcess.h:
+ * NetworkProcess/NetworkProcess.messages.in:
+ * NetworkProcess/ios/NetworkProcessIOS.mm:
+ (WebKit::NetworkProcess::parentProcessHasServiceWorkerEntitlement const):
+ (WebKit::NetworkProcess::disableServiceWorkerEntitlement):
+ (WebKit::NetworkProcess::clearServiceWorkerEntitlementOverride):
+ In order to test this thoroughly, TestWebKitAPI needed a way to
+ temporarily disable the service worker entitlement. This function
+ overrides the check for the entitlement if the bool is set, disabling
+ the entitlement.
+
+ * Shared/WebPageCreationParameters.cpp:
+ (WebKit::WebPageCreationParameters::encode const):
+ (WebKit::WebPageCreationParameters::decode):
+ * Shared/WebPageCreationParameters.h:
+ WebPage needs to know if it is app-bound when created so it can update
+ the service worker preferences key accordingly.
+
+ * Shared/WebPreferences.yaml:
+ * UIProcess/API/Cocoa/WKPreferences.mm:
+ (-[WKPreferences _serviceWorkerEntitlementDisabledForTesting]):
+ (-[WKPreferences _setServiceWorkerEntitlementDisabledForTesting:]):
+ * UIProcess/API/Cocoa/WKPreferencesPrivate.h:
+ Disable entitlement for testing.
+
+ * UIProcess/API/APIPageConfiguration.cpp:
+ (API::PageConfiguration::copy const):
+ * UIProcess/API/APIPageConfiguration.h:
+ (API::PageConfiguration::limitsNavigationsToAppBoundDomains const):
+ (API::PageConfiguration::setLimitsNavigationsToAppBoundDomains):
+ (API::PageConfiguration::limitsNavigationToAppBoundDomains const): Deleted.
+ (API::PageConfiguration::setLimitsNavigationToAppBoundDomains): Deleted.
+ (-[WKWebViewConfiguration limitsNavigationsToAppBoundDomains]):
+ (-[WKWebViewConfiguration setLimitsNavigationsToAppBoundDomains:]):
+ (-[WKWebViewConfiguration limitsNavigationToAppBoundDomains]): Deleted.
+ (-[WKWebViewConfiguration setLimitsNavigationToAppBoundDomains:]): Deleted.
+ * UIProcess/API/Cocoa/WKWebViewConfiguration.mm:
+ Inconsistent naming (Navigation vs Navigations).
+
+ * UIProcess/API/Cocoa/WKWebView.mm:
+ (-[WKWebView _setupPageConfiguration:]):
+ Check for entitlement or app-bound webview.
+
+ (-[WKWebView _serviceWorkersEnabled:]):
+ (-[WKWebView _clearServiceWorkerEntitlementOverride:]):
+ * UIProcess/API/Cocoa/WKWebViewPrivate.h:
+ Testing SPIs.
+
+ * UIProcess/Network/NetworkProcessProxy.cpp:
+ (WebKit::NetworkProcessProxy::getAppBoundDomains):
+ * UIProcess/Network/NetworkProcessProxy.h:
+ * UIProcess/Network/NetworkProcessProxy.messages.in:
+ Sends the app-bound domains to the Network Process.
+
+ * UIProcess/WebPageProxy.cpp:
+ (WebKit::m_limitsNavigationsToAppBoundDomains):
+ (WebKit::m_limitsNavigationToAppBoundDomains): Deleted.
+ Naming inconsistency.
+
+ (WebKit::WebPageProxy::disableServiceWorkerEntitlementInNetworkProcess):
+ (WebKit::WebPageProxy::clearServiceWorkerEntitlementOverride):
+ * UIProcess/WebPageProxy.h:
+ Disable entitlement for testing.
+
+ * WebProcess/WebPage/WebPage.cpp:
+ (WebKit::m_isNavigatingToAppBoundDomain):
+ Set this parameter in the constructor so it will be accurate when
+ updating preferences.
+
+ (WebKit::WebPage::updatePreferences):
+ * WebProcess/WebPage/WebPage.h:
+ (WebKit::WebPage::clearServiceWorkerEntitlementOverride):
+ * WebProcess/WebPage/WebPage.messages.in:
+ * WebProcess/WebPage/ios/WebPageIOS.mm:
+ (WebKit::WebPage::parentProcessHasServiceWorkerEntitlement const):
+ (WebKit::WebPage::disableServiceWorkerEntitlement):
+ (WebKit::WebPage::clearServiceWorkerEntitlementOverride):
+ Disable entitlement for testing.
+
2020-04-17 Alex Christensen <[email protected]>
NetworkSessionCocoa should request client certificate only once per host/port
Modified: trunk/Source/WebKit/NetworkProcess/NetworkConnectionToWebProcess.cpp (260302 => 260303)
--- trunk/Source/WebKit/NetworkProcess/NetworkConnectionToWebProcess.cpp 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/NetworkProcess/NetworkConnectionToWebProcess.cpp 2020-04-18 00:54:41 UTC (rev 260303)
@@ -121,8 +121,7 @@
m_connection->open();
#if ENABLE(SERVICE_WORKER)
- if (networkProcess.parentProcessHasServiceWorkerEntitlement())
- establishSWServerConnection();
+ establishSWServerConnection();
#endif
}
@@ -431,15 +430,8 @@
}
#if ENABLE(SERVICE_WORKER)
-bool NetworkConnectionToWebProcess::isServiceWorkerAllowed() const
-{
- return m_networkProcess->parentProcessHasServiceWorkerEntitlement();
-}
-
std::unique_ptr<ServiceWorkerFetchTask> NetworkConnectionToWebProcess::createFetchTask(NetworkResourceLoader& loader, const ResourceRequest& request)
{
- if (!isServiceWorkerAllowed())
- return nullptr;
return swConnection().createFetchTask(loader, request);
}
#endif
@@ -447,18 +439,15 @@
void NetworkConnectionToWebProcess::scheduleResourceLoad(NetworkResourceLoadParameters&& loadParameters)
{
#if ENABLE(SERVICE_WORKER)
- bool isServiceWorkerAllowed = this->isServiceWorkerAllowed();
- if (isServiceWorkerAllowed) {
- auto& server = m_networkProcess->swServerForSession(m_sessionID);
- if (!server.isImportCompleted()) {
- server.whenImportIsCompleted([this, protectedThis = makeRef(*this), loadParameters = WTFMove(loadParameters)]() mutable {
- if (!m_networkProcess->webProcessConnection(webProcessIdentifier()))
- return;
- ASSERT(m_networkProcess->swServerForSession(m_sessionID).isImportCompleted());
- scheduleResourceLoad(WTFMove(loadParameters));
- });
- return;
- }
+ auto& server = m_networkProcess->swServerForSession(m_sessionID);
+ if (!server.isImportCompleted()) {
+ server.whenImportIsCompleted([this, protectedThis = makeRef(*this), loadParameters = WTFMove(loadParameters)]() mutable {
+ if (!m_networkProcess->webProcessConnection(webProcessIdentifier()))
+ return;
+ ASSERT(m_networkProcess->swServerForSession(m_sessionID).isImportCompleted());
+ scheduleResourceLoad(WTFMove(loadParameters));
+ });
+ return;
}
#endif
auto identifier = loadParameters.identifier;
@@ -469,12 +458,11 @@
auto& loader = m_networkResourceLoaders.add(identifier, NetworkResourceLoader::create(WTFMove(loadParameters), *this)).iterator->value;
#if ENABLE(SERVICE_WORKER)
- if (isServiceWorkerAllowed) {
- loader->startWithServiceWorker();
- return;
- }
+ loader->startWithServiceWorker();
+ return;
+#else
+ loader->start();
#endif
- loader->start();
}
void NetworkConnectionToWebProcess::performSynchronousLoad(NetworkResourceLoadParameters&& loadParameters, Messages::NetworkConnectionToWebProcess::PerformSynchronousLoad::DelayedReply&& reply)
@@ -1053,7 +1041,6 @@
WebSWServerConnection& NetworkConnectionToWebProcess::swConnection()
{
- ASSERT(isServiceWorkerAllowed());
if (!m_swConnection)
establishSWServerConnection();
return *m_swConnection;
Modified: trunk/Source/WebKit/NetworkProcess/NetworkConnectionToWebProcess.h (260302 => 260303)
--- trunk/Source/WebKit/NetworkProcess/NetworkConnectionToWebProcess.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/NetworkProcess/NetworkConnectionToWebProcess.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -236,7 +236,6 @@
void establishSWContextConnection(WebCore::RegistrableDomain&&, CompletionHandler<void()>&&);
void closeSWContextConnection();
void unregisterSWConnection();
- bool isServiceWorkerAllowed() const;
#endif
void createNewMessagePortChannel(const WebCore::MessagePortIdentifier& port1, const WebCore::MessagePortIdentifier& port2);
Modified: trunk/Source/WebKit/NetworkProcess/NetworkProcess.cpp (260302 => 260303)
--- trunk/Source/WebKit/NetworkProcess/NetworkProcess.cpp 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/NetworkProcess/NetworkProcess.cpp 2020-04-18 00:54:41 UTC (rev 260303)
@@ -345,10 +345,8 @@
#endif
#if ENABLE(SERVICE_WORKER)
- if (parentProcessHasServiceWorkerEntitlement()) {
- bool serviceWorkerProcessTerminationDelayEnabled = true;
- addServiceWorkerSession(PAL::SessionID::defaultSessionID(), serviceWorkerProcessTerminationDelayEnabled, WTFMove(parameters.serviceWorkerRegistrationDirectory), parameters.serviceWorkerRegistrationDirectoryExtensionHandle);
- }
+ bool serviceWorkerProcessTerminationDelayEnabled = true;
+ addServiceWorkerSession(PAL::SessionID::defaultSessionID(), serviceWorkerProcessTerminationDelayEnabled, WTFMove(parameters.serviceWorkerRegistrationDirectory), parameters.serviceWorkerRegistrationDirectoryExtensionHandle);
#endif
m_storageManagerSet->add(sessionID, parameters.defaultDataStoreParameters.localStorageDirectory, parameters.defaultDataStoreParameters.localStorageDirectoryExtensionHandle);
@@ -438,8 +436,7 @@
#endif
#if ENABLE(SERVICE_WORKER)
- if (parentProcessHasServiceWorkerEntitlement())
- addServiceWorkerSession(sessionID, parameters.serviceWorkerProcessTerminationDelayEnabled, WTFMove(parameters.serviceWorkerRegistrationDirectory), parameters.serviceWorkerRegistrationDirectoryExtensionHandle);
+ addServiceWorkerSession(sessionID, parameters.serviceWorkerProcessTerminationDelayEnabled, WTFMove(parameters.serviceWorkerRegistrationDirectory), parameters.serviceWorkerRegistrationDirectoryExtensionHandle);
#endif
m_storageManagerSet->add(sessionID, parameters.localStorageDirectory, parameters.localStorageDirectoryExtensionHandle);
@@ -2455,11 +2452,13 @@
// If there's not, then where did this PAL::SessionID come from?
ASSERT(sessionID.isEphemeral() || !path.isEmpty());
- return makeUnique<SWServer>(makeUniqueRef<WebSWOriginStore>(), info.processTerminationDelayEnabled, WTFMove(path), sessionID, [this, sessionID](auto&& jobData, bool shouldRefreshCache, auto&& request, auto&& completionHandler) mutable {
+ return makeUnique<SWServer>(makeUniqueRef<WebSWOriginStore>(), info.processTerminationDelayEnabled, WTFMove(path), sessionID, parentProcessHasServiceWorkerEntitlement(), [this, sessionID](auto&& jobData, bool shouldRefreshCache, auto&& request, auto&& completionHandler) mutable {
ServiceWorkerSoftUpdateLoader::start(networkSession(sessionID), WTFMove(jobData), shouldRefreshCache, WTFMove(request), WTFMove(completionHandler));
}, [this, sessionID](auto& registrableDomain, auto&& completionHandler) {
ASSERT(!registrableDomain.isEmpty());
parentProcessConnection()->sendWithAsyncReply(Messages::NetworkProcessProxy::EstablishWorkerContextConnectionToNetworkProcess { registrableDomain, sessionID }, WTFMove(completionHandler), 0);
+ }, [this, sessionID](auto&& completionHandler) {
+ parentProcessConnection()->sendWithAsyncReply(Messages::NetworkProcessProxy::GetAppBoundDomains { sessionID }, WTFMove(completionHandler), 0);
});
});
return *result.iterator->value;
@@ -2475,7 +2474,6 @@
void NetworkProcess::registerSWServerConnection(WebSWServerConnection& connection)
{
- ASSERT(parentProcessHasServiceWorkerEntitlement());
auto* store = existingSWOriginStoreForSession(connection.sessionID());
ASSERT(store);
if (store)
Modified: trunk/Source/WebKit/NetworkProcess/NetworkProcess.h (260302 => 260303)
--- trunk/Source/WebKit/NetworkProcess/NetworkProcess.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/NetworkProcess/NetworkProcess.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -306,6 +306,8 @@
#if PLATFORM(IOS_FAMILY)
bool parentProcessHasServiceWorkerEntitlement() const;
+ void disableServiceWorkerEntitlement();
+ void clearServiceWorkerEntitlementOverride(CompletionHandler<void()>&&);
#else
bool parentProcessHasServiceWorkerEntitlement() const { return true; }
#endif
Modified: trunk/Source/WebKit/NetworkProcess/NetworkProcess.messages.in (260302 => 260303)
--- trunk/Source/WebKit/NetworkProcess/NetworkProcess.messages.in 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/NetworkProcess/NetworkProcess.messages.in 2020-04-18 00:54:41 UTC (rev 260303)
@@ -172,4 +172,9 @@
HasAppBoundSession(PAL::SessionID sessionID) -> (bool hasAppBoundSession) Async
SetInAppBrowserPrivacyEnabled(PAL::SessionID sessionID, bool value) -> () Async
+
+#if PLATFORM(IOS_FAMILY)
+ DisableServiceWorkerEntitlement()
+ ClearServiceWorkerEntitlementOverride() -> () Async
+#endif
}
Modified: trunk/Source/WebKit/NetworkProcess/ios/NetworkProcessIOS.mm (260302 => 260303)
--- trunk/Source/WebKit/NetworkProcess/ios/NetworkProcessIOS.mm 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/NetworkProcess/ios/NetworkProcessIOS.mm 2020-04-18 00:54:41 UTC (rev 260303)
@@ -74,12 +74,28 @@
notImplemented();
}
+static bool disableServiceWorkerEntitlementTestingOverride;
+
bool NetworkProcess::parentProcessHasServiceWorkerEntitlement() const
{
+ if (disableServiceWorkerEntitlementTestingOverride)
+ return false;
+
static bool hasEntitlement = WTF::hasEntitlement(parentProcessConnection()->xpcConnection(), "com.apple.developer.WebKit.ServiceWorkers");
return hasEntitlement;
}
+void NetworkProcess::disableServiceWorkerEntitlement()
+{
+ disableServiceWorkerEntitlementTestingOverride = true;
+}
+
+void NetworkProcess::clearServiceWorkerEntitlementOverride(CompletionHandler<void()>&& completionHandler)
+{
+ disableServiceWorkerEntitlementTestingOverride = false;
+ completionHandler();
+}
+
} // namespace WebKit
#endif // PLATFORM(IOS_FAMILY)
Modified: trunk/Source/WebKit/Shared/WebPageCreationParameters.cpp (260302 => 260303)
--- trunk/Source/WebKit/Shared/WebPageCreationParameters.cpp 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/Shared/WebPageCreationParameters.cpp 2020-04-18 00:54:41 UTC (rev 260303)
@@ -146,6 +146,7 @@
encoder << shouldCaptureDisplayInUIProcess;
encoder << shouldRenderCanvasInGPUProcess;
encoder << needsInAppBrowserPrivacyQuirks;
+ encoder << limitsNavigationsToAppBoundDomains;
#if PLATFORM(GTK)
encoder << themeName;
@@ -470,6 +471,9 @@
if (!decoder.decode(parameters.needsInAppBrowserPrivacyQuirks))
return WTF::nullopt;
+ if (!decoder.decode(parameters.limitsNavigationsToAppBoundDomains))
+ return WTF::nullopt;
+
#if PLATFORM(GTK)
if (!decoder.decode(parameters.themeName))
return WTF::nullopt;
Modified: trunk/Source/WebKit/Shared/WebPageCreationParameters.h (260302 => 260303)
--- trunk/Source/WebKit/Shared/WebPageCreationParameters.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/Shared/WebPageCreationParameters.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -217,6 +217,7 @@
bool shouldCaptureDisplayInUIProcess { false };
bool shouldRenderCanvasInGPUProcess { false };
bool needsInAppBrowserPrivacyQuirks { false };
+ bool limitsNavigationsToAppBoundDomains { false };
#if PLATFORM(GTK)
String themeName;
Modified: trunk/Source/WebKit/Shared/WebPreferences.yaml (260302 => 260303)
--- trunk/Source/WebKit/Shared/WebPreferences.yaml 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/Shared/WebPreferences.yaml 2020-04-18 00:54:41 UTC (rev 260303)
@@ -1273,6 +1273,11 @@
webcoreBinding: RuntimeEnabledFeatures
category: debug
+ServiceWorkerEntitlementDisabledForTesting:
+ type: bool
+ defaultValue: false
+ webcoreBinding: none
+
# For experimental features:
# The type should be boolean.
# You must provide a humanReadableName and humanReadableDescription for all experimental features. They
Modified: trunk/Source/WebKit/UIProcess/API/APIPageConfiguration.cpp (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/API/APIPageConfiguration.cpp 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/API/APIPageConfiguration.cpp 2020-04-18 00:54:41 UTC (rev 260303)
@@ -97,7 +97,7 @@
copy->m_ignoresAppBoundDomains = this->m_ignoresAppBoundDomains;
copy->m_loadsSubresources = this->m_loadsSubresources;
copy->m_loadsFromNetwork = this->m_loadsFromNetwork;
- copy->m_limitsNavigationToAppBoundDomains = this->m_limitsNavigationToAppBoundDomains;
+ copy->m_limitsNavigationsToAppBoundDomains = this->m_limitsNavigationsToAppBoundDomains;
return copy;
}
Modified: trunk/Source/WebKit/UIProcess/API/APIPageConfiguration.h (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/API/APIPageConfiguration.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/API/APIPageConfiguration.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -158,8 +158,8 @@
bool loadsFromNetwork() const { return m_loadsFromNetwork; }
void setLoadsFromNetwork(bool loads) { m_loadsFromNetwork = loads; }
- bool limitsNavigationToAppBoundDomains() const { return m_limitsNavigationToAppBoundDomains; }
- void setLimitsNavigationToAppBoundDomains(bool limits) { m_limitsNavigationToAppBoundDomains = limits; }
+ bool limitsNavigationsToAppBoundDomains() const { return m_limitsNavigationsToAppBoundDomains; }
+ void setLimitsNavigationsToAppBoundDomains(bool limits) { m_limitsNavigationsToAppBoundDomains = limits; }
private:
@@ -204,7 +204,7 @@
bool m_ignoresAppBoundDomains { false };
bool m_loadsSubresources { true };
bool m_loadsFromNetwork { true };
- bool m_limitsNavigationToAppBoundDomains { false };
+ bool m_limitsNavigationsToAppBoundDomains { false };
};
} // namespace API
Modified: trunk/Source/WebKit/UIProcess/API/Cocoa/WKPreferences.mm (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/API/Cocoa/WKPreferences.mm 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/API/Cocoa/WKPreferences.mm 2020-04-18 00:54:41 UTC (rev 260303)
@@ -923,6 +923,16 @@
return _preferences->isITPDatabaseEnabled();
}
+- (BOOL)_serviceWorkerEntitlementDisabledForTesting
+{
+ return _preferences->serviceWorkerEntitlementDisabledForTesting();
+}
+
+- (void)_setServiceWorkerEntitlementDisabledForTesting:(BOOL)disable
+{
+ _preferences->setServiceWorkerEntitlementDisabledForTesting(disable);
+}
+
#if PLATFORM(MAC)
- (void)_setJavaEnabledForLocalFiles:(BOOL)enabled
{
Modified: trunk/Source/WebKit/UIProcess/API/Cocoa/WKPreferencesPrivate.h (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/API/Cocoa/WKPreferencesPrivate.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/API/Cocoa/WKPreferencesPrivate.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -165,6 +165,7 @@
@property (nonatomic, setter=_setAcceleratedCompositingEnabled:) BOOL _acceleratedCompositingEnabled WK_API_AVAILABLE(macos(10.13.4), ios(WK_IOS_TBA));
@property (nonatomic, setter=_setRequestAnimationFrameEnabled:) BOOL _requestAnimationFrameEnabled WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
@property (nonatomic, readonly) BOOL _isITPDatabaseEnabled WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
+@property (nonatomic, setter=_setServiceWorkerEntitlementDisabledForTesting:) BOOL _serviceWorkerEntitlementDisabledForTesting WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
#if !TARGET_OS_IPHONE
@property (nonatomic, setter=_setWebGLEnabled:) BOOL _webGLEnabled WK_API_AVAILABLE(macos(10.13.4));
Modified: trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebView.mm (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebView.mm 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebView.mm 2020-04-18 00:54:41 UTC (rev 260303)
@@ -121,6 +121,7 @@
#import <WebCore/MIMETypeRegistry.h>
#import <WebCore/PlatformScreen.h>
#import <WebCore/RuntimeApplicationChecks.h>
+#import <WebCore/RuntimeEnabledFeatures.h>
#import <WebCore/SQLiteDatabaseTracker.h>
#import <WebCore/Settings.h>
#import <WebCore/SharedBuffer.h>
@@ -523,8 +524,9 @@
#endif
#if PLATFORM(IOS_FAMILY) && ENABLE(SERVICE_WORKER)
- if (!WTF::processHasEntitlement("com.apple.developer.WebKit.ServiceWorkers"))
+ if ((!WTF::processHasEntitlement("com.apple.developer.WebKit.ServiceWorkers") || !![_configuration preferences]._serviceWorkerEntitlementDisabledForTesting) && ![_configuration limitsNavigationsToAppBoundDomains])
pageConfiguration->preferences()->setServiceWorkersEnabled(false);
+ pageConfiguration->preferences()->setServiceWorkerEntitlementDisabledForTesting(!![_configuration preferences]._serviceWorkerEntitlementDisabledForTesting);
#endif
if (!linkedOnOrAfter(WebKit::SDKVersion::FirstWhereSiteSpecificQuirksAreEnabledByDefault))
@@ -2650,6 +2652,19 @@
});
}
+- (void)_serviceWorkersEnabled:(void(^)(BOOL))completionHandler
+{
+ auto enabled = [_configuration preferences]->_preferences.get()->serviceWorkersEnabled() || WebCore::RuntimeEnabledFeatures::sharedFeatures().serviceWorkerEnabled();
+ completionHandler(enabled);
+}
+
+- (void)_clearServiceWorkerEntitlementOverride:(void (^)(void))completionHandler
+{
+ _page->clearServiceWorkerEntitlementOverride([completionHandler = makeBlockPtr(completionHandler)] {
+ completionHandler();
+ });
+}
+
- (id <_WKInputDelegate>)_inputDelegate
{
return _inputDelegate.getAutoreleased();
Modified: trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebViewConfiguration.mm (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebViewConfiguration.mm 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebViewConfiguration.mm 2020-04-18 00:54:41 UTC (rev 260303)
@@ -685,14 +685,14 @@
_allowTopNavigationToDataURLs = allowTopNavigationToDataURLs;
}
-- (BOOL)limitsNavigationToAppBoundDomains
+- (BOOL)limitsNavigationsToAppBoundDomains
{
- return _pageConfiguration->limitsNavigationToAppBoundDomains();
+ return _pageConfiguration->limitsNavigationsToAppBoundDomains();
}
-- (void)setLimitsNavigationToAppBoundDomains:(BOOL)limitsToAppBoundDomains
+- (void)setLimitsNavigationsToAppBoundDomains:(BOOL)limitsToAppBoundDomains
{
- _pageConfiguration->setLimitsNavigationToAppBoundDomains(limitsToAppBoundDomains);
+ _pageConfiguration->setLimitsNavigationsToAppBoundDomains(limitsToAppBoundDomains);
}
- (BOOL)_convertsPositionStyleOnCopy
Modified: trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebViewPrivate.h (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebViewPrivate.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebViewPrivate.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -343,6 +343,8 @@
- (void)_grantAccessToPreferenceService WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
+- (void)_serviceWorkersEnabled:(void(^)(BOOL))completionHandler WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
+- (void)_clearServiceWorkerEntitlementOverride:(void (^)(void))completionHandler WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
@end
#if TARGET_OS_IPHONE
Modified: trunk/Source/WebKit/UIProcess/Network/NetworkProcessProxy.cpp (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/Network/NetworkProcessProxy.cpp 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/Network/NetworkProcessProxy.cpp 2020-04-18 00:54:41 UTC (rev 260303)
@@ -1481,6 +1481,21 @@
sendWithAsyncReply(Messages::NetworkProcess::SetInAppBrowserPrivacyEnabled(sessionID, value), WTFMove(completionHandler));
}
+void NetworkProcessProxy::getAppBoundDomains(PAL::SessionID sessionID, CompletionHandler<void(HashSet<WebCore::RegistrableDomain>&&)>&& completionHandler)
+{
+#if PLATFORM(IOS_FAMILY)
+ if (auto* store = websiteDataStoreFromSessionID(sessionID)) {
+ store->getAppBoundDomains([completionHandler = WTFMove(completionHandler)] (auto& appBoundDomains) mutable {
+ auto appBoundDomainsCopy = appBoundDomains;
+ completionHandler(WTFMove(appBoundDomainsCopy));
+ });
+ return;
+ }
+ completionHandler({ });
+#else
+ completionHandler({ });
+#endif
+}
} // namespace WebKit
Modified: trunk/Source/WebKit/UIProcess/Network/NetworkProcessProxy.h (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/Network/NetworkProcessProxy.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/Network/NetworkProcessProxy.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -223,7 +223,8 @@
void hasAppBoundSession(PAL::SessionID, CompletionHandler<void(bool)>&&);
void setInAppBrowserPrivacyEnabled(PAL::SessionID, bool, CompletionHandler<void()>&&);
-
+ void getAppBoundDomains(PAL::SessionID, CompletionHandler<void(HashSet<WebCore::RegistrableDomain>&&)>&&);
+
private:
// AuxiliaryProcessProxy
ASCIILiteral processName() const final { return "Networking"_s; }
Modified: trunk/Source/WebKit/UIProcess/Network/NetworkProcessProxy.messages.in (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/Network/NetworkProcessProxy.messages.in 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/Network/NetworkProcessProxy.messages.in 2020-04-18 00:54:41 UTC (rev 260303)
@@ -67,6 +67,8 @@
SetWebProcessHasUploads(WebCore::ProcessIdentifier processID, bool hasUpload)
+ GetAppBoundDomains(PAL::SessionID sessionID) -> (HashSet<WebCore::RegistrableDomain> appBoundDomains) Async
+
RequestStorageSpace(PAL::SessionID sessionID, struct WebCore::ClientOrigin origin, uint64_t quota, uint64_t currentSize, uint64_t spaceRequired) -> (Optional<uint64_t> newQuota) Async
ResourceLoadDidSendRequest(WebKit::WebPageProxyIdentifier pageIdentifier, struct WebKit::ResourceLoadInfo resourceLoadInfo, WebCore::ResourceRequest request, Optional<IPC::FormDataReference> httpBody)
Modified: trunk/Source/WebKit/UIProcess/WebPageProxy.cpp (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/WebPageProxy.cpp 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/WebPageProxy.cpp 2020-04-18 00:54:41 UTC (rev 260303)
@@ -179,6 +179,7 @@
#include <WebCore/WindowFeatures.h>
#include <WebCore/WritingDirection.h>
#include <stdio.h>
+#include <wtf/CallbackAggregator.h>
#include <wtf/NeverDestroyed.h>
#include <wtf/Scope.h>
#include <wtf/SystemTracing.h>
@@ -485,7 +486,7 @@
, m_tryCloseTimeoutTimer(RunLoop::main(), this, &WebPageProxy::tryCloseTimedOut)
#if PLATFORM(COCOA)
, m_ignoresAppBoundDomains(m_configuration->ignoresAppBoundDomains() || WTF::processHasEntitlement("com.apple.private.applemediaservices"))
- , m_limitsNavigationToAppBoundDomains(m_configuration->limitsNavigationToAppBoundDomains())
+ , m_limitsNavigationsToAppBoundDomains(m_configuration->limitsNavigationsToAppBoundDomains())
#endif
{
RELEASE_LOG_IF_ALLOWED(Loading, "constructor:");
@@ -521,6 +522,9 @@
#if PLATFORM(IOS_FAMILY)
DeprecatedGlobalSettings::setDisableScreenSizeOverride(m_preferences->disableScreenSizeOverride());
+
+ if (m_configuration->preferences()->serviceWorkerEntitlementDisabledForTesting())
+ disableServiceWorkerEntitlementInNetworkProcess();
#endif
#if PLATFORM(COCOA)
@@ -3156,6 +3160,34 @@
completionHandler(m_isNavigatingToAppBoundDomain && (*m_isNavigatingToAppBoundDomain == NavigatingToAppBoundDomain::Yes));
}
+void WebPageProxy::disableServiceWorkerEntitlementInNetworkProcess()
+{
+#if PLATFORM(IOS_FAMILY)
+ if (auto* networkProcess = m_process->processPool().networkProcess()) {
+ if (!networkProcess->canSendMessage())
+ return;
+ networkProcess->send(Messages::NetworkProcess::DisableServiceWorkerEntitlement(), 0);
+ }
+#endif
+}
+
+void WebPageProxy::clearServiceWorkerEntitlementOverride(CompletionHandler<void()>&& completionHandler)
+{
+#if PLATFORM(IOS_FAMILY)
+ auto callbackAggregator = CallbackAggregator::create(WTFMove(completionHandler));
+ sendWithAsyncReply(Messages::WebPage::ClearServiceWorkerEntitlementOverride(), [callbackAggregator = callbackAggregator.copyRef()] { });
+ if (auto* networkProcess = m_process->processPool().networkProcess()) {
+ if (!networkProcess->canSendMessage()) {
+ completionHandler();
+ return;
+ }
+ networkProcess->sendWithAsyncReply(Messages::NetworkProcess::ClearServiceWorkerEntitlementOverride(), [callbackAggregator = callbackAggregator.copyRef()] { });
+ }
+#else
+ completionHandler();
+#endif
+}
+
void WebPageProxy::receivedNavigationPolicyDecision(PolicyAction policyAction, API::Navigation* navigation, ProcessSwapRequestedByClient processSwapRequestedByClient, WebFrameProxy& frame, RefPtr<API::WebsitePolicies>&& policies, Ref<PolicyDecisionSender>&& sender)
{
Ref<WebsiteDataStore> websiteDataStore = m_websiteDataStore.copyRef();
@@ -7804,6 +7836,7 @@
parameters.shouldCaptureVideoInGPUProcess = preferences().captureVideoInGPUProcessEnabled();
parameters.shouldRenderCanvasInGPUProcess = preferences().renderCanvasInGPUProcessEnabled();
parameters.shouldCaptureDisplayInUIProcess = m_process->processPool().configuration().shouldCaptureDisplayInUIProcess();
+ parameters.limitsNavigationsToAppBoundDomains = m_limitsNavigationsToAppBoundDomains;
#if PLATFORM(GTK)
parameters.themeName = pageClient().themeName();
Modified: trunk/Source/WebKit/UIProcess/WebPageProxy.h (260302 => 260303)
--- trunk/Source/WebKit/UIProcess/WebPageProxy.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/UIProcess/WebPageProxy.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -1729,6 +1729,9 @@
void isNavigatingToAppBoundDomainTesting(CompletionHandler<void(bool)>&&);
Optional<NavigatingToAppBoundDomain> isNavigatingToAppBoundDomain() const { return m_isNavigatingToAppBoundDomain; }
+ void disableServiceWorkerEntitlementInNetworkProcess();
+ void clearServiceWorkerEntitlementOverride(CompletionHandler<void()>&&);
+
#if PLATFORM(COCOA)
void grantAccessToCurrentPasteboardData(const String& pasteboardName);
#endif
@@ -2797,7 +2800,7 @@
NavigatedAwayFromAppBoundDomain m_hasNavigatedAwayFromAppBoundDomain { NavigatedAwayFromAppBoundDomain::No };
bool m_ignoresAppBoundDomains { false };
bool m_userScriptsNotified { false };
- bool m_limitsNavigationToAppBoundDomains { false };
+ bool m_limitsNavigationsToAppBoundDomains { false };
#if ENABLE(ROUTING_ARBITRATION)
std::unique_ptr<AudioSessionRoutingArbitratorProxy> m_routingArbitrator;
Modified: trunk/Source/WebKit/WebProcess/WebPage/WebPage.cpp (260302 => 260303)
--- trunk/Source/WebKit/WebProcess/WebPage/WebPage.cpp 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/WebProcess/WebPage/WebPage.cpp 2020-04-18 00:54:41 UTC (rev 260303)
@@ -460,6 +460,7 @@
#endif
, m_overriddenMediaType(parameters.overriddenMediaType)
, m_processDisplayName(parameters.processDisplayName)
+ , m_isNavigatingToAppBoundDomain(parameters.limitsNavigationsToAppBoundDomains ? NavigatingToAppBoundDomain::Yes : NavigatingToAppBoundDomain::No)
{
ASSERT(m_identifier);
@@ -3672,9 +3673,12 @@
#endif
#if ENABLE(SERVICE_WORKER)
+ if (store.getBoolValueForKey(WebPreferencesKey::serviceWorkerEntitlementDisabledForTestingKey()))
+ disableServiceWorkerEntitlement();
+
if (store.getBoolValueForKey(WebPreferencesKey::serviceWorkersEnabledKey())) {
- ASSERT(parentProcessHasServiceWorkerEntitlement());
- if (!parentProcessHasServiceWorkerEntitlement())
+ ASSERT(parentProcessHasServiceWorkerEntitlement() || m_isNavigatingToAppBoundDomain);
+ if (!parentProcessHasServiceWorkerEntitlement() && !m_isNavigatingToAppBoundDomain)
RuntimeEnabledFeatures::sharedFeatures().setServiceWorkerEnabled(false);
}
#endif
Modified: trunk/Source/WebKit/WebProcess/WebPage/WebPage.h (260302 => 260303)
--- trunk/Source/WebKit/WebProcess/WebPage/WebPage.h 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/WebProcess/WebPage/WebPage.h 2020-04-18 00:54:41 UTC (rev 260303)
@@ -1523,8 +1523,12 @@
#if PLATFORM(IOS_FAMILY)
bool parentProcessHasServiceWorkerEntitlement() const;
+ void disableServiceWorkerEntitlement();
+ void clearServiceWorkerEntitlementOverride(CompletionHandler<void()>&&);
#else
bool parentProcessHasServiceWorkerEntitlement() const { return true; }
+ void disableServiceWorkerEntitlement() { }
+ void clearServiceWorkerEntitlementOverride(CompletionHandler<void()>&& completionHandler) { completionHandler(); }
#endif
void didReceivePolicyDecision(WebCore::FrameIdentifier, uint64_t listenerID, PolicyDecision&&);
Modified: trunk/Source/WebKit/WebProcess/WebPage/WebPage.messages.in (260302 => 260303)
--- trunk/Source/WebKit/WebProcess/WebPage/WebPage.messages.in 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/WebProcess/WebPage/WebPage.messages.in 2020-04-18 00:54:41 UTC (rev 260303)
@@ -122,6 +122,7 @@
InsertTextPlaceholder(WebCore::IntSize size) -> (Optional<WebCore::ElementContext> placeholder) Async
RemoveTextPlaceholder(struct WebCore::ElementContext placeholder) -> () Async
FocusTextInputContextAndPlaceCaret(struct WebCore::ElementContext context, WebCore::IntPoint point) -> (bool success) Async
+ ClearServiceWorkerEntitlementOverride() -> () Async
#endif
SetControlledByAutomation(bool controlled)
Modified: trunk/Source/WebKit/WebProcess/WebPage/ios/WebPageIOS.mm (260302 => 260303)
--- trunk/Source/WebKit/WebProcess/WebPage/ios/WebPageIOS.mm 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Source/WebKit/WebProcess/WebPage/ios/WebPageIOS.mm 2020-04-18 00:54:41 UTC (rev 260303)
@@ -488,12 +488,28 @@
return sendResult && eventWasHandled;
}
+static bool disableServiceWorkerEntitlementTestingOverride;
+
bool WebPage::parentProcessHasServiceWorkerEntitlement() const
{
+ if (disableServiceWorkerEntitlementTestingOverride)
+ return false;
+
static bool hasEntitlement = WTF::hasEntitlement(WebProcess::singleton().parentProcessConnection()->xpcConnection(), "com.apple.developer.WebKit.ServiceWorkers");
return hasEntitlement;
}
+void WebPage::disableServiceWorkerEntitlement()
+{
+ disableServiceWorkerEntitlementTestingOverride = true;
+}
+
+void WebPage::clearServiceWorkerEntitlementOverride(CompletionHandler<void()>&& completionHandler)
+{
+ disableServiceWorkerEntitlementTestingOverride = false;
+ completionHandler();
+}
+
void WebPage::sendComplexTextInputToPlugin(uint64_t, const String&)
{
notImplemented();
Modified: trunk/Tools/ChangeLog (260302 => 260303)
--- trunk/Tools/ChangeLog 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Tools/ChangeLog 2020-04-18 00:54:41 UTC (rev 260303)
@@ -1,3 +1,18 @@
+2020-04-17 Kate Cheney <[email protected]>
+
+ Enable service workers for app-bound domains
+ https://bugs.webkit.org/show_bug.cgi?id=210451
+ <rdar://problem/61479474>
+
+ Reviewed by Brent Fulgham.
+
+ Adds 2 test cases to make sure service workers behave properly on
+ app bound domains, and that the APIs are not available on non-app
+ bound domains.
+
+ * TestWebKitAPI/Tests/WebKitCocoa/InAppBrowserPrivacy.mm:
+ (-[SWInAppBrowserPrivacyMessageHandler userContentController:didReceiveScriptMessage:]):
+
2020-04-17 Alex Christensen <[email protected]>
NetworkSessionCocoa should request client certificate only once per host/port
Modified: trunk/Tools/TestWebKitAPI/Tests/WebKitCocoa/InAppBrowserPrivacy.mm (260302 => 260303)
--- trunk/Tools/TestWebKitAPI/Tests/WebKitCocoa/InAppBrowserPrivacy.mm 2020-04-17 23:40:39 UTC (rev 260302)
+++ trunk/Tools/TestWebKitAPI/Tests/WebKitCocoa/InAppBrowserPrivacy.mm 2020-04-18 00:54:41 UTC (rev 260303)
@@ -26,6 +26,7 @@
#import "config.h"
#import "PlatformUtilities.h"
+#import "ServiceWorkerTCPServer.h"
#import "TestNavigationDelegate.h"
#import "TestWKWebView.h"
#import "WKWebViewConfigurationExtras.h"
@@ -743,6 +744,137 @@
TestWebKitAPI::Util::run(&done);
}
+@interface SWInAppBrowserPrivacyMessageHandler : NSObject <WKScriptMessageHandler>
+@end
+
+@implementation SWInAppBrowserPrivacyMessageHandler
+- (void)userContentController:(WKUserContentController *)userContentController didReceiveScriptMessage:(WKScriptMessage *)message
+{
+ EXPECT_WK_STREQ(@"Message from worker: ServiceWorker received: Hello from an app-bound domain", [message body]);
+ isDone = true;
+}
+@end
+
+static const char* mainBytes = R"SWRESOURCE(
+<script>
+
+function log(msg)
+{
+ window.webkit.messageHandlers.sw.postMessage(msg);
+}
+
+navigator.serviceWorker.addEventListener("message", function(event) {
+ log("Message from worker: " + event.data);
+});
+
+try {
+
+navigator.serviceWorker.register('/sw.js').then(function(reg) {
+ worker = reg.installing ? reg.installing : reg.active;
+ worker.postMessage("Hello from an app-bound domain");
+}).catch(function(error) {
+ log("Registration failed with: " + error);
+});
+} catch(e) {
+ log("Exception: " + e);
+}
+
+</script>
+)SWRESOURCE";
+
+static const char* scriptBytes = R"SWRESOURCE(
+
+self.addEventListener("message", (event) => {
+ event.source.postMessage("ServiceWorker received: " + event.data);
+});
+
+)SWRESOURCE";
+
+TEST(InAppBrowserPrivacy, AppBoundDomainAllowsServiceWorkers)
+{
+ initializeInAppBrowserPrivacyTestSettings();
+ isDone = false;
+
+ auto configuration = adoptNS([[WKWebViewConfiguration alloc] init]);
+ auto messageHandler = adoptNS([[SWInAppBrowserPrivacyMessageHandler alloc] init]);
+ [[configuration userContentController] addScriptMessageHandler:messageHandler.get() name:@"sw"];
+ [configuration preferences]._serviceWorkerEntitlementDisabledForTesting = YES;
+ [configuration setLimitsNavigationsToAppBoundDomains:YES];
+
+ auto webView = adoptNS([[WKWebView alloc] initWithFrame:NSMakeRect(0, 0, 800, 600) configuration:configuration.get()]);
+
+ ServiceWorkerTCPServer server1({
+ { "text/html", mainBytes },
+ { "application/_javascript_", scriptBytes},
+ });
+
+ [WKWebsiteDataStore _allowWebsiteDataRecordsForAllOrigins];
+
+ // Start with a clean slate data store
+ [[WKWebsiteDataStore defaultDataStore] removeDataOfTypes:[WKWebsiteDataStore allWebsiteDataTypes] modifiedSince:[NSDate distantPast] completionHandler:^() {
+ isDone = true;
+ }];
+ TestWebKitAPI::Util::run(&isDone);
+ isDone = false;
+
+ // Expect the service worker load to complete successfully.
+ [webView loadRequest:server1.requestWithLocalhost()];
+ TestWebKitAPI::Util::run(&isDone);
+ isDone = false;
+
+ [[WKWebsiteDataStore defaultDataStore] fetchDataRecordsOfTypes:[NSSet setWithObject:WKWebsiteDataTypeServiceWorkerRegistrations] completionHandler:^(NSArray<WKWebsiteDataRecord *> *websiteDataRecords) {
+ EXPECT_EQ(1u, [websiteDataRecords count]);
+ EXPECT_WK_STREQ(websiteDataRecords[0].displayName, "localhost");
+ isDone = true;
+ }];
+
+ TestWebKitAPI::Util::run(&isDone);
+ isDone = false;
+
+ // Reset service worker entitlement.
+ [webView _clearServiceWorkerEntitlementOverride:^(void) {
+ cleanUpInAppBrowserPrivacyTestSettings();
+ isDone = true;
+ }];
+ TestWebKitAPI::Util::run(&isDone);
+ isDone = false;
+}
+
+TEST(InAppBrowserPrivacy, NonAppBoundDomainDoesNotAllowServiceWorkers)
+{
+ initializeInAppBrowserPrivacyTestSettings();
+ isDone = false;
+
+ auto configuration = adoptNS([[WKWebViewConfiguration alloc] init]);
+ auto schemeHandler = adoptNS([[InAppBrowserSchemeHandler alloc] init]);
+ [configuration setURLSchemeHandler:schemeHandler.get() forURLScheme:@"in-app-browser"];
+ // Disable entitlement which allows service workers.
+ [configuration preferences]._serviceWorkerEntitlementDisabledForTesting = YES;
+
+ auto webView = adoptNS([[WKWebView alloc] initWithFrame:NSMakeRect(0, 0, 800, 600) configuration:configuration.get()]);
+
+ // Load a non-app bound domain.
+ NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:@"in-app-browser:///in-app-browser-privacy-test-user-style-sheets"]];
+ [webView loadRequest:request];
+ [webView _test_waitForDidFinishNavigation];
+
+ // Expect that service workers are disabled for this webView.
+ isDone = false;
+ [webView _serviceWorkersEnabled:^(BOOL enabled) {
+ EXPECT_FALSE(enabled);
+ isDone = true;
+ }];
+ TestWebKitAPI::Util::run(&isDone);
+
+ // Reset service worker entitlement.
+ [webView _clearServiceWorkerEntitlementOverride:^(void) {
+ cleanUpInAppBrowserPrivacyTestSettings();
+ isDone = true;
+ }];
+ TestWebKitAPI::Util::run(&isDone);
+ isDone = false;
+}
+
#endif // USE(APPLE_INTERNAL_SDK)
#endif // PLATFORM(IOS_FAMILY)