Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(890)

Side by Side Diff: extensions/renderer/guest_view/mime_handler_view/mime_handler_view_container.cc

Issue 729333002: Add PostMessage support for MimeHandlerView (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 6 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "extensions/renderer/guest_view/mime_handler_view/mime_handler_view_con tainer.h" 5 #include "extensions/renderer/guest_view/mime_handler_view/mime_handler_view_con tainer.h"
6 6
7 #include "content/public/renderer/render_frame.h" 7 #include "content/public/renderer/render_frame.h"
8 #include "content/public/renderer/render_view.h"
8 #include "extensions/common/extension_messages.h" 9 #include "extensions/common/extension_messages.h"
9 #include "extensions/common/guest_view/guest_view_constants.h" 10 #include "extensions/common/guest_view/guest_view_constants.h"
11 #include "gin/arguments.h"
12 #include "gin/dictionary.h"
13 #include "gin/handle.h"
14 #include "gin/interceptor.h"
15 #include "gin/object_template_builder.h"
16 #include "gin/wrappable.h"
10 #include "third_party/WebKit/public/web/WebDocument.h" 17 #include "third_party/WebKit/public/web/WebDocument.h"
11 #include "third_party/WebKit/public/web/WebLocalFrame.h" 18 #include "third_party/WebKit/public/web/WebLocalFrame.h"
19 #include "third_party/WebKit/public/web/WebView.h"
12 20
13 namespace extensions { 21 namespace extensions {
14 22
23 namespace {
24
25 const char kPostMessageName[] = "postMessage";
26
27 // The gin-backed scriptable object which is exposed by the BrowserPlugin for
28 // MimeHandlerViewContainer. This currently only implements "postMessage".
29 class ScriptableObject : public gin::Wrappable<ScriptableObject>,
30 public gin::NamedPropertyInterceptor {
31 public:
32 static gin::WrapperInfo kWrapperInfo;
33
34 static v8::Handle<v8::Object> Create(
35 v8::Isolate* isolate,
36 base::WeakPtr<MimeHandlerViewContainer> container) {
37 ScriptableObject* scriptable_object =
38 new ScriptableObject(isolate, container);
39 return gin::CreateHandle(isolate, scriptable_object).ToV8()->ToObject();
40 }
41
42 // gin::NamedPropertyInterceptor
43 v8::Local<v8::Value> GetNamedProperty(
44 v8::Isolate* isolate,
45 const std::string& identifier) override {
46 if (identifier == kPostMessageName) {
47 return gin::CreateFunctionTemplate(isolate,
48 base::Bind(&MimeHandlerViewContainer::PostMessage,
49 container_, isolate))->GetFunction();
50 }
51 return v8::Local<v8::Value>();
52 }
53
54 private:
55 ScriptableObject(v8::Isolate* isolate,
56 base::WeakPtr<MimeHandlerViewContainer> container)
57 : gin::NamedPropertyInterceptor(isolate, this),
58 container_(container) {}
59 virtual ~ScriptableObject() {}
60
61 // gin::Wrappable
62 virtual gin::ObjectTemplateBuilder GetObjectTemplateBuilder(
63 v8::Isolate* isolate) override {
64 return gin::Wrappable<ScriptableObject>::GetObjectTemplateBuilder(isolate)
65 .AddNamedPropertyInterceptor();
66 }
67
68 base::WeakPtr<MimeHandlerViewContainer> container_;
69 };
70
71 // static
72 gin::WrapperInfo ScriptableObject::kWrapperInfo = { gin::kEmbedderNativeGin };
73
74 } // namespace
75
15 MimeHandlerViewContainer::MimeHandlerViewContainer( 76 MimeHandlerViewContainer::MimeHandlerViewContainer(
16 content::RenderFrame* render_frame, 77 content::RenderFrame* render_frame,
17 const std::string& mime_type, 78 const std::string& mime_type,
18 const GURL& original_url) 79 const GURL& original_url)
19 : GuestViewContainer(render_frame), 80 : GuestViewContainer(render_frame),
20 mime_type_(mime_type), 81 mime_type_(mime_type),
21 original_url_(original_url) { 82 original_url_(original_url),
83 guest_proxy_routing_id_(-1),
84 weak_factory_(this) {
22 DCHECK(!mime_type_.empty()); 85 DCHECK(!mime_type_.empty());
23 is_embedded_ = !render_frame->GetWebFrame()->document().isPluginDocument(); 86 is_embedded_ = !render_frame->GetWebFrame()->document().isPluginDocument();
24 } 87 }
25 88
26 MimeHandlerViewContainer::~MimeHandlerViewContainer() { 89 MimeHandlerViewContainer::~MimeHandlerViewContainer() {
27 if (loader_) 90 if (loader_)
28 loader_->cancel(); 91 loader_->cancel();
29 } 92 }
30 93
94 void MimeHandlerViewContainer::Ready() {
95 blink::WebFrame* frame = render_frame()->GetWebFrame();
96 blink::WebURLLoaderOptions options;
97 // The embedded plugin is allowed to be cross-origin.
98 options.crossOriginRequestPolicy =
99 blink::WebURLLoaderOptions::CrossOriginRequestPolicyAllow;
100 DCHECK(!loader_);
101 loader_.reset(frame->createAssociatedURLLoader(options));
102
103 blink::WebURLRequest request(original_url_);
104 request.setRequestContext(blink::WebURLRequest::RequestContextObject);
105 loader_->loadAsynchronously(request, this);
106 }
107
31 void MimeHandlerViewContainer::DidFinishLoading() { 108 void MimeHandlerViewContainer::DidFinishLoading() {
32 DCHECK(!is_embedded_); 109 DCHECK(!is_embedded_);
33 CreateMimeHandlerViewGuest(); 110 CreateMimeHandlerViewGuest();
34 } 111 }
35 112
36 void MimeHandlerViewContainer::DidReceiveData(const char* data, 113 void MimeHandlerViewContainer::DidReceiveData(const char* data,
37 int data_length) { 114 int data_length) {
38 html_string_ += std::string(data, data_length); 115 html_string_ += std::string(data, data_length);
39 } 116 }
40 117
41 bool MimeHandlerViewContainer::OnMessageReceived(const IPC::Message& message) { 118 bool MimeHandlerViewContainer::OnMessageReceived(const IPC::Message& message) {
42 bool handled = true; 119 bool handled = true;
43 IPC_BEGIN_MESSAGE_MAP(MimeHandlerViewContainer, message) 120 IPC_BEGIN_MESSAGE_MAP(MimeHandlerViewContainer, message)
44 IPC_MESSAGE_HANDLER(ExtensionMsg_CreateMimeHandlerViewGuestACK, 121 IPC_MESSAGE_HANDLER(ExtensionMsg_CreateMimeHandlerViewGuestACK,
45 OnCreateMimeHandlerViewGuestACK) 122 OnCreateMimeHandlerViewGuestACK)
123 IPC_MESSAGE_HANDLER(ExtensionMsg_GuestAttached, OnGuestAttached)
46 IPC_MESSAGE_UNHANDLED(handled = false) 124 IPC_MESSAGE_UNHANDLED(handled = false)
47 IPC_END_MESSAGE_MAP() 125 IPC_END_MESSAGE_MAP()
48 return handled; 126 return handled;
49 } 127 }
50 128
51 void MimeHandlerViewContainer::Ready() { 129 v8::Local<v8::Object> MimeHandlerViewContainer::V8ScriptableObject(
52 blink::WebFrame* frame = render_frame()->GetWebFrame(); 130 v8::Isolate* isolate) {
53 blink::WebURLLoaderOptions options; 131 if (scriptable_object_.IsEmpty()) {
54 // The embedded plugin is allowed to be cross-origin. 132 v8::Local<v8::Object> object =
55 options.crossOriginRequestPolicy = 133 ScriptableObject::Create(isolate, weak_factory_.GetWeakPtr());
56 blink::WebURLLoaderOptions::CrossOriginRequestPolicyAllow; 134 scriptable_object_.reset(object);
57 DCHECK(!loader_); 135 }
58 loader_.reset(frame->createAssociatedURLLoader(options)); 136 return scriptable_object_.NewHandle(isolate);
59
60 blink::WebURLRequest request(original_url_);
61 request.setRequestContext(blink::WebURLRequest::RequestContextObject);
62 loader_->loadAsynchronously(request, this);
63 } 137 }
64 138
65 void MimeHandlerViewContainer::didReceiveData(blink::WebURLLoader* /* unused */, 139 void MimeHandlerViewContainer::didReceiveData(blink::WebURLLoader* /* unused */,
66 const char* data, 140 const char* data,
67 int data_length, 141 int data_length,
68 int /* unused */) { 142 int /* unused */) {
69 html_string_ += std::string(data, data_length); 143 html_string_ += std::string(data, data_length);
70 } 144 }
71 145
72 void MimeHandlerViewContainer::didFinishLoading( 146 void MimeHandlerViewContainer::didFinishLoading(
73 blink::WebURLLoader* /* unused */, 147 blink::WebURLLoader* /* unused */,
74 double /* unused */, 148 double /* unused */,
75 int64_t /* unused */) { 149 int64_t /* unused */) {
76 DCHECK(is_embedded_); 150 DCHECK(is_embedded_);
77 CreateMimeHandlerViewGuest(); 151 CreateMimeHandlerViewGuest();
78 } 152 }
79 153
154 void MimeHandlerViewContainer::PostMessage(v8::Isolate* isolate,
155 v8::Handle<v8::Value> message) {
156 content::RenderView* guest_proxy_render_view =
157 content::RenderView::FromRoutingID(guest_proxy_routing_id_);
158 if (!guest_proxy_render_view)
159 return;
160 blink::WebFrame* guest_proxy_frame =
161 guest_proxy_render_view->GetWebView()->mainFrame();
162 if (!guest_proxy_frame)
163 return;
164
165 v8::Local<v8::Object> guest_proxy_window =
166 guest_proxy_frame->mainWorldScriptContext()->Global();
167 gin::Dictionary window_object(isolate, guest_proxy_window);
168 v8::Handle<v8::Function> post_message;
169 if (!window_object.Get(std::string(kPostMessageName), &post_message))
170 return;
171
172 v8::Handle<v8::Value> args[] = {
173 message,
174 // Post the message to any domain inside the browser plugin. The embedder
175 // should already know what is embedded.
176 gin::StringToV8(isolate, "*")
177 };
178 post_message.As<v8::Function>()->Call(
179 guest_proxy_window, arraysize(args), args);
180 }
181
80 void MimeHandlerViewContainer::OnCreateMimeHandlerViewGuestACK( 182 void MimeHandlerViewContainer::OnCreateMimeHandlerViewGuestACK(
81 int element_instance_id) { 183 int element_instance_id) {
82 DCHECK_NE(this->element_instance_id(), guestview::kInstanceIDNone); 184 DCHECK_NE(this->element_instance_id(), guestview::kInstanceIDNone);
83 DCHECK_EQ(this->element_instance_id(), element_instance_id); 185 DCHECK_EQ(this->element_instance_id(), element_instance_id);
84 render_frame()->AttachGuest(element_instance_id); 186 render_frame()->AttachGuest(element_instance_id);
85 } 187 }
86 188
189 void MimeHandlerViewContainer::OnGuestAttached(int /* unused */,
190 int guest_proxy_routing_id) {
191 // Save the RenderView routing ID of the guest here so it can be used to route
192 // PostMessage calls.
193 guest_proxy_routing_id_ = guest_proxy_routing_id;
194 }
195
87 void MimeHandlerViewContainer::CreateMimeHandlerViewGuest() { 196 void MimeHandlerViewContainer::CreateMimeHandlerViewGuest() {
88 // The loader has completed loading |html_string_| so we can dispose it. 197 // The loader has completed loading |html_string_| so we can dispose it.
89 loader_.reset(); 198 loader_.reset();
90 199
91 // Parse the stream URL to ensure it's valid. 200 // Parse the stream URL to ensure it's valid.
92 GURL stream_url(html_string_); 201 GURL stream_url(html_string_);
93 202
94 DCHECK_NE(element_instance_id(), guestview::kInstanceIDNone); 203 DCHECK_NE(element_instance_id(), guestview::kInstanceIDNone);
95 render_frame()->Send(new ExtensionHostMsg_CreateMimeHandlerViewGuest( 204 render_frame()->Send(new ExtensionHostMsg_CreateMimeHandlerViewGuest(
96 render_frame()->GetRoutingID(), stream_url.spec(), original_url_.spec(), 205 render_frame()->GetRoutingID(), stream_url.spec(), original_url_.spec(),
97 mime_type_, element_instance_id())); 206 mime_type_, element_instance_id()));
98 } 207 }
99 208
100 } // namespace extensions 209 } // namespace extensions
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698