[WK2][NETWORK_SESSION] Add support for downloading file backed blobs
authorcdumez@apple.com <cdumez@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Wed, 9 Nov 2016 18:07:07 +0000 (18:07 +0000)
committercdumez@apple.com <cdumez@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Wed, 9 Nov 2016 18:07:07 +0000 (18:07 +0000)
https://bugs.webkit.org/show_bug.cgi?id=164458
<rdar://problem/28905514>

Reviewed by Darin Adler.

Source/WebKit2:

Add support for downloading file backed blobs on WebKit2.
It previously wasn't working because we weren't calling
BlobDataFileReference::prepareForFileAccess() for each blob file before
starting the download, similarly to what is done in NetworkResourceLoader's
consumeSandboxExtensions().

* NetworkProcess/Downloads/DownloadManager.cpp:
(WebKit::DownloadManager::startDownload):
* NetworkProcess/Downloads/DownloadManager.h:
(WebKit::DownloadManager::startDownload):
* NetworkProcess/NetworkConnectionToWebProcess.cpp:
(WebKit::NetworkConnectionToWebProcess::startDownload):
(WebKit::NetworkConnectionToWebProcess::convertMainResourceLoadToDownload):
* NetworkProcess/NetworkDataTask.cpp:
(WebKit::NetworkDataTask::create):
* NetworkProcess/NetworkDataTask.h:
* NetworkProcess/NetworkDataTaskBlob.cpp:
(WebKit::NetworkDataTaskBlob::NetworkDataTaskBlob):
(WebKit::NetworkDataTaskBlob::~NetworkDataTaskBlob):
(WebKit::NetworkDataTaskBlob::download):
* NetworkProcess/NetworkDataTaskBlob.h:
* NetworkProcess/NetworkLoad.cpp:
(WebKit::NetworkLoad::NetworkLoad):
* NetworkProcess/NetworkLoadParameters.h:
* NetworkProcess/NetworkProcess.cpp:
(WebKit::NetworkProcess::downloadRequest):
* NetworkProcess/NetworkResourceLoader.cpp:
(WebKit::NetworkResourceLoader::NetworkResourceLoader):
(WebKit::NetworkResourceLoader::startNetworkLoad):
* NetworkProcess/PingLoad.h:

Tools:

Add testRunner.setShouldDownloadUndisplayableMIMETypes(bool) API so that layout
tests can request that such resources are downloaded instead of being ignored.

* WebKitTestRunner/InjectedBundle/Bindings/TestRunner.idl:
* WebKitTestRunner/InjectedBundle/TestRunner.cpp:
(WTR::TestRunner::setShouldDownloadUndisplayableMIMETypes):
* WebKitTestRunner/InjectedBundle/TestRunner.h:
* WebKitTestRunner/TestController.cpp:
(WTR::TestController::decidePolicyForNavigationResponse):
* WebKitTestRunner/TestController.h:
(WTR::TestController::setShouldDownloadUndisplayableMIMETypes):
* WebKitTestRunner/TestInvocation.cpp:
(WTR::TestInvocation::didReceiveMessageFromInjectedBundle):

LayoutTests:

Add layout test coverage for downloading blobs, both via <a download> or
because a load is later converted into a download.

* fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download-expected.txt: Added.
* fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html: Added.
* fast/dom/HTMLAnchorElement/anchor-file-blob-download-expected.txt: Added.
* fast/dom/HTMLAnchorElement/anchor-file-blob-download.html: Added.
* platform/ios-simulator-wk1/TestExpectations:
* platform/ios-simulator-wk2/TestExpectations:
* platform/mac-wk1/TestExpectations:
* platform/win/TestExpectations:

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@208438 268f45cc-cd09-0410-ab3c-d52691b4dbfc

31 files changed:
LayoutTests/ChangeLog
LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download-expected.txt [new file with mode: 0644]
LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html [new file with mode: 0644]
LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-download-expected.txt [new file with mode: 0644]
LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-download.html [new file with mode: 0644]
LayoutTests/platform/ios-simulator-wk1/TestExpectations
LayoutTests/platform/ios-simulator-wk2/TestExpectations
LayoutTests/platform/mac-wk1/TestExpectations
LayoutTests/platform/mac-wk2/TestExpectations
LayoutTests/platform/win/TestExpectations
Source/WebCore/platform/network/BlobResourceHandle.cpp
Source/WebKit2/ChangeLog
Source/WebKit2/NetworkProcess/Downloads/DownloadManager.cpp
Source/WebKit2/NetworkProcess/Downloads/DownloadManager.h
Source/WebKit2/NetworkProcess/NetworkConnectionToWebProcess.cpp
Source/WebKit2/NetworkProcess/NetworkDataTask.cpp
Source/WebKit2/NetworkProcess/NetworkDataTask.h
Source/WebKit2/NetworkProcess/NetworkDataTaskBlob.cpp
Source/WebKit2/NetworkProcess/NetworkDataTaskBlob.h
Source/WebKit2/NetworkProcess/NetworkLoad.cpp
Source/WebKit2/NetworkProcess/NetworkLoadParameters.h
Source/WebKit2/NetworkProcess/NetworkProcess.cpp
Source/WebKit2/NetworkProcess/NetworkResourceLoader.cpp
Source/WebKit2/NetworkProcess/PingLoad.h
Tools/ChangeLog
Tools/WebKitTestRunner/InjectedBundle/Bindings/TestRunner.idl
Tools/WebKitTestRunner/InjectedBundle/TestRunner.cpp
Tools/WebKitTestRunner/InjectedBundle/TestRunner.h
Tools/WebKitTestRunner/TestController.cpp
Tools/WebKitTestRunner/TestController.h
Tools/WebKitTestRunner/TestInvocation.cpp

