Re-land 42631: The problem was that notifications aren't implemented on linux/views yet.

[email protected]

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@42671 0039d316-1c4b-4281-b951-d872f2087c98
diff --git a/chrome/browser/extensions/extension_dom_ui.cc b/chrome/browser/extensions/extension_dom_ui.cc
index 7ee7339d..7d8d15d 100644
--- a/chrome/browser/extensions/extension_dom_ui.cc
+++ b/chrome/browser/extensions/extension_dom_ui.cc
@@ -67,7 +67,8 @@
   NavigationController& controller = tab_contents()->controller();
   const GURL& url = controller.GetActiveEntry()->url();
   extension_function_dispatcher_.reset(
-      new ExtensionFunctionDispatcher(render_view_host, this, url));
+      ExtensionFunctionDispatcher::Create(render_view_host, this, url));
+  DCHECK(extension_function_dispatcher_.get());
 }
 
 void ExtensionDOMUI::ResetExtensionBookmarkManagerEventRouter() {
diff --git a/chrome/browser/extensions/extension_function_dispatcher.cc b/chrome/browser/extensions/extension_function_dispatcher.cc
index f436d27..76a2300 100644
--- a/chrome/browser/extensions/extension_function_dispatcher.cc
+++ b/chrome/browser/extensions/extension_function_dispatcher.cc
@@ -263,9 +263,26 @@
   return &instances;
 }
 
+ExtensionFunctionDispatcher* ExtensionFunctionDispatcher::Create(
+    RenderViewHost* render_view_host,
+    Delegate* delegate,
+    const GURL& url) {
+  ExtensionsService* service =
+      render_view_host->process()->profile()->GetExtensionsService();
+  DCHECK(service);
+
+  Extension* extension = service->GetExtensionByURL(url);
+  if (extension)
+    return new ExtensionFunctionDispatcher(render_view_host, delegate,
+                                           extension, url);
+  else
+    return NULL;
+}
+
 ExtensionFunctionDispatcher::ExtensionFunctionDispatcher(
     RenderViewHost* render_view_host,
     Delegate* delegate,
+    Extension* extension,
     const GURL& url)
   : profile_(render_view_host->process()->profile()),
     render_view_host_(render_view_host),
@@ -274,9 +291,6 @@
     ALLOW_THIS_IN_INITIALIZER_LIST(peer_(new Peer(this))) {
   // TODO(erikkay) should we do something for these errors in Release?
   DCHECK(url.SchemeIs(chrome::kExtensionScheme));
-
-  Extension* extension =
-      profile()->GetExtensionsService()->GetExtensionByURL(url);
   DCHECK(extension);
 
   all_instances()->insert(this);
diff --git a/chrome/browser/extensions/extension_function_dispatcher.h b/chrome/browser/extensions/extension_function_dispatcher.h
index 18cce3b..86342cc0 100644
--- a/chrome/browser/extensions/extension_function_dispatcher.h
+++ b/chrome/browser/extensions/extension_function_dispatcher.h
@@ -77,12 +77,15 @@
   // Resets all functions to their initial implementation.
   static void ResetFunctions();
 
+  // Creates an instance for the specified RenderViewHost and URL. If the URL
+  // does not contain a valid extension, returns NULL.
+  static ExtensionFunctionDispatcher* Create(RenderViewHost* render_view_host,
+                                             Delegate* delegate,
+                                             const GURL& url);
+
   // Retrieves a vector of all EFD instances.
   static std::set<ExtensionFunctionDispatcher*>* all_instances();
 
-  ExtensionFunctionDispatcher(RenderViewHost* render_view_host,
-                              Delegate* delegate,
-                              const GURL& url);
   ~ExtensionFunctionDispatcher();
 
   Delegate* delegate() { return delegate_; }
@@ -123,6 +126,11 @@
   RenderViewHost* render_view_host() { return render_view_host_; }
 
  private:
+  ExtensionFunctionDispatcher(RenderViewHost* render_view_host,
+                              Delegate* delegate,
+                              Extension* extension,
+                              const GURL& url);
+
   // We need to keep a pointer to the profile because we use it in the dtor
   // in sending EXTENSION_FUNCTION_DISPATCHER_DESTROYED, but by that point
   // the render_view_host_ has been deleted.
diff --git a/chrome/browser/extensions/extension_host.cc b/chrome/browser/extensions/extension_host.cc
index a57780b..b8baf39 100644
--- a/chrome/browser/extensions/extension_host.cc
+++ b/chrome/browser/extensions/extension_host.cc
@@ -324,7 +324,7 @@
       << extension_->name();
   url_ = params.url;
   extension_function_dispatcher_.reset(
-      new ExtensionFunctionDispatcher(render_view_host_, this, url_));
+      ExtensionFunctionDispatcher::Create(render_view_host_, this, url_));
 }
 
 void ExtensionHost::InsertInfobarCSS() {
@@ -676,7 +676,7 @@
   LOG(INFO) << "(RenderViewCreated) Resetting EFD to " << url_.spec() << " for "
       << extension_->name();
   extension_function_dispatcher_.reset(
-      new ExtensionFunctionDispatcher(render_view_host, this, url_));
+      ExtensionFunctionDispatcher::Create(render_view_host, this, url_));
 
   if (extension_host_type_ == ViewType::EXTENSION_TOOLSTRIP ||
       extension_host_type_ == ViewType::EXTENSION_MOLE ||
diff --git a/chrome/browser/extensions/fragment_navigation_apitest.cc b/chrome/browser/extensions/fragment_navigation_apitest.cc
index 7524c9120..00bc536 100644
--- a/chrome/browser/extensions/fragment_navigation_apitest.cc
+++ b/chrome/browser/extensions/fragment_navigation_apitest.cc
@@ -16,4 +16,3 @@
   const char* extension_name = "executescript/fragment";
   ASSERT_TRUE(RunExtensionTest(extension_name)) << message_;
 }
-
diff --git a/chrome/browser/extensions/notifications_apitest.cc b/chrome/browser/extensions/notifications_apitest.cc
new file mode 100644
index 0000000..2fd86fa
--- /dev/null
+++ b/chrome/browser/extensions/notifications_apitest.cc
@@ -0,0 +1,15 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chrome/browser/extensions/extension_apitest.h"
+
+
+IN_PROC_BROWSER_TEST_F(ExtensionApiTest, Notifications) {
+#if defined(OS_LINUX) && defined(TOOLKIT_VIEWS)
+  // Notifications not supported on linux/views yet.
+#else
+  ASSERT_TRUE(RunExtensionTest("notifications/has_permission")) << message_;
+  ASSERT_TRUE(RunExtensionTest("notifications/has_not_permission")) << message_;
+#endif
+}