diff options
author | skerner@chromium.org <skerner@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-08-27 14:22:12 +0000 |
---|---|---|
committer | skerner@chromium.org <skerner@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-08-27 14:22:12 +0000 |
commit | 2747dd8492489e9b5efa322990185537c9557c60 (patch) | |
tree | 7992f279958da0a98978f1848bfb2119c0721cd8 | |
parent | e5a00caa638c720ed9257c57e98b0f8476ce5853 (diff) | |
download | chromium_src-2747dd8492489e9b5efa322990185537c9557c60.zip chromium_src-2747dd8492489e9b5efa322990185537c9557c60.tar.gz chromium_src-2747dd8492489e9b5efa322990185537c9557c60.tar.bz2 |
Implement window.chrome.app.isInstalled .
BUG=49225
TEST=ExtensionBrowserTest.PropertyAppIsInstalled
Review URL: http://codereview.chromium.org/3169045
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@57674 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r-- | chrome/browser/extensions/extension_browsertests_misc.cc | 90 | ||||
-rw-r--r-- | chrome/chrome_renderer.gypi | 4 | ||||
-rw-r--r-- | chrome/renderer/extensions/chrome_app_bindings.cc | 61 | ||||
-rw-r--r-- | chrome/renderer/extensions/chrome_app_bindings.h | 28 | ||||
-rw-r--r-- | chrome/renderer/render_thread.cc | 3 | ||||
-rw-r--r-- | chrome/test/data/extensions/app_dot_com_app/manifest.json | 11 |
6 files changed, 192 insertions, 5 deletions
diff --git a/chrome/browser/extensions/extension_browsertests_misc.cc b/chrome/browser/extensions/extension_browsertests_misc.cc index 9076447..f504c4f 100644 --- a/chrome/browser/extensions/extension_browsertests_misc.cc +++ b/chrome/browser/extensions/extension_browsertests_misc.cc @@ -81,9 +81,20 @@ IN_PROC_BROWSER_TEST_F(ExtensionBrowserTest, OriginPrivileges) { ASSERT_TRUE(LoadExtension(test_data_dir_ .AppendASCII("origin_privileges").AppendASCII("extension"))); + GURL origin_privileges_index( + test_server()->GetURL("files/extensions/origin_privileges/index.html")); + + std::string host_a("a.com"); + GURL::Replacements make_host_a_com; + make_host_a_com.SetHostStr(host_a); + + std::string host_b("b.com"); + GURL::Replacements make_host_b_com; + make_host_b_com.SetHostStr(host_b); + // A web host that has permission. - ui_test_utils::NavigateToURL(browser(), - GURL("http://a.com:1337/files/extensions/origin_privileges/index.html")); + ui_test_utils::NavigateToURL( + browser(), origin_privileges_index.ReplaceComponents(make_host_a_com)); std::string result; ui_test_utils::ExecuteJavaScriptAndExtractString( browser()->GetSelectedTabContents()->render_view_host(), L"", @@ -92,8 +103,8 @@ IN_PROC_BROWSER_TEST_F(ExtensionBrowserTest, OriginPrivileges) { EXPECT_EQ(result, "Loaded"); // A web host that does not have permission. - ui_test_utils::NavigateToURL(browser(), - GURL("http://b.com:1337/files/extensions/origin_privileges/index.html")); + ui_test_utils::NavigateToURL( + browser(), origin_privileges_index.ReplaceComponents(make_host_b_com)); ui_test_utils::ExecuteJavaScriptAndExtractString( browser()->GetSelectedTabContents()->render_view_host(), L"", L"window.domAutomationController.send(document.title)", @@ -782,3 +793,74 @@ IN_PROC_BROWSER_TEST_F(ExtensionBrowserTest, DISABLED_OptionsPage) { EXPECT_EQ(extension->GetResourceURL("options.html"), tab_strip->GetTabContentsAt(1)->GetURL()); } + +// Test window.chrome.app.isInstalled . +IN_PROC_BROWSER_TEST_F(ExtensionBrowserTest, PropertyAppIsInstalled) { + + std::string app_host("app.com"); + std::string nonapp_host("nonapp.com"); + + host_resolver()->AddRule(app_host, "127.0.0.1"); + host_resolver()->AddRule(nonapp_host, "127.0.0.1"); + ASSERT_TRUE(test_server()->Start()); + + GURL test_file_url(test_server()->GetURL("files/extensions/test_file.html")); + GURL::Replacements replace_host; + + replace_host.SetHostStr(app_host); + GURL app_url(test_file_url.ReplaceComponents(replace_host)); + + replace_host.SetHostStr(nonapp_host); + GURL non_app_url(test_file_url.ReplaceComponents(replace_host)); + + + // Load an app which includes app.com in its extent. + ASSERT_TRUE(LoadExtension( + test_data_dir_.AppendASCII("app_dot_com_app"))); + + + // Test that a non-app page has chrome.app.isInstalled = false. + ui_test_utils::NavigateToURL(browser(), non_app_url); + std::wstring get_app_is_installed = + L"window.domAutomationController.send(" + L" JSON.stringify(window.chrome.app.isInstalled));"; + std::string result; + ASSERT_TRUE( + ui_test_utils::ExecuteJavaScriptAndExtractString( + browser()->GetSelectedTabContents()->render_view_host(), + L"", + get_app_is_installed.c_str(), + &result)); + EXPECT_EQ("false", result); + + + // Check that an app page has chrome.app.isInstalled = true. + ui_test_utils::NavigateToURL(browser(), app_url); + ASSERT_TRUE( + ui_test_utils::ExecuteJavaScriptAndExtractString( + browser()->GetSelectedTabContents()->render_view_host(), + L"", + get_app_is_installed.c_str(), + &result)); + EXPECT_EQ("true", result); + + + // Test that trying to set window.chrome.app.isInstalled throws + // an exception. + ASSERT_TRUE( + ui_test_utils::ExecuteJavaScriptAndExtractString( + browser()->GetSelectedTabContents()->render_view_host(), + L"", + L"window.domAutomationController.send(" + L" function() {" + L" try {" + L" window.chrome.app.isInstalled = false;" + L" return 'BAD: Should have thrown by now...';" + L" } catch (e) {" + L" return 'GOOD: Saw expected error.';" + L" }" + L" }()" + L");", + &result)); + EXPECT_EQ("GOOD: Saw expected error.", result); +} diff --git a/chrome/chrome_renderer.gypi b/chrome/chrome_renderer.gypi index b47adea..3a632bd 100644 --- a/chrome/chrome_renderer.gypi +++ b/chrome/chrome_renderer.gypi @@ -1,4 +1,4 @@ -# Copyright (c) 2009 The Chromium Authors. All rights reserved. +# 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. @@ -51,6 +51,8 @@ 'renderer/automation/dom_automation_v8_extension.h', 'renderer/extensions/bindings_utils.cc', 'renderer/extensions/bindings_utils.h', + 'renderer/extensions/chrome_app_bindings.cc', + 'renderer/extensions/chrome_app_bindings.h', 'renderer/extensions/event_bindings.cc', 'renderer/extensions/event_bindings.h', 'renderer/extensions/extension_process_bindings.cc', diff --git a/chrome/renderer/extensions/chrome_app_bindings.cc b/chrome/renderer/extensions/chrome_app_bindings.cc new file mode 100644 index 0000000..37558dc --- /dev/null +++ b/chrome/renderer/extensions/chrome_app_bindings.cc @@ -0,0 +1,61 @@ +// 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/renderer/extensions/chrome_app_bindings.h" + +#include "chrome/renderer/render_thread.h" +#include "third_party/WebKit/WebKit/chromium/public/WebFrame.h" +#include "v8/include/v8.h" + +using WebKit::WebFrame; + +namespace extensions_v8 { + +static const char* const kAppExtensionName = "v8/ChromeApp"; + +class ChromeAppExtensionWrapper : public v8::Extension { + public: + ChromeAppExtensionWrapper() : + v8::Extension(kAppExtensionName, + "var chrome;" + "if (!chrome)" + " chrome = {};" + "if (!chrome.app) {" + " chrome.app = new function() {" + " native function GetIsInstalled();" + " this.__defineGetter__('isInstalled', GetIsInstalled);" + " };" + "}") {} + + virtual v8::Handle<v8::FunctionTemplate> GetNativeFunction( + v8::Handle<v8::String> name) { + if (name->Equals(v8::String::New("GetIsInstalled"))) { + return v8::FunctionTemplate::New(GetIsInstalled); + } + return v8::Handle<v8::FunctionTemplate>(); + } + + static v8::Handle<v8::Value> GetIsInstalled(const v8::Arguments& args) { + WebFrame* frame = WebFrame::frameForCurrentContext(); + if (!frame) + return v8::Boolean::New(false); + + GURL url(frame->url()); + if (url.is_empty() || + !url.is_valid() || + !(url.SchemeIs("http") || url.SchemeIs("https"))) + return v8::Boolean::New(false); + + bool has_web_extent = + !RenderThread::current()->GetExtensionIdByURL(url).empty(); + + return v8::Boolean::New(has_web_extent); + } +}; + +v8::Extension* ChromeAppExtension::Get() { + return new ChromeAppExtensionWrapper(); +} + +} // namespace extensions_v8 diff --git a/chrome/renderer/extensions/chrome_app_bindings.h b/chrome/renderer/extensions/chrome_app_bindings.h new file mode 100644 index 0000000..1292eb2 --- /dev/null +++ b/chrome/renderer/extensions/chrome_app_bindings.h @@ -0,0 +1,28 @@ +// 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. + +// The AppObjectExtension is a v8 extension that creates an object +// at window.chrome.app. This object allows javascript to get details +// on the app state of the page. +// The read-only property app.isInstalled is true if the current page is +// within the extent of an installed, enabled app. + +#ifndef CHROME_RENDERER_EXTENSIONS_CHROME_APP_BINDINGS_H_ +#define CHROME_RENDERER_EXTENSIONS_CHROME_APP_BINDINGS_H_ +#pragma once + +namespace v8 { +class Extension; +} + +namespace extensions_v8 { + +class ChromeAppExtension { + public: + static v8::Extension* Get(); +}; + +} // namespace extensions_v8 + +#endif // CHROME_RENDERER_EXTENSIONS_CHROME_APP_BINDINGS_H_ diff --git a/chrome/renderer/render_thread.cc b/chrome/renderer/render_thread.cc index c105ae3..83754f7 100644 --- a/chrome/renderer/render_thread.cc +++ b/chrome/renderer/render_thread.cc @@ -47,6 +47,7 @@ #include "chrome/renderer/cookie_message_filter.h" #include "chrome/renderer/devtools_agent_filter.h" #include "chrome/renderer/extension_groups.h" +#include "chrome/renderer/extensions/chrome_app_bindings.h" #include "chrome/renderer/extensions/event_bindings.h" #include "chrome/renderer/extensions/extension_process_bindings.h" #include "chrome/renderer/extensions/js_only_v8_extensions.h" @@ -855,6 +856,8 @@ void RenderThread::EnsureWebKitInitialized() { WebScriptController::registerExtension( extensions_v8::LoadTimesExtension::Get()); WebScriptController::registerExtension( + extensions_v8::ChromeAppExtension::Get()); + WebScriptController::registerExtension( extensions_v8::ExternalExtension::Get()); const WebKit::WebString kExtensionScheme = diff --git a/chrome/test/data/extensions/app_dot_com_app/manifest.json b/chrome/test/data/extensions/app_dot_com_app/manifest.json new file mode 100644 index 0000000..bf55770 --- /dev/null +++ b/chrome/test/data/extensions/app_dot_com_app/manifest.json @@ -0,0 +1,11 @@ +{ + "name": "App Dot Com: The App", + "version": "0.1", + "app": { + "launch": { + "container": "tab", + "web_url": "http://app.com/" + }, + "urls": [ "http://app.com/" ] + } +} |