Upstream version 9.38.198.0
[platform/framework/web/crosswalk.git] / src / content / browser / service_worker / service_worker_request_handler.cc
index 1ad1f3c..7b615b3 100644 (file)
@@ -4,6 +4,8 @@
 
 #include "content/browser/service_worker/service_worker_request_handler.h"
 
+#include <string>
+
 #include "content/browser/service_worker/service_worker_context_core.h"
 #include "content/browser/service_worker/service_worker_context_wrapper.h"
 #include "content/browser/service_worker/service_worker_provider_host.h"
@@ -12,6 +14,8 @@
 #include "content/browser/service_worker/service_worker_utils.h"
 #include "content/common/service_worker/service_worker_types.h"
 #include "net/url_request/url_request.h"
+#include "net/url_request/url_request_interceptor.h"
+#include "webkit/browser/blob/blob_storage_context.h"
 
 namespace content {
 
@@ -20,11 +24,11 @@ namespace {
 int kUserDataKey;  // Key value is not important.
 
 class ServiceWorkerRequestInterceptor
-    : public net::URLRequestJobFactory::ProtocolHandler {
+    : public net::URLRequestInterceptor {
  public:
   ServiceWorkerRequestInterceptor() {}
   virtual ~ServiceWorkerRequestInterceptor() {}
-  virtual net::URLRequestJob* MaybeCreateJob(
+  virtual net::URLRequestJob* MaybeInterceptRequest(
       net::URLRequest* request,
       net::NetworkDelegate* network_delegate) const OVERRIDE {
     ServiceWorkerRequestHandler* handler =
@@ -38,16 +42,27 @@ class ServiceWorkerRequestInterceptor
   DISALLOW_COPY_AND_ASSIGN(ServiceWorkerRequestInterceptor);
 };
 
+bool IsMethodSupportedForAppCache(const std::string& method) {
+  return (method == "GET") || (method == "HEAD");
+}
+
+bool IsSchemeAndMethodSupportedForAppCache(const net::URLRequest* request) {
+  return request->url().SchemeIsHTTPOrHTTPS() &&
+         IsMethodSupportedForAppCache(request->method());
+}
+
 }  // namespace
 
 void ServiceWorkerRequestHandler::InitializeHandler(
     net::URLRequest* request,
     ServiceWorkerContextWrapper* context_wrapper,
+    webkit_blob::BlobStorageContext* blob_storage_context,
     int process_id,
     int provider_id,
-    ResourceType::Type resource_type) {
-  if (!ServiceWorkerUtils::IsFeatureEnabled())
+    ResourceType resource_type) {
+  if (!IsSchemeAndMethodSupportedForAppCache(request)) {
     return;
+  }
 
   if (!context_wrapper || !context_wrapper->context() ||
       provider_id == kInvalidServiceWorkerProviderId) {
@@ -56,16 +71,15 @@ void ServiceWorkerRequestHandler::InitializeHandler(
 
   ServiceWorkerProviderHost* provider_host =
       context_wrapper->context()->GetProviderHost(process_id, provider_id);
-  if (!provider_host)
+  if (!provider_host || !provider_host->IsContextAlive())
     return;
 
-  if (!provider_host->ShouldHandleRequest(resource_type))
+  scoped_ptr<ServiceWorkerRequestHandler> handler(
+      provider_host->CreateRequestHandler(resource_type,
+                                          blob_storage_context->AsWeakPtr()));
+  if (!handler)
     return;
 
-  scoped_ptr<ServiceWorkerRequestHandler> handler(
-      new ServiceWorkerRequestHandler(context_wrapper->context()->AsWeakPtr(),
-                                      provider_host->AsWeakPtr(),
-                                      resource_type));
   request->SetUserData(&kUserDataKey, handler.release());
 }
 
@@ -75,100 +89,24 @@ ServiceWorkerRequestHandler* ServiceWorkerRequestHandler::GetHandler(
       request->GetUserData(&kUserDataKey));
 }
 
-scoped_ptr<net::URLRequestJobFactory::ProtocolHandler>
+scoped_ptr<net::URLRequestInterceptor>
 ServiceWorkerRequestHandler::CreateInterceptor() {
-  return make_scoped_ptr<net::URLRequestJobFactory::ProtocolHandler>(
+  return scoped_ptr<net::URLRequestInterceptor>(
       new ServiceWorkerRequestInterceptor);
 }
 
 ServiceWorkerRequestHandler::~ServiceWorkerRequestHandler() {
 }
 
-net::URLRequestJob* ServiceWorkerRequestHandler::MaybeCreateJob(
-    net::URLRequest* request,
-    net::NetworkDelegate* network_delegate) {
-  if (!context_ || !provider_host_) {
-    // We can't do anything other than to fall back to network.
-    job_ = NULL;
-    return NULL;
-  }
-
-  // This may get called multiple times for original and redirect requests:
-  // A. original request case: job_ is null, no previous location info.
-  // B. redirect or restarted request case:
-  //  a) job_ is non-null if the previous location was forwarded to SW.
-  //  b) job_ is null if the previous location was fallback.
-  //  c) job_ is non-null if additional restart was required to fall back.
-
-  // We've come here by restart, we already have original request and it
-  // tells we should fallback to network. (Case B-c)
-  if (job_.get() && job_->ShouldFallbackToNetwork()) {
-    job_ = NULL;
-    return NULL;
-  }
-
-  // It's for original request (A) or redirect case (B-a or B-b).
-  DCHECK(!job_.get() || job_->ShouldForwardToServiceWorker());
-
-  job_ = new ServiceWorkerURLRequestJob(request, network_delegate,
-                                        provider_host_);
-  if (ServiceWorkerUtils::IsMainResourceType(resource_type_))
-    PrepareForMainResource(request->url());
-  else
-    PrepareForSubResource();
-
-  if (job_->ShouldFallbackToNetwork()) {
-    // If we know we can fallback to network at this point (in case
-    // the storage lookup returned immediately), just return NULL here to
-    // fallback to network.
-    job_ = NULL;
-    return NULL;
-  }
-
-  return job_.get();
-}
-
 ServiceWorkerRequestHandler::ServiceWorkerRequestHandler(
     base::WeakPtr<ServiceWorkerContextCore> context,
     base::WeakPtr<ServiceWorkerProviderHost> provider_host,
-    ResourceType::Type resource_type)
+    base::WeakPtr<webkit_blob::BlobStorageContext> blob_storage_context,
+    ResourceType resource_type)
     : context_(context),
       provider_host_(provider_host),
-      resource_type_(resource_type),
-      weak_factory_(this) {
-}
-
-void ServiceWorkerRequestHandler::PrepareForMainResource(const GURL& url) {
-  DCHECK(job_.get());
-  DCHECK(context_);
-  // The corresponding provider_host may already have associate version in
-  // redirect case, unassociate it now.
-  provider_host_->AssociateVersion(NULL);
-  context_->storage()->FindRegistrationForDocument(
-      url,
-      base::Bind(&self::DidLookupRegistrationForMainResource,
-                  weak_factory_.GetWeakPtr()));
-}
-
-void ServiceWorkerRequestHandler::DidLookupRegistrationForMainResource(
-    ServiceWorkerStatusCode status,
-    const scoped_refptr<ServiceWorkerRegistration>& registration) {
-  DCHECK(job_.get());
-  if (status != SERVICE_WORKER_OK || !registration->active_version()) {
-    // No registration, or no active version for the registration is available.
-    job_->FallbackToNetwork();
-    return;
-  }
-  DCHECK(registration);
-  provider_host_->AssociateVersion(registration->active_version());
-  job_->ForwardToServiceWorker();
-}
-
-void ServiceWorkerRequestHandler::PrepareForSubResource() {
-  DCHECK(job_.get());
-  DCHECK(context_);
-  DCHECK(provider_host_->associated_version());
-  job_->ForwardToServiceWorker();
+      blob_storage_context_(blob_storage_context),
+      resource_type_(resource_type) {
 }
 
 }  // namespace content