summaryrefslogtreecommitdiffstats
path: root/chrome/renderer/extensions
diff options
context:
space:
mode:
authormpcomplete@google.com <mpcomplete@google.com@0039d316-1c4b-4281-b951-d872f2087c98>2009-06-08 20:53:24 +0000
committermpcomplete@google.com <mpcomplete@google.com@0039d316-1c4b-4281-b951-d872f2087c98>2009-06-08 20:53:24 +0000
commit0281b06f8bbde4c064a9276e6d70484ba2a3eaec (patch)
treefb2a4a873c32f45d27d982a8eb5068349d311c4d /chrome/renderer/extensions
parentb6f05b3fd9422fd9b5c8142fa4224ba2d8abf1d4 (diff)
downloadchromium_src-0281b06f8bbde4c064a9276e6d70484ba2a3eaec.zip
chromium_src-0281b06f8bbde4c064a9276e6d70484ba2a3eaec.tar.gz
chromium_src-0281b06f8bbde4c064a9276e6d70484ba2a3eaec.tar.bz2
Revert 17889. It broke the extensions_uitests. And I didn't even get it
reviewed! (Wow, brainfart.) TBR=aa Review URL: http://codereview.chromium.org/119324 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@17893 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/renderer/extensions')
-rw-r--r--chrome/renderer/extensions/bindings_utils.cc23
-rw-r--r--chrome/renderer/extensions/bindings_utils.h5
-rw-r--r--chrome/renderer/extensions/event_bindings.cc15
-rw-r--r--chrome/renderer/extensions/extension_api_client_unittest.cc7
-rw-r--r--chrome/renderer/extensions/extension_process_bindings.cc125
-rw-r--r--chrome/renderer/extensions/extension_process_bindings.h16
6 files changed, 79 insertions, 112 deletions
diff --git a/chrome/renderer/extensions/bindings_utils.cc b/chrome/renderer/extensions/bindings_utils.cc
index 81e2058..097c8d0 100644
--- a/chrome/renderer/extensions/bindings_utils.cc
+++ b/chrome/renderer/extensions/bindings_utils.cc
@@ -4,7 +4,6 @@
#include "chrome/renderer/extensions/bindings_utils.h"
-#include "base/string_util.h"
#include "chrome/renderer/render_view.h"
#include "webkit/glue/webframe.h"
@@ -22,25 +21,3 @@ RenderView* GetRenderViewForCurrentContext() {
DCHECK(renderview) << "Encountered a WebView without a WebViewDelegate";
return renderview;
}
-
-void CallFunctionInContext(v8::Handle<v8::Context> context,
- const std::string& function_name, int argc,
- v8::Handle<v8::Value>* argv) {
- v8::Context::Scope context_scope(context);
-
- // Look up the function name, which may be a sub-property like
- // "chrome.handleResponse_" in the global variable.
- v8::Local<v8::Value> value = context->Global();
- std::vector<std::string> components;
- SplitStringDontTrim(function_name, '.', &components);
- for (size_t i = 0; i < components.size(); ++i) {
- if (value->IsObject())
- value = value->ToObject()->Get(v8::String::New(components[i].c_str()));
- }
- if (!value->IsFunction())
- return;
-
- v8::Local<v8::Function> function = v8::Local<v8::Function>::Cast(value);
- if (!function.IsEmpty())
- function->Call(v8::Object::New(), argc, argv);
-}
diff --git a/chrome/renderer/extensions/bindings_utils.h b/chrome/renderer/extensions/bindings_utils.h
index c4be3ad..7596952 100644
--- a/chrome/renderer/extensions/bindings_utils.h
+++ b/chrome/renderer/extensions/bindings_utils.h
@@ -8,7 +8,6 @@
#include "app/resource_bundle.h"
#include "base/singleton.h"
#include "base/string_piece.h"
-#include "v8/include/v8.h"
#include <string>
@@ -33,8 +32,4 @@ const char* GetStringResource() {
// an error to call this when not in a V8 context.
RenderView* GetRenderViewForCurrentContext();
-void CallFunctionInContext(v8::Handle<v8::Context> context,
- const std::string& function_name, int argc,
- v8::Handle<v8::Value>* argv);
-
#endif // CHROME_RENDERER_EXTENSIONS_BINDINGS_UTILS_H_
diff --git a/chrome/renderer/extensions/event_bindings.cc b/chrome/renderer/extensions/event_bindings.cc
index 576beba..19a9245 100644
--- a/chrome/renderer/extensions/event_bindings.cc
+++ b/chrome/renderer/extensions/event_bindings.cc
@@ -168,6 +168,19 @@ void EventBindings::CallFunction(const std::string& function_name,
int argc, v8::Handle<v8::Value>* argv) {
for (ContextList::iterator it = GetRegisteredContexts().begin();
it != GetRegisteredContexts().end(); ++it) {
- CallFunctionInContext(*it, function_name, argc, argv);
+ DCHECK(!it->IsEmpty());
+ v8::Context::Scope context_scope(*it);
+ v8::Local<v8::Object> global = (*it)->Global();
+
+ v8::Local<v8::Script> script = v8::Script::Compile(
+ v8::String::New(function_name.c_str()));
+ v8::Local<v8::Value> function_obj = script->Run();
+ if (!function_obj->IsFunction())
+ continue;
+
+ v8::Local<v8::Function> function =
+ v8::Local<v8::Function>::Cast(function_obj);
+ if (!function.IsEmpty())
+ function->Call(v8::Object::New(), argc, argv);
}
}
diff --git a/chrome/renderer/extensions/extension_api_client_unittest.cc b/chrome/renderer/extensions/extension_api_client_unittest.cc
index b77394c0..ddc7c42 100644
--- a/chrome/renderer/extensions/extension_api_client_unittest.cc
+++ b/chrome/renderer/extensions/extension_api_client_unittest.cc
@@ -90,9 +90,10 @@ TEST_F(ExtensionAPIClientTest, CallbackDispatching) {
int callback_id = params.c;
ASSERT_TRUE(callback_id >= 0);
- //// Now send the callback a response
- ExtensionProcessBindings::HandleResponse(
- callback_id, true, "{\"foo\":\"bar\"}", "");
+ // Now send the callback a response
+ ExtensionProcessBindings::CallContext call(GetMainFrame(), "CreateTab");
+ ExtensionProcessBindings::ExecuteResponseInFrame(
+ &call, callback_id, true, "{\"foo\":\"bar\"}", "");
// And verify that it worked
ASSERT_EQ("pass", GetConsoleMessage());
diff --git a/chrome/renderer/extensions/extension_process_bindings.cc b/chrome/renderer/extensions/extension_process_bindings.cc
index 5580e8d..6057a3e 100644
--- a/chrome/renderer/extensions/extension_process_bindings.cc
+++ b/chrome/renderer/extensions/extension_process_bindings.cc
@@ -5,7 +5,6 @@
#include "chrome/renderer/extensions/extension_process_bindings.h"
#include "base/singleton.h"
-#include "base/stl_util-inl.h"
#include "chrome/common/render_messages.h"
#include "chrome/common/url_constants.h"
#include "chrome/renderer/extensions/bindings_utils.h"
@@ -34,41 +33,10 @@ const char* kExtensionDeps[] = {
// |extension_id| -> <List of v8 Contexts for the "views" of that extension>
typedef std::list< v8::Persistent<v8::Context> > ContextList;
typedef std::map<std::string, ContextList> ExtensionIdContextsMap;
-
-// Contains info relevant to a pending request.
-struct CallContext {
- public :
- CallContext(v8::Persistent<v8::Context> context, const std::string& name)
- : context(context), name(name) {
- }
- v8::Persistent<v8::Context> context;
- std::string name;
-};
-typedef std::map<int, CallContext*> PendingRequestMap;
-
-struct SingletonData {
- std::set<std::string> function_names_;
+struct ExtensionViewContexts {
ExtensionIdContextsMap contexts;
- PendingRequestMap pending_requests;
-
- ~SingletonData() {
- STLDeleteContainerPairSecondPointers(pending_requests.begin(),
- pending_requests.end());
- }
};
-static std::set<std::string>* GetFunctionNameSet() {
- return &Singleton<SingletonData>()->function_names_;
-}
-
-static ContextList& GetRegisteredContexts(std::string extension_id) {
- return Singleton<SingletonData>::get()->contexts[extension_id];
-}
-
-static PendingRequestMap& GetPendingRequestMap() {
- return Singleton<SingletonData>::get()->pending_requests;
-}
-
class ExtensionImpl : public v8::Extension {
public:
ExtensionImpl() : v8::Extension(
@@ -101,6 +69,18 @@ class ExtensionImpl : public v8::Extension {
}
private:
+ struct SingletonData {
+ std::set<std::string> function_names_;
+ };
+
+ static std::set<std::string>* GetFunctionNameSet() {
+ return &Singleton<SingletonData>()->function_names_;
+ }
+
+ static ContextList& GetRegisteredContexts(std::string extension_id) {
+ return Singleton<ExtensionViewContexts>::get()->contexts[extension_id];
+ }
+
static v8::Handle<v8::Value> RegisterExtension(const v8::Arguments& args) {
RenderView* renderview = GetRenderViewForCurrentContext();
DCHECK(renderview);
@@ -120,24 +100,11 @@ class ExtensionImpl : public v8::Extension {
DCHECK_EQ(args.Length(), 1);
DCHECK(args[0]->IsString());
+ std::string extension_id(*v8::String::Utf8Value(args[0]));
+ ContextList& contexts = GetRegisteredContexts(extension_id);
v8::Local<v8::Context> current_context = v8::Context::GetCurrent();
DCHECK(!current_context.IsEmpty());
- // Remove all pending requests for this context.
- PendingRequestMap pending_requests = GetPendingRequestMap();
- for (PendingRequestMap::iterator it = pending_requests.begin();
- it != pending_requests.end(); ) {
- PendingRequestMap::iterator current = it++;
- if (current->second->context == current_context) {
- current->second->context.Dispose();
- current->second->context.Clear();
- delete current->second;
- pending_requests.erase(current);
- }
- }
-
- std::string extension_id(*v8::String::Utf8Value(args[0]));
- ContextList& contexts = GetRegisteredContexts(extension_id);
ContextList::iterator it = std::find(contexts.begin(), contexts.end(),
current_context);
if (it == contexts.end()) {
@@ -182,26 +149,22 @@ class ExtensionImpl : public v8::Extension {
static v8::Handle<v8::Value> StartRequest(const v8::Arguments& args) {
// Get the current RenderView so that we can send a routed IPC message from
// the correct source.
+ WebFrame* webframe = WebFrame::RetrieveFrameForCurrentContext();
RenderView* renderview = GetRenderViewForCurrentContext();
- if (!renderview)
+ if (!webframe || !renderview)
return v8::Undefined();
if (args.Length() != 3 || !args[0]->IsString() || !args[1]->IsInt32() ||
!args[2]->IsBoolean())
return v8::Undefined();
- std::string name = *v8::String::AsciiValue(args.Data());
- std::string json_args = *v8::String::Utf8Value(args[0]);
int request_id = args[1]->Int32Value();
bool has_callback = args[2]->BooleanValue();
- v8::Persistent<v8::Context> current_context =
- v8::Persistent<v8::Context>::New(v8::Context::GetCurrent());
- DCHECK(!current_context.IsEmpty());
- GetPendingRequestMap()[request_id] =
- new CallContext(current_context, *v8::String::AsciiValue(args.Data()));
-
- renderview->SendExtensionRequest(name, json_args, request_id, has_callback);
+ renderview->SendExtensionRequest(
+ std::string(*v8::String::AsciiValue(args.Data())),
+ std::string(*v8::String::Utf8Value(args[0])),
+ request_id, has_callback, webframe);
return v8::Undefined();
}
@@ -223,23 +186,31 @@ void ExtensionProcessBindings::RegisterExtensionContext(WebFrame* frame) {
"chrome.self.register_();")));
}
-void ExtensionProcessBindings::HandleResponse(int request_id, bool success,
- const std::string& response,
- const std::string& error) {
- CallContext* call = GetPendingRequestMap()[request_id];
- if (!call)
- return; // The frame went away.
-
- v8::HandleScope handle_scope;
- v8::Handle<v8::Value> argv[5];
- argv[0] = v8::Integer::New(request_id);
- argv[1] = v8::String::New(call->name.c_str());
- argv[2] = v8::Boolean::New(success);
- argv[3] = v8::String::New(response.c_str());
- argv[4] = v8::String::New(error.c_str());
- CallFunctionInContext(call->context, "chrome.handleResponse_",
- arraysize(argv), argv);
-
- GetPendingRequestMap().erase(request_id);
- delete call;
+void ExtensionProcessBindings::ExecuteResponseInFrame(
+ CallContext *call, int request_id, bool success,
+ const std::string& response,
+ const std::string& error) {
+ std::string code = "chrome.handleResponse_(";
+ code += IntToString(request_id);
+
+ code += ", '" + call->name_;
+
+ if (success)
+ code += "', true";
+ else
+ code += "', false";
+
+ code += ", '";
+ size_t offset = code.length();
+ code += response;
+ ReplaceSubstringsAfterOffset(&code, offset, "\\", "\\\\");
+ ReplaceSubstringsAfterOffset(&code, offset, "'", "\\'");
+ code += "', '";
+ offset = code.length();
+ code += error;
+ ReplaceSubstringsAfterOffset(&code, offset, "\\", "\\\\");
+ ReplaceSubstringsAfterOffset(&code, offset, "'", "\\'");
+ code += "')";
+
+ call->frame_->ExecuteScript(WebScriptSource(WebString::fromUTF8(code)));
}
diff --git a/chrome/renderer/extensions/extension_process_bindings.h b/chrome/renderer/extensions/extension_process_bindings.h
index 9639090..d5798cd 100644
--- a/chrome/renderer/extensions/extension_process_bindings.h
+++ b/chrome/renderer/extensions/extension_process_bindings.h
@@ -16,12 +16,22 @@ class WebFrame;
class ExtensionProcessBindings {
public:
+ struct CallContext {
+ public :
+ CallContext(WebFrame *frame, const std::string& name)
+ : frame_(frame),
+ name_(name) {}
+ WebFrame* frame_;
+ std::string name_;
+ };
+
static void SetFunctionNames(const std::vector<std::string>& names);
static v8::Extension* Get();
static void RegisterExtensionContext(WebFrame* frame);
- static void HandleResponse(int request_id, bool success,
- const std::string& response,
- const std::string& error);
+ static void ExecuteResponseInFrame(CallContext *call, int request_id,
+ bool success,
+ const std::string& response,
+ const std::string& error);
};
#endif // CHROME_RENDERER_EXTENSIONS_EXTENSION_PROCESS_BINDINGS_H_