index 2aa88d9..6388d77 100644 (file)
@@ -1,5 +1,25 @@
 2016-11-09  Chris Dumez  <cdumez@apple.com>
 
+        [WK2][NETWORK_SESSION] Add support for downloading file backed blobs
+        https://bugs.webkit.org/show_bug.cgi?id=164458
+        <rdar://problem/28905514>
+
+        Reviewed by Darin Adler.
+
+        Add layout test coverage for downloading blobs, both via <a download> or
+        because a load is later converted into a download.
+
+        * fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download-expected.txt: Added.
+        * fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html: Added.
+        * fast/dom/HTMLAnchorElement/anchor-file-blob-download-expected.txt: Added.
+        * fast/dom/HTMLAnchorElement/anchor-file-blob-download.html: Added.
+        * platform/ios-simulator-wk1/TestExpectations:
+        * platform/ios-simulator-wk2/TestExpectations:
+        * platform/mac-wk1/TestExpectations:
+        * platform/win/TestExpectations:
+
+2016-11-09  Chris Dumez  <cdumez@apple.com>
+
         [WK2] Network cache speculative revalidation can cause loads to hang
         https://bugs.webkit.org/show_bug.cgi?id=164532
         <rdar://problem/28519331>
diff --git a/LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download-expected.txt b/LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download-expected.txt
new file mode 100644 (file)
index 0000000..11140fd
--- /dev/null
@@ -0,0 +1,6 @@
+Download started.
+Downloading URL with suggested filename "unknown"
+Download completed.
+The download should succeed.
+
+File backed blob URL
diff --git a/LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html b/LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html
new file mode 100644 (file)
index 0000000..b618800
--- /dev/null
@@ -0,0 +1,37 @@
+<!DOCTYPE html>
+<html>
+<head>
+<script type='text/javascript'>
+if (window.testRunner) {
+  testRunner.dumpAsText();
+  testRunner.waitUntilDone();
+  testRunner.setShouldDownloadUndisplayableMIMETypes(true);
+}
+</script>
+</head>
+<body>
+<p>The download should succeed.</p>
+<a id="blob-url">File backed blob URL</a>
+<script>
+function click(elmt)
+{
+    if (!window.eventSender) {
+        alert('Click the link to run the test.');
+        return;
+    }
+    eventSender.mouseMoveTo(elmt.offsetLeft + 5, elmt.offsetTop + 5);
+    eventSender.mouseDown();
+    eventSender.mouseUp();
+}
+
+function runTest()
+{
+    file = internals.createFile("../../../resources/Ahem.otf");
+    var link = document.getElementById("blob-url");
+    link.href = window.URL.createObjectURL(file);
+    click(link);
+}
+runTest();
+</script>
+</body>
+</html>
diff --git a/LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-download-expected.txt b/LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-download-expected.txt
new file mode 100644 (file)
index 0000000..8a0e5ff
--- /dev/null
@@ -0,0 +1,6 @@
+Download started.
+Downloading URL with suggested filename "abe.png"
+Download completed.
+The suggested filename above should be "abe.png" and the download should succeed.
+
+File backed blob URL
diff --git a/LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-download.html b/LayoutTests/fast/dom/HTMLAnchorElement/anchor-file-blob-download.html
new file mode 100644 (file)
index 0000000..61871cd
--- /dev/null
@@ -0,0 +1,36 @@
+<!DOCTYPE html>
+<html>
+<head>
+<script type='text/javascript'>
+if (window.testRunner) {
+  testRunner.dumpAsText();
+  testRunner.waitUntilDone();
+}
+</script>
+</head>
+<body>
+<p>The suggested filename above should be "abe.png" and the download should succeed.</p>
+<a id="blob-url" download="abe.png">File backed blob URL</a>
+<script>
+function click(elmt)
+{
+    if (!window.eventSender) {
+        alert('Click the link to run the test.');
+        return;
+    }
+    eventSender.mouseMoveTo(elmt.offsetLeft + 5, elmt.offsetTop + 5);
+    eventSender.mouseDown();
+    eventSender.mouseUp();
+}
+
+function runTest()
+{
+    file = internals.createFile("../resources/abe.png");
+    var link = document.getElementById("blob-url");
+    link.href = window.URL.createObjectURL(file);
+    click(link);
+}
+runTest();
+</script>
+</body>
+</html>
index 53e3e6a..8827a46 100644 (file)
@@ -1332,12 +1332,16 @@ webkit.org/b/155495 compositing/visible-rect/animated-from-none.html [ Failure P
 # <a download> is not supported in WK1 yet.
 webkit.org/b/156069 fast/dom/HTMLAnchorElement/anchor-download-synthetic-click.html [ Skip ]
 webkit.org/b/156069 fast/dom/HTMLAnchorElement/anchor-download-user-triggered-synthetic-click.html [ Skip ]
+webkit.org/b/156069 fast/dom/HTMLAnchorElement/anchor-file-blob-download.html [ Skip ]
 webkit.org/b/156069 http/tests/download/area-download.html [ Skip ]
 webkit.org/b/156069 http/tests/security/anchor-download-allow-blob.html [ Skip ]
 webkit.org/b/156069 http/tests/security/anchor-download-allow-data.html [ Skip ]
 webkit.org/b/156069 http/tests/security/anchor-download-allow-sameorigin.html [ Skip ]
 webkit.org/b/156069 http/tests/security/anchor-download-block-crossorigin.html [ Skip ]
 
+# testRunner.setShouldDownloadUndisplayableMIMETypes() is not supported on WK1.
+fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html [ Skip ]
+
 webkit.org/b/137572 scrollbars/scrollbar-iframe-click-does-not-blur-content.html [ Failure ]
 
 # This test relies on a settings option that we can only set with WKRT.
index e0516a5..6d01b07 100644 (file)
@@ -1815,6 +1815,8 @@ webkit.org/b/155948 transitions/cancel-transition.html [ Pass Failure ]
 # <a download> does not work on iOS.
 webkit.org/b/156067 fast/dom/HTMLAnchorElement/anchor-download-unset.html [ Skip ]
 webkit.org/b/156067 fast/dom/HTMLAnchorElement/anchor-download.html [ Skip ]
+webkit.org/b/156067 fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html [ Skip ]
+webkit.org/b/156067 fast/dom/HTMLAnchorElement/anchor-file-blob-download.html [ Skip ]
 webkit.org/b/156067 fast/dom/HTMLAnchorElement/anchor-nodownload-set.html [ Skip ]
 webkit.org/b/156067 fast/dom/HTMLAnchorElement/anchor-nodownload.html [ Skip ]
 webkit.org/b/156067 fast/dom/HTMLAnchorElement/anchor-download-synthetic-click.html [ Skip ]
index 27887ea..663a0fd 100644 (file)
@@ -197,12 +197,16 @@ webkit.org/b/156069 fast/dom/HTMLAnchorElement/anchor-nodownload-set.html [ Fail
 webkit.org/b/156069 fast/dom/HTMLAnchorElement/anchor-download.html [ Failure ]
 webkit.org/b/156069 fast/dom/HTMLAnchorElement/anchor-download-synthetic-click.html [ Skip ]
 webkit.org/b/156069 fast/dom/HTMLAnchorElement/anchor-download-user-triggered-synthetic-click.html [ Skip ]
+webkit.org/b/156069 fast/dom/HTMLAnchorElement/anchor-file-blob-download.html [ Skip ]
 webkit.org/b/156069 http/tests/download/area-download.html [ Skip ]
 webkit.org/b/156069 http/tests/security/anchor-download-allow-blob.html [ Skip ]
 webkit.org/b/156069 http/tests/security/anchor-download-allow-data.html [ Skip ]
 webkit.org/b/156069 http/tests/security/anchor-download-allow-sameorigin.html [ Skip ]
 webkit.org/b/156069 http/tests/security/anchor-download-block-crossorigin.html [ Skip ]
 
+# testRunner.setShouldDownloadUndisplayableMIMETypes() is not supported on WK1.
+fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html [ Skip ]
+
 webkit.org/b/156629 imported/w3c/web-platform-tests/html/semantics/embedded-content/the-img-element/sizes/parse-a-sizes-attribute.html [ Pass Failure ]
 
 webkit.org/b/157007 fast/layers/no-clipping-overflow-hidden-added-after-transform.html [ Pass ImageOnlyFailure ]
index a5ee1f6..c9e525d 100644 (file)
@@ -493,6 +493,10 @@ webkit.org/b/158639 [ Release Yosemite ] imported/blink/storage/indexeddb/blob-d
 # rdar://problem/26885345
 [ Sierra+ ] media/click-placeholder-not-pausing.html [ Pass ]
 
+# Download of file backed blob URLs is broken for !NETWORK_SESSION code path.
+webkit.org/b/164522 [ Yosemite ElCapitan ] fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html [ Failure ]
+webkit.org/b/164522 [ Yosemite ElCapitan ] fast/dom/HTMLAnchorElement/anchor-file-blob-download.html [ Failure ]
+
 # RTL Scrollbars are enabled on Sierra WebKit2.
 [ Sierra+ ] fast/scrolling/rtl-scrollbars.html [ Pass ]
 [ Sierra+ ] fast/scrolling/rtl-scrollbars-simple.html [ Pass ]
index d52b0e3..4dbbe63 100644 (file)
@@ -447,10 +447,14 @@ fast/dom/HTMLAnchorElement/anchor-nodownload-set.html [ Skip ]
 fast/dom/HTMLAnchorElement/anchor-download-unset.html [ Skip ]
 fast/dom/HTMLAnchorElement/anchor-download-synthetic-click.html [ Skip ]
 fast/dom/HTMLAnchorElement/anchor-download-user-triggered-synthetic-click.html [ Skip ]
+fast/dom/HTMLAnchorElement/anchor-file-blob-download.html [ Skip ]
 http/tests/download/area-download.html [ Skip ]
 http/tests/security/anchor-download-allow-data.html [ Skip ]
 http/tests/security/anchor-download-allow-sameorigin.html [ Skip ]
 
+# testRunner.setShouldDownloadUndisplayableMIMETypes() is not supported on WK1.
+fast/dom/HTMLAnchorElement/anchor-file-blob-convert-to-download.html [ Skip ]
+
 # TODO Expose title direction in WebKit API (Chromium Only)
 webkit.org/b/58845 fast/dom/title-directionality.html [ Skip ]
 webkit.org/b/58845 fast/dom/title-directionality-removeChild.html [ Skip ]
index 853b1eb..952e744 100644 (file)
@@ -150,6 +150,7 @@ BlobResourceHandle::~BlobResourceHandle()
 void BlobResourceHandle::cancel()
 {
     m_asyncStream = nullptr;
+    m_fileOpened = false;
 
     m_aborted = true;
 
index 8cbe3bf..c45fd40 100644 (file)
@@ -1,5 +1,44 @@
 2016-11-09  Chris Dumez  <cdumez@apple.com>
 
+        [WK2][NETWORK_SESSION] Add support for downloading file backed blobs
+        https://bugs.webkit.org/show_bug.cgi?id=164458
+        <rdar://problem/28905514>
+
+        Reviewed by Darin Adler.
+
+        Add support for downloading file backed blobs on WebKit2.
+        It previously wasn't working because we weren't calling
+        BlobDataFileReference::prepareForFileAccess() for each blob file before
+        starting the download, similarly to what is done in NetworkResourceLoader's
+        consumeSandboxExtensions().
+
+        * NetworkProcess/Downloads/DownloadManager.cpp:
+        (WebKit::DownloadManager::startDownload):
+        * NetworkProcess/Downloads/DownloadManager.h:
+        (WebKit::DownloadManager::startDownload):
+        * NetworkProcess/NetworkConnectionToWebProcess.cpp:
+        (WebKit::NetworkConnectionToWebProcess::startDownload):
+        (WebKit::NetworkConnectionToWebProcess::convertMainResourceLoadToDownload):
+        * NetworkProcess/NetworkDataTask.cpp:
+        (WebKit::NetworkDataTask::create):
+        * NetworkProcess/NetworkDataTask.h:
+        * NetworkProcess/NetworkDataTaskBlob.cpp:
+        (WebKit::NetworkDataTaskBlob::NetworkDataTaskBlob):
+        (WebKit::NetworkDataTaskBlob::~NetworkDataTaskBlob):
+        (WebKit::NetworkDataTaskBlob::download):
+        * NetworkProcess/NetworkDataTaskBlob.h:
+        * NetworkProcess/NetworkLoad.cpp:
+        (WebKit::NetworkLoad::NetworkLoad):
+        * NetworkProcess/NetworkLoadParameters.h:
+        * NetworkProcess/NetworkProcess.cpp:
+        (WebKit::NetworkProcess::downloadRequest):
+        * NetworkProcess/NetworkResourceLoader.cpp:
+        (WebKit::NetworkResourceLoader::NetworkResourceLoader):
+        (WebKit::NetworkResourceLoader::startNetworkLoad):
+        * NetworkProcess/PingLoad.h:
+
+2016-11-09  Chris Dumez  <cdumez@apple.com>
+
         [WK2] Network cache speculative revalidation can cause loads to hang
         https://bugs.webkit.org/show_bug.cgi?id=164532
         <rdar://problem/28519331>
index b406de7..1cc6c35 100644 (file)
@@ -27,6 +27,7 @@
 #include "DownloadManager.h"
 
 #include "Download.h"
+#include "NetworkBlobRegistry.h"
 #include "NetworkLoad.h"
 #include "NetworkSession.h"
 #include "PendingDownload.h"
@@ -44,16 +45,20 @@ DownloadManager::DownloadManager(Client& client)
 {
 }
 
-void DownloadManager::startDownload(SessionID sessionID, DownloadID downloadID, const ResourceRequest& request, const String& suggestedName)
+void DownloadManager::startDownload(NetworkConnectionToWebProcess* connection, SessionID sessionID, DownloadID downloadID, const ResourceRequest& request, const String& suggestedName)
 {
 #if USE(NETWORK_SESSION)
     auto* networkSession = SessionTracker::networkSession(sessionID);
     if (!networkSession)
         return;
+
     NetworkLoadParameters parameters;
     parameters.sessionID = sessionID;
     parameters.request = request;
     parameters.clientCredentialPolicy = ClientCredentialPolicy::MayAskClientForCredentials;
+    if (request.url().protocolIsBlob() && connection)
+        parameters.blobFileReferences = NetworkBlobRegistry::singleton().filesInBlob(*connection, parameters.request.url());
+
     m_pendingDownloads.add(downloadID, std::make_unique<PendingDownload>(WTFMove(parameters), downloadID, *networkSession, suggestedName));
 #else
     auto download = std::make_unique<Download>(*this, downloadID, request, suggestedName);
index 9063f84..1874955 100644 (file)
@@ -51,6 +51,7 @@ namespace WebKit {
 
 class AuthenticationManager;
 class Download;
+class NetworkConnectionToWebProcess;
 class PendingDownload;
 
 class DownloadManager {
@@ -72,7 +73,7 @@ public:
 
     explicit DownloadManager(Client&);
 
-    void startDownload(WebCore::SessionID, DownloadID, const WebCore::ResourceRequest&, const String& suggestedName = { });
+    void startDownload(NetworkConnectionToWebProcess*, WebCore::SessionID, DownloadID, const WebCore::ResourceRequest&, const String& suggestedName = { });
 #if USE(NETWORK_SESSION)
     void dataTaskBecameDownloadTask(DownloadID, std::unique_ptr<Download>&&);
 #if USE(PROTECTION_SPACE_AUTH_CALLBACK)
index 0e63c3f..76f69a4 100644 (file)
@@ -189,14 +189,14 @@ static NetworkStorageSession& storageSession(SessionID sessionID)
 
 void NetworkConnectionToWebProcess::startDownload(SessionID sessionID, DownloadID downloadID, const ResourceRequest& request, const String& suggestedName)
 {
-    NetworkProcess::singleton().downloadManager().startDownload(sessionID, downloadID, request, suggestedName);
+    NetworkProcess::singleton().downloadManager().startDownload(this, sessionID, downloadID, request, suggestedName);
 }
 
 void NetworkConnectionToWebProcess::convertMainResourceLoadToDownload(SessionID sessionID, uint64_t mainResourceLoadIdentifier, DownloadID downloadID, const ResourceRequest& request, const ResourceResponse& response)
 {
     auto& networkProcess = NetworkProcess::singleton();
     if (!mainResourceLoadIdentifier) {
-        networkProcess.downloadManager().startDownload(sessionID, downloadID, request);
+        networkProcess.downloadManager().startDownload(this, sessionID, downloadID, request);
         return;
     }
 
index dbb065d..e946f41 100644 (file)
@@ -29,6 +29,7 @@
 #if USE(NETWORK_SESSION)
 
 #include "NetworkDataTaskBlob.h"
+#include "NetworkLoadParameters.h"
 #include "NetworkSession.h"
 #include <wtf/MainThread.h>
 
@@ -43,16 +44,16 @@ using namespace WebCore;
 
 namespace WebKit {
 
-Ref<NetworkDataTask> NetworkDataTask::create(NetworkSession& session, NetworkDataTaskClient& client, const ResourceRequest& request, StoredCredentials storedCredentials, ContentSniffingPolicy shouldContentSniff, bool shouldClearReferrerOnHTTPSToHTTPRedirect)
+Ref<NetworkDataTask> NetworkDataTask::create(NetworkSession& session, NetworkDataTaskClient& client, const NetworkLoadParameters& parameters)
 {
-    if (request.url().protocolIsBlob())
-        return NetworkDataTaskBlob::create(session, client, request, shouldContentSniff);
+    if (parameters.request.url().protocolIsBlob())
+        return NetworkDataTaskBlob::create(session, client, parameters.request, parameters.contentSniffingPolicy, parameters.blobFileReferences);
 
 #if PLATFORM(COCOA)
-    return NetworkDataTaskCocoa::create(session, client, request, storedCredentials, shouldContentSniff, shouldClearReferrerOnHTTPSToHTTPRedirect);
+    return NetworkDataTaskCocoa::create(session, client, parameters.request, parameters.allowStoredCredentials, parameters.contentSniffingPolicy, parameters.shouldClearReferrerOnHTTPSToHTTPRedirect);
 #endif
 #if USE(SOUP)
-    return NetworkDataTaskSoup::create(session, client, request, storedCredentials, shouldContentSniff, shouldClearReferrerOnHTTPSToHTTPRedirect);
+    return NetworkDataTaskSoup::create(session, client, parameters.request, parameters.allowStoredCredentials, parameters.contentSniffingPolicy, parameters.shouldClearReferrerOnHTTPSToHTTPRedirect);
 #endif
 }
 
index 6da41c2..9eb1bb8 100644 (file)
@@ -48,6 +48,7 @@ class SharedBuffer;
 namespace WebKit {
 
 class Download;
+class NetworkLoadParameters;
 class NetworkSession;
 class PendingDownload;
 enum class AuthenticationChallengeDisposition;
@@ -73,7 +74,7 @@ public:
 
 class NetworkDataTask : public RefCounted<NetworkDataTask> {
 public:
-    static Ref<NetworkDataTask> create(NetworkSession&, NetworkDataTaskClient&, const WebCore::ResourceRequest&, WebCore::StoredCredentials, WebCore::ContentSniffingPolicy, bool shouldClearReferrerOnHTTPSToHTTPRedirect);
+    static Ref<NetworkDataTask> create(NetworkSession&, NetworkDataTaskClient&, const NetworkLoadParameters&);
 
     virtual ~NetworkDataTask();
 
index a296d65..c383b4f 100644 (file)
@@ -73,17 +73,25 @@ static const char* httpInternalErrorText = "Internal Server Error";
 
 static const char* const webKitBlobResourceDomain = "WebKitBlobResource";
 
-NetworkDataTaskBlob::NetworkDataTaskBlob(NetworkSession& session, NetworkDataTaskClient& client, const ResourceRequest& request, ContentSniffingPolicy shouldContentSniff)
+NetworkDataTaskBlob::NetworkDataTaskBlob(NetworkSession& session, NetworkDataTaskClient& client, const ResourceRequest& request, ContentSniffingPolicy shouldContentSniff, const Vector<RefPtr<WebCore::BlobDataFileReference>>& fileReferences)
     : NetworkDataTask(session, client, request, DoNotAllowStoredCredentials, false)
-    , m_blobData(static_cast<BlobRegistryImpl&>(blobRegistry()).getBlobDataFromURL(request.url()))
     , m_stream(std::make_unique<AsyncFileStream>(*this))
+    , m_fileReferences(fileReferences)
 {
+    for (auto& fileReference : m_fileReferences)
+        fileReference->prepareForFileAccess();
+
+    m_blobData = static_cast<BlobRegistryImpl&>(blobRegistry()).getBlobDataFromURL(request.url());
+
     m_session->registerNetworkDataTask(*this);
     LOG(NetworkSession, "%p - Created NetworkDataTaskBlob for %s", this, request.url().string().utf8().data());
 }
 
 NetworkDataTaskBlob::~NetworkDataTaskBlob()
 {
+    for (auto& fileReference : m_fileReferences)
+        fileReference->revokeFileAccess();
+
     clearStream();
     m_session->unregisterNetworkDataTask(*this);
 }
@@ -472,8 +480,8 @@ void NetworkDataTaskBlob::download()
     downloadManager.dataTaskBecameDownloadTask(m_pendingDownloadID, WTFMove(download));
     downloadPtr->didCreateDestination(m_pendingDownloadLocation);
 
-    ASSERT(m_client);
-    m_client->didBecomeDownload();
+    if (m_client)
+        m_client->didBecomeDownload();
 
     m_buffer.resize(bufferSize);
     read();
index 8a26363..48ce504 100644 (file)
@@ -39,6 +39,7 @@
 
 namespace WebCore {
 class AsyncFileStream;
+class BlobDataFileReference;
 class BlobData;
 class BlobDataItem;
 }
@@ -47,15 +48,15 @@ namespace WebKit {
 
 class NetworkDataTaskBlob final : public NetworkDataTask, public WebCore::FileStreamClient {
 public:
-    static Ref<NetworkDataTask> create(NetworkSession& session, NetworkDataTaskClient& client, const WebCore::ResourceRequest& request, WebCore::ContentSniffingPolicy shouldContentSniff)
+    static Ref<NetworkDataTask> create(NetworkSession& session, NetworkDataTaskClient& client, const WebCore::ResourceRequest& request, WebCore::ContentSniffingPolicy shouldContentSniff, const Vector<RefPtr<WebCore::BlobDataFileReference>>& fileReferences)
     {
-        return adoptRef(*new NetworkDataTaskBlob(session, client, request, shouldContentSniff));
+        return adoptRef(*new NetworkDataTaskBlob(session, client, request, shouldContentSniff, fileReferences));
     }
 
     ~NetworkDataTaskBlob();
 
 private:
-    NetworkDataTaskBlob(NetworkSession&, NetworkDataTaskClient&, const WebCore::ResourceRequest&, WebCore::ContentSniffingPolicy);
+    NetworkDataTaskBlob(NetworkSession&, NetworkDataTaskClient&, const WebCore::ResourceRequest&, WebCore::ContentSniffingPolicy, const Vector<RefPtr<WebCore::BlobDataFileReference>>&);
 
     void suspend() override;
     void cancel() override;
@@ -113,6 +114,8 @@ private:
     unsigned m_readItemCount { 0 };
     bool m_fileOpened { false };
     WebCore::PlatformFileHandle m_downloadFile { WebCore::invalidPlatformFileHandle };
+
+    Vector<RefPtr<WebCore::BlobDataFileReference>> m_fileReferences;
     RefPtr<SandboxExtension> m_sandboxExtension;
 };
 
index 1267505..0b35f74 100644 (file)
@@ -67,7 +67,7 @@ NetworkLoad::NetworkLoad(NetworkLoadClient& client, NetworkLoadParameters&& para
     , m_parameters(WTFMove(parameters))
     , m_currentRequest(m_parameters.request)
 {
-    m_task = NetworkDataTask::create(networkSession, *this, m_parameters.request, m_parameters.allowStoredCredentials, m_parameters.contentSniffingPolicy, m_parameters.shouldClearReferrerOnHTTPSToHTTPRedirect);
+    m_task = NetworkDataTask::create(networkSession, *this, m_parameters);
     if (!m_parameters.defersLoading)
         m_task->resume();
 }
index 4d2d455..d064beb 100644 (file)
@@ -26,6 +26,7 @@
 #ifndef NetworkLoadParameters_h
 #define NetworkLoadParameters_h
 
+#include <WebCore/BlobDataFileReference.h>
 #include <WebCore/ResourceLoaderOptions.h>
 #include <WebCore/ResourceRequest.h>
 #include <WebCore/SessionID.h>
@@ -45,6 +46,9 @@ public:
     bool shouldClearReferrerOnHTTPSToHTTPRedirect { true };
     bool defersLoading { false };
     bool needsCertificateInfo { false };
+#if USE(NETWORK_SESSION)
+    Vector<RefPtr<WebCore::BlobDataFileReference>> blobFileReferences;
+#endif
 };
 
 } // namespace WebKit
index 1270e3b..8e9e79a 100644 (file)
@@ -466,7 +466,7 @@ void NetworkProcess::deleteWebsiteDataForOrigins(SessionID sessionID, OptionSet<
 
 void NetworkProcess::downloadRequest(SessionID sessionID, DownloadID downloadID, const ResourceRequest& request, const String& suggestedFilename)
 {
-    downloadManager().startDownload(sessionID, downloadID, request, suggestedFilename);
+    downloadManager().startDownload(nullptr, sessionID, downloadID, request, suggestedFilename);
 }
 
 void NetworkProcess::resumeDownload(SessionID sessionID, DownloadID downloadID, const IPC::DataReference& resumeData, const String& path, const WebKit::SandboxExtension::Handle& sandboxExtensionHandle)
index 371e6d5..28cebf8 100644 (file)
@@ -98,10 +98,13 @@ NetworkResourceLoader::NetworkResourceLoader(const NetworkResourceLoadParameters
         }
     }
 
+#if !USE(NETWORK_SESSION)
     if (originalRequest().url().protocolIsBlob()) {
         ASSERT(!m_parameters.resourceSandboxExtension);
         m_fileReferences.appendVector(NetworkBlobRegistry::singleton().filesInBlob(connection, originalRequest().url()));
     }
+#endif
+
 
     if (synchronousReply)
         m_synchronousLoadData = std::make_unique<SynchronousLoadData>(WTFMove(synchronousReply));
@@ -219,6 +222,9 @@ void NetworkResourceLoader::startNetworkLoad(const ResourceRequest& request)
     parameters.request = request;
 
 #if USE(NETWORK_SESSION)
+    if (request.url().protocolIsBlob())
+        parameters.blobFileReferences = NetworkBlobRegistry::singleton().filesInBlob(m_connection, originalRequest().url());
+
     auto* networkSession = SessionTracker::networkSession(parameters.sessionID);
     if (!networkSession) {
         WTFLogAlways("Attempted to create a NetworkLoad with a session (id=%" PRIu64 ") that does not exist.", parameters.sessionID.sessionID());
index 5f3da3a..4f931ff 100644 (file)
@@ -39,7 +39,7 @@ public:
         , m_shouldFollowRedirects(parameters.shouldFollowRedirects)
     {
         if (auto* networkSession = SessionTracker::networkSession(parameters.sessionID)) {
-            m_task = NetworkDataTask::create(*networkSession, *this, parameters.request, parameters.allowStoredCredentials, parameters.contentSniffingPolicy, parameters.shouldClearReferrerOnHTTPSToHTTPRedirect);
+            m_task = NetworkDataTask::create(*networkSession, *this, parameters);
             m_task->resume();
         } else
             ASSERT_NOT_REACHED();
index 7b72e0a..2ba2c40 100644 (file)
@@ -1,3 +1,25 @@
+2016-11-09  Chris Dumez  <cdumez@apple.com>
+
+        [WK2][NETWORK_SESSION] Add support for downloading file backed blobs
+        https://bugs.webkit.org/show_bug.cgi?id=164458
+        <rdar://problem/28905514>
+
+        Reviewed by Darin Adler.
+
+        Add testRunner.setShouldDownloadUndisplayableMIMETypes(bool) API so that layout
+        tests can request that such resources are downloaded instead of being ignored.
+
+        * WebKitTestRunner/InjectedBundle/Bindings/TestRunner.idl:
+        * WebKitTestRunner/InjectedBundle/TestRunner.cpp:
+        (WTR::TestRunner::setShouldDownloadUndisplayableMIMETypes):
+        * WebKitTestRunner/InjectedBundle/TestRunner.h:
+        * WebKitTestRunner/TestController.cpp:
+        (WTR::TestController::decidePolicyForNavigationResponse):
+        * WebKitTestRunner/TestController.h:
+        (WTR::TestController::setShouldDownloadUndisplayableMIMETypes):
+        * WebKitTestRunner/TestInvocation.cpp:
+        (WTR::TestInvocation::didReceiveMessageFromInjectedBundle):
+
 2016-11-09  Jonathan Bedard  <jbedard@apple.com>
 
         Make rpaths more robust for iOS Simulators
index de507fb..54dc768 100644 (file)
@@ -81,6 +81,7 @@ interface TestRunner {
     void setShouldDecideNavigationPolicyAfterDelay(boolean value);
     void setNavigationGesturesEnabled(boolean value);
     void setIgnoresViewportScaleLimits(boolean value);
+    void setShouldDownloadUndisplayableMIMETypes(boolean value);
 
     // Special DOM functions.
     void clearBackForwardList();
index 492b6b2..50ed7a5 100644 (file)
@@ -1022,6 +1022,13 @@ void TestRunner::setIgnoresViewportScaleLimits(bool value)
     WKBundlePagePostMessage(InjectedBundle::singleton().page()->page(), messageName.get(), messageBody.get());
 }
 
+void TestRunner::setShouldDownloadUndisplayableMIMETypes(bool value)
+{
+    WKRetainPtr<WKStringRef> messageName(AdoptWK, WKStringCreateWithUTF8CString("SetShouldDownloadUndisplayableMIMETypes"));
+    WKRetainPtr<WKBooleanRef> messageBody(AdoptWK, WKBooleanCreate(value));
+    WKBundlePagePostMessage(InjectedBundle::singleton().page()->page(), messageName.get(), messageBody.get());
+}
+
 static unsigned nextUIScriptCallbackID()
 {
     static unsigned callbackID = FirstUIScriptCallbackID;
index 01360c8..fec09f1 100644 (file)
@@ -311,6 +311,7 @@ public:
     void setShouldDecideNavigationPolicyAfterDelay(bool);
     void setNavigationGesturesEnabled(bool);
     void setIgnoresViewportScaleLimits(bool);
+    void setShouldDownloadUndisplayableMIMETypes(bool);
 
     void runUIScript(JSStringRef script, JSValueRef callback);
     void runUIScriptCallback(unsigned callbackID, JSStringRef result);
index 94722ae..282e909 100644 (file)
@@ -2061,7 +2061,10 @@ void TestController::decidePolicyForNavigationResponse(WKNavigationResponseRef n
         return;
     }
 
-    WKFramePolicyListenerIgnore(listener);
+    if (m_shouldDownloadUndisplayableMIMETypes)
+        WKFramePolicyListenerDownload(listener);
+    else
+        WKFramePolicyListenerIgnore(listener);
 }
 
 void TestController::didNavigateWithNavigationData(WKContextRef, WKPageRef, WKNavigationDataRef navigationData, WKFrameRef frame, const void* clientInfo)
index 53cd261..2f071b6 100644 (file)
@@ -142,6 +142,8 @@ public:
     void setNavigationGesturesEnabled(bool value);
     void setIgnoresViewportScaleLimits(bool);
 
+    void setShouldDownloadUndisplayableMIMETypes(bool value) { m_shouldDownloadUndisplayableMIMETypes = value; }
+
 private:
     WKRetainPtr<WKPageConfigurationRef> generatePageConfiguration(WKContextConfigurationRef);
     WKRetainPtr<WKContextConfigurationRef> generateContextConfiguration() const;
@@ -324,6 +326,7 @@ private:
 
     bool m_policyDelegateEnabled { false };
     bool m_policyDelegatePermissive { false };
+    bool m_shouldDownloadUndisplayableMIMETypes { false };
 
     bool m_rejectsProtectionSpaceAndContinueForAuthenticationChallenges { false };
     bool m_handlesAuthenticationChallenges { false };
index b26668d..ecfae49 100644 (file)
@@ -687,6 +687,13 @@ void TestInvocation::didReceiveMessageFromInjectedBundle(WKStringRef messageName
         return;
     }
 
+    if (WKStringIsEqualToUTF8CString(messageName, "SetShouldDownloadUndisplayableMIMETypes")) {
+        ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
+        WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
+        TestController::singleton().setShouldDownloadUndisplayableMIMETypes(WKBooleanGetValue(value));
+        return;
+    }
+
     if (WKStringIsEqualToUTF8CString(messageName, "RunUIProcessScript")) {
         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
         WKRetainPtr<WKStringRef> scriptKey(AdoptWK, WKStringCreateWithUTF8CString("Script"));