summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorkalman@chromium.org <kalman@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-01-29 16:53:45 +0000
committerkalman@chromium.org <kalman@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-01-29 16:53:45 +0000
commit1dbc10e1ded96c967fa804dd040d1425f6bda127 (patch)
tree59c48915d88cc088e65d31a71f5eab57dd164913
parent7415e329ce844348328e54a99d36f31dc72d890c (diff)
downloadchromium_src-1dbc10e1ded96c967fa804dd040d1425f6bda127.zip
chromium_src-1dbc10e1ded96c967fa804dd040d1425f6bda127.tar.gz
chromium_src-1dbc10e1ded96c967fa804dd040d1425f6bda127.tar.bz2
Merge 243959 "Register bindings for blessed web contexts (aka ho..."
> Register bindings for blessed web contexts (aka hosted app contexts) by hand > rather than automatically; this allows them to be treated like web contexts > rather than extension contexts, which allows the more complex bindings rules > for making the messaging APIs (chrome.runtime.connect/sendMessage) available. > Make them available. > > BUG=326250 > R=koz@chromium.org > > Review URL: https://codereview.chromium.org/114803007 TBR=kalman@chromium.org Review URL: https://codereview.chromium.org/135393006 git-svn-id: svn://svn.chromium.org/chrome/branches/1750/src@247703 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/browser/extensions/extension_messages_apitest.cc41
-rw-r--r--chrome/common/extensions/api/_api_features.json3
-rw-r--r--chrome/renderer/extensions/chrome_v8_context.cc11
-rw-r--r--chrome/renderer/extensions/dispatcher.cc4
-rw-r--r--chrome/renderer/extensions/runtime_custom_bindings.cc8
5 files changed, 62 insertions, 5 deletions
diff --git a/chrome/browser/extensions/extension_messages_apitest.cc b/chrome/browser/extensions/extension_messages_apitest.cc
index 5853612..c1505cf 100644
--- a/chrome/browser/extensions/extension_messages_apitest.cc
+++ b/chrome/browser/extensions/extension_messages_apitest.cc
@@ -226,7 +226,8 @@ class ExternallyConnectableMessagingTest : public ExtensionApiTest {
"onMessage",
"onMessageExternal",
"onRestartRequired",
- "id",
+ // Note: no "id" here because this test method is used for hosted apps,
+ // which do have access to runtime.id.
};
// Turn the array into a JS array, which effectively gets eval()ed.
@@ -313,6 +314,25 @@ class ExternallyConnectableMessagingTest : public ExtensionApiTest {
connectable_with_tls_channel_id_manifest());
}
+ const Extension* LoadChromiumHostedApp() {
+ const Extension* hosted_app =
+ LoadExtensionIntoDir(&hosted_app_dir_, base::StringPrintf(
+ "{"
+ " \"name\": \"chromium_hosted_app\","
+ " \"version\": \"1.0\","
+ " \"manifest_version\": 2,"
+ " \"app\": {"
+ " \"urls\": [\"%s\"],"
+ " \"launch\": {"
+ " \"web_url\": \"%s\""
+ " }\n"
+ " }\n"
+ "}", chromium_org_url().spec().c_str(),
+ chromium_org_url().spec().c_str()));
+ CHECK(hosted_app);
+ return hosted_app;
+ }
+
void InitializeTestServer() {
base::FilePath test_data;
EXPECT_TRUE(PathService::Get(chrome::DIR_TEST_DATA, &test_data));
@@ -392,6 +412,7 @@ class ExternallyConnectableMessagingTest : public ExtensionApiTest {
TestExtensionDir web_connectable_dir_;
TestExtensionDir not_connectable_dir_;
TestExtensionDir tls_channel_id_connectable_dir_;
+ TestExtensionDir hosted_app_dir_;
};
IN_PROC_BROWSER_TEST_F(ExternallyConnectableMessagingTest, NotInstalled) {
@@ -903,5 +924,23 @@ IN_PROC_BROWSER_TEST_F(ExtensionApiTest, MessagingUserGesture) {
"});", receiver->id().c_str())));
}
+// Tests that a hosted app on a connectable site doesn't interfere with the
+// connectability of that site.
+IN_PROC_BROWSER_TEST_F(ExternallyConnectableMessagingTest, HostedAppOnWebsite) {
+ InitializeTestServer();
+
+ LoadChromiumHostedApp();
+
+ // The presence of the hosted app shouldn't give the ability to send messages.
+ ui_test_utils::NavigateToURL(browser(), chromium_org_url());
+ EXPECT_EQ(NAMESPACE_NOT_DEFINED, CanConnectAndSendMessages(""));
+ EXPECT_FALSE(AreAnyNonWebApisDefined());
+
+ // Once a connectable extension is installed, it should.
+ const Extension* extension = LoadChromiumConnectableExtension();
+ EXPECT_EQ(OK, CanConnectAndSendMessages(extension->id()));
+ EXPECT_FALSE(AreAnyNonWebApisDefined());
+}
+
} // namespace
}; // namespace extensions
diff --git a/chrome/common/extensions/api/_api_features.json b/chrome/common/extensions/api/_api_features.json
index eb87ca2..70aa897 100644
--- a/chrome/common/extensions/api/_api_features.json
+++ b/chrome/common/extensions/api/_api_features.json
@@ -4,6 +4,9 @@
// See c/c/e/features/* to understand this file, in particular feature.h,
// simple_feature.h, and base_feature_provider.h.
+//
+// Note that specifying "web_page", "blessed_web_page", or "all" as a context
+// type will require manually updating chrome/renderer/resources/dispatcher.cc.
{
"activityLogPrivate": {
diff --git a/chrome/renderer/extensions/chrome_v8_context.cc b/chrome/renderer/extensions/chrome_v8_context.cc
index e6e8d18..66d14c0 100644
--- a/chrome/renderer/extensions/chrome_v8_context.cc
+++ b/chrome/renderer/extensions/chrome_v8_context.cc
@@ -106,8 +106,17 @@ bool ChromeV8Context::IsAnyFeatureAvailableToContext(
Feature::Availability ChromeV8Context::GetAvailability(
const std::string& api_name) {
+ // Hack: Hosted apps should have the availability of messaging APIs based on
+ // the URL of the page (which might have access depending on some extension
+ // with externally_connectable), not whether the app has access to messaging
+ // (which it won't).
+ const Extension* extension = extension_.get();
+ if (extension && extension->is_hosted_app() &&
+ (api_name == "runtime.connect" || api_name == "runtime.sendMessage")) {
+ extension = NULL;
+ }
return ExtensionAPI::GetSharedInstance()->IsAvailable(api_name,
- extension_.get(),
+ extension,
context_type_,
GetURL());
}
diff --git a/chrome/renderer/extensions/dispatcher.cc b/chrome/renderer/extensions/dispatcher.cc
index bc3aad0..86f3283 100644
--- a/chrome/renderer/extensions/dispatcher.cc
+++ b/chrome/renderer/extensions/dispatcher.cc
@@ -707,7 +707,8 @@ void Dispatcher::AddOrRemoveBindingsForContext(ChromeV8Context* context) {
// the same code regardless of context type.
switch (context->context_type()) {
case Feature::UNSPECIFIED_CONTEXT:
- case Feature::WEB_PAGE_CONTEXT: {
+ case Feature::WEB_PAGE_CONTEXT:
+ case Feature::BLESSED_WEB_PAGE_CONTEXT: {
// Web page context; it's too expensive to run the full bindings code.
// Hard-code that the app and webstore APIs are available...
RegisterBinding("app", context);
@@ -732,7 +733,6 @@ void Dispatcher::AddOrRemoveBindingsForContext(ChromeV8Context* context) {
}
case Feature::BLESSED_EXTENSION_CONTEXT:
- case Feature::BLESSED_WEB_PAGE_CONTEXT:
case Feature::UNBLESSED_EXTENSION_CONTEXT:
case Feature::CONTENT_SCRIPT_CONTEXT: {
// Extension context; iterate through all the APIs and bind the available
diff --git a/chrome/renderer/extensions/runtime_custom_bindings.cc b/chrome/renderer/extensions/runtime_custom_bindings.cc
index e2030d1..0db2a40 100644
--- a/chrome/renderer/extensions/runtime_custom_bindings.cc
+++ b/chrome/renderer/extensions/runtime_custom_bindings.cc
@@ -58,7 +58,13 @@ void RuntimeCustomBindings::OpenChannelToExtension(
CHECK(args[0]->IsString() && args[1]->IsString() && args[2]->IsBoolean());
ExtensionMsg_ExternalConnectionInfo info;
- info.source_id = context()->GetExtensionID();
+
+ // For messaging APIs, hosted apps should be considered a web page so hide
+ // its extension ID.
+ const Extension* extension = context()->extension();
+ if (extension && !extension->is_hosted_app())
+ info.source_id = extension->id();
+
info.target_id = *v8::String::Utf8Value(args[0]->ToString());
info.source_url = context()->GetURL();
std::string channel_name = *v8::String::Utf8Value(args[1]->ToString());