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

Side by Side Diff: chrome/renderer/extensions/webstore_bindings.cc

Issue 175263003: Add chrome.webstore API methods to allow sites to see progress of installation (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Latest master Created 6 years, 9 months 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 (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 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 "chrome/renderer/extensions/webstore_bindings.h" 5 #include "chrome/renderer/extensions/webstore_bindings.h"
6 6
7 #include "base/strings/string_util.h" 7 #include "base/strings/string_util.h"
8 #include "chrome/common/extensions/api/webstore/webstore_api_constants.h"
9 #include "chrome/common/extensions/chrome_extension_messages.h"
8 #include "chrome/common/extensions/extension_constants.h" 10 #include "chrome/common/extensions/extension_constants.h"
9 #include "chrome/renderer/extensions/chrome_v8_context.h" 11 #include "chrome/renderer/extensions/chrome_v8_context.h"
10 #include "content/public/renderer/render_view.h" 12 #include "content/public/renderer/render_view.h"
11 #include "extensions/common/extension.h" 13 #include "extensions/common/extension.h"
12 #include "extensions/common/extension_messages.h"
13 #include "grit/renderer_resources.h" 14 #include "grit/renderer_resources.h"
14 #include "third_party/WebKit/public/web/WebDocument.h" 15 #include "third_party/WebKit/public/web/WebDocument.h"
15 #include "third_party/WebKit/public/web/WebElement.h" 16 #include "third_party/WebKit/public/web/WebElement.h"
16 #include "third_party/WebKit/public/web/WebNode.h" 17 #include "third_party/WebKit/public/web/WebNode.h"
17 #include "third_party/WebKit/public/web/WebNodeList.h" 18 #include "third_party/WebKit/public/web/WebNodeList.h"
18 #include "third_party/WebKit/public/web/WebUserGestureIndicator.h" 19 #include "third_party/WebKit/public/web/WebUserGestureIndicator.h"
19 #include "url/gurl.h" 20 #include "url/gurl.h"
20 #include "v8/include/v8.h" 21 #include "v8/include/v8.h"
21 22
22 using blink::WebDocument; 23 using blink::WebDocument;
23 using blink::WebElement; 24 using blink::WebElement;
24 using blink::WebFrame; 25 using blink::WebFrame;
25 using blink::WebNode; 26 using blink::WebNode;
26 using blink::WebNodeList; 27 using blink::WebNodeList;
27 using blink::WebUserGestureIndicator; 28 using blink::WebUserGestureIndicator;
28 29
29 namespace extensions { 30 namespace extensions {
30 31
31 namespace { 32 namespace {
32 33
33 const char kWebstoreLinkRelation[] = "chrome-webstore-item"; 34 const char kWebstoreLinkRelation[] = "chrome-webstore-item";
34 35
35 const char kPreferredStoreLinkUrlNotAString[] =
36 "The Chrome Web Store item link URL parameter must be a string.";
37 const char kSuccessCallbackNotAFunctionError[] =
38 "The success callback parameter must be a function.";
39 const char kFailureCallbackNotAFunctionError[] =
40 "The failure callback parameter must be a function.";
41 const char kNotInTopFrameError[] = 36 const char kNotInTopFrameError[] =
42 "Chrome Web Store installations can only be started by the top frame."; 37 "Chrome Web Store installations can only be started by the top frame.";
43 const char kNotUserGestureError[] = 38 const char kNotUserGestureError[] =
44 "Chrome Web Store installations can only be initated by a user gesture."; 39 "Chrome Web Store installations can only be initated by a user gesture.";
45 const char kNoWebstoreItemLinkFoundError[] = 40 const char kNoWebstoreItemLinkFoundError[] =
46 "No Chrome Web Store item link found."; 41 "No Chrome Web Store item link found.";
47 const char kInvalidWebstoreItemUrlError[] = 42 const char kInvalidWebstoreItemUrlError[] =
48 "Invalid Chrome Web Store item URL."; 43 "Invalid Chrome Web Store item URL.";
49 44
50 // chrome.webstore.install() calls generate an install ID so that the install's 45 // chrome.webstore.install() calls generate an install ID so that the install's
51 // callbacks may be fired when the browser notifies us of install completion 46 // callbacks may be fired when the browser notifies us of install completion
52 // (successful or not) via OnInlineWebstoreInstallResponse. 47 // (successful or not) via OnInlineWebstoreInstallResponse.
53 int g_next_install_id = 0; 48 int g_next_install_id = 0;
54 49
55 } // anonymous namespace 50 } // anonymous namespace
56 51
57 WebstoreBindings::WebstoreBindings(Dispatcher* dispatcher, 52 WebstoreBindings::WebstoreBindings(Dispatcher* dispatcher,
58 ChromeV8Context* context) 53 ChromeV8Context* context)
59 : ChromeV8Extension(dispatcher, context), 54 : ChromeV8Extension(dispatcher, context),
60 ChromeV8ExtensionHandler(context) { 55 ChromeV8ExtensionHandler(context) {
61 RouteFunction("Install", 56 RouteFunction("Install",
62 base::Bind(&WebstoreBindings::Install, base::Unretained(this))); 57 base::Bind(&WebstoreBindings::Install, base::Unretained(this)));
63 } 58 }
64 59
65 void WebstoreBindings::Install( 60 void WebstoreBindings::Install(
66 const v8::FunctionCallbackInfo<v8::Value>& args) { 61 const v8::FunctionCallbackInfo<v8::Value>& args) {
67 WebFrame* frame = WebFrame::frameForContext(context()->v8_context()); 62 content::RenderView* render_view = GetRenderView();
68 if (!frame || !frame->view())
69 return;
70
71 content::RenderView* render_view =
72 content::RenderView::FromWebView(frame->view());
73 if (!render_view) 63 if (!render_view)
74 return; 64 return;
75 65
66 // The first two arguments indicate whether or not there are install stage
67 // or download progress listeners.
68 int listener_mask = 0;
69 CHECK(args[0]->IsBoolean());
70 if (args[0]->BooleanValue())
71 listener_mask |= api::webstore::INSTALL_STAGE_LISTENER;
72 CHECK(args[1]->IsBoolean());
73 if (args[1]->BooleanValue())
74 listener_mask |= api::webstore::DOWNLOAD_PROGRESS_LISTENER;
75
76 std::string preferred_store_link_url; 76 std::string preferred_store_link_url;
77 if (!args[0]->IsUndefined()) { 77 if (!args[2]->IsUndefined()) {
78 if (args[0]->IsString()) { 78 CHECK(args[2]->IsString());
79 preferred_store_link_url = std::string(*v8::String::Utf8Value(args[0])); 79 preferred_store_link_url = std::string(*v8::String::Utf8Value(args[2]));
80 } else {
81 args.GetIsolate()->ThrowException(v8::String::NewFromUtf8(
82 args.GetIsolate(), kPreferredStoreLinkUrlNotAString));
83 return;
84 }
85 } 80 }
86 81
87 std::string webstore_item_id; 82 std::string webstore_item_id;
88 std::string error; 83 std::string error;
84 WebFrame* frame = context()->web_frame();
85
89 if (!GetWebstoreItemIdFromFrame( 86 if (!GetWebstoreItemIdFromFrame(
90 frame, preferred_store_link_url, &webstore_item_id, &error)) { 87 frame, preferred_store_link_url, &webstore_item_id, &error)) {
91 args.GetIsolate()->ThrowException( 88 args.GetIsolate()->ThrowException(
92 v8::String::NewFromUtf8(args.GetIsolate(), error.c_str())); 89 v8::String::NewFromUtf8(args.GetIsolate(), error.c_str()));
93 return; 90 return;
94 } 91 }
95 92
96 int install_id = g_next_install_id++; 93 int install_id = g_next_install_id++;
97 if (!args[1]->IsUndefined() && !args[1]->IsFunction()) {
98 args.GetIsolate()->ThrowException(v8::String::NewFromUtf8(
99 args.GetIsolate(), kSuccessCallbackNotAFunctionError));
100 return;
101 }
102 94
103 if (!args[2]->IsUndefined() && !args[2]->IsFunction()) { 95 Send(new ExtensionHostMsg_InlineWebstoreInstall(render_view->GetRoutingID(),
104 args.GetIsolate()->ThrowException(v8::String::NewFromUtf8( 96 install_id,
105 args.GetIsolate(), kFailureCallbackNotAFunctionError)); 97 GetRoutingID(),
106 return; 98 webstore_item_id,
107 } 99 frame->document().url(),
108 100 listener_mask));
109 Send(new ExtensionHostMsg_InlineWebstoreInstall(
110 render_view->GetRoutingID(),
111 install_id,
112 GetRoutingID(),
113 webstore_item_id,
114 frame->document().url()));
115 101
116 args.GetReturnValue().Set(static_cast<int32_t>(install_id)); 102 args.GetReturnValue().Set(static_cast<int32_t>(install_id));
117 } 103 }
118 104
119 // static 105 // static
120 bool WebstoreBindings::GetWebstoreItemIdFromFrame( 106 bool WebstoreBindings::GetWebstoreItemIdFromFrame(
121 WebFrame* frame, const std::string& preferred_store_link_url, 107 WebFrame* frame, const std::string& preferred_store_link_url,
122 std::string* webstore_item_id, std::string* error) { 108 std::string* webstore_item_id, std::string* error) {
123 if (frame != frame->top()) { 109 if (frame != frame->top()) {
124 *error = kNotInTopFrameError; 110 *error = kNotInTopFrameError;
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after
200 } 186 }
201 187
202 *error = kNoWebstoreItemLinkFoundError; 188 *error = kNoWebstoreItemLinkFoundError;
203 return false; 189 return false;
204 } 190 }
205 191
206 bool WebstoreBindings::OnMessageReceived(const IPC::Message& message) { 192 bool WebstoreBindings::OnMessageReceived(const IPC::Message& message) {
207 IPC_BEGIN_MESSAGE_MAP(WebstoreBindings, message) 193 IPC_BEGIN_MESSAGE_MAP(WebstoreBindings, message)
208 IPC_MESSAGE_HANDLER(ExtensionMsg_InlineWebstoreInstallResponse, 194 IPC_MESSAGE_HANDLER(ExtensionMsg_InlineWebstoreInstallResponse,
209 OnInlineWebstoreInstallResponse) 195 OnInlineWebstoreInstallResponse)
196 IPC_MESSAGE_HANDLER(ExtensionMsg_InlineInstallStageChanged,
197 OnInlineInstallStageChanged)
198 IPC_MESSAGE_HANDLER(ExtensionMsg_InlineInstallDownloadProgress,
199 OnInlineInstallDownloadProgress)
210 IPC_MESSAGE_UNHANDLED(CHECK(false) << "Unhandled IPC message") 200 IPC_MESSAGE_UNHANDLED(CHECK(false) << "Unhandled IPC message")
211 IPC_END_MESSAGE_MAP() 201 IPC_END_MESSAGE_MAP()
212 return true; 202 return true;
213 } 203 }
214 204
215 void WebstoreBindings::OnInlineWebstoreInstallResponse( 205 void WebstoreBindings::OnInlineWebstoreInstallResponse(
216 int install_id, 206 int install_id,
217 bool success, 207 bool success,
218 const std::string& error) { 208 const std::string& error) {
219 v8::Isolate* isolate = context()->isolate(); 209 v8::Isolate* isolate = context()->isolate();
220 v8::HandleScope handle_scope(isolate); 210 v8::HandleScope handle_scope(isolate);
221 v8::Context::Scope context_scope(context()->v8_context()); 211 v8::Context::Scope context_scope(context()->v8_context());
222 v8::Handle<v8::Value> argv[] = { 212 v8::Handle<v8::Value> argv[] = {
223 v8::Integer::New(isolate, install_id), 213 v8::Integer::New(isolate, install_id),
224 v8::Boolean::New(isolate, success), 214 v8::Boolean::New(isolate, success),
225 v8::String::NewFromUtf8(isolate, error.c_str()) 215 v8::String::NewFromUtf8(isolate, error.c_str())
226 }; 216 };
227 context()->module_system()->CallModuleMethod( 217 context()->module_system()->CallModuleMethod(
228 "webstore", "onInstallResponse", arraysize(argv), argv); 218 "webstore", "onInstallResponse", arraysize(argv), argv);
229 } 219 }
230 220
221 void WebstoreBindings::OnInlineInstallStageChanged(int stage) {
222 const char* stage_string = NULL;
223 api::webstore::InstallStage install_stage =
224 static_cast<api::webstore::InstallStage>(stage);
225 switch (install_stage) {
226 case api::webstore::INSTALL_STAGE_DOWNLOADING:
227 stage_string = api::webstore::kInstallStageDownloading;
228 break;
229 case api::webstore::INSTALL_STAGE_INSTALLING:
230 stage_string = api::webstore::kInstallStageInstalling;
231 break;
232 }
233 v8::Isolate* isolate = context()->isolate();
234 v8::HandleScope handle_scope(isolate);
235 v8::Context::Scope context_scope(context()->v8_context());
236 v8::Handle<v8::Value> argv[] = {
237 v8::String::NewFromUtf8(isolate, stage_string)};
238 context()->module_system()->CallModuleMethod(
239 "webstore", "onInstallStageChanged", arraysize(argv), argv);
240 }
241
242 void WebstoreBindings::OnInlineInstallDownloadProgress(int percent_downloaded) {
243 v8::Isolate* isolate = context()->isolate();
244 v8::HandleScope handle_scope(isolate);
245 v8::Context::Scope context_scope(context()->v8_context());
246 v8::Handle<v8::Value> argv[] = {
247 v8::Number::New(isolate, percent_downloaded / 100.0)};
248 context()->module_system()->CallModuleMethod(
249 "webstore", "onDownloadProgress", arraysize(argv), argv);
250 }
251
231 } // namespace extensions 252 } // namespace extensions
OLDNEW
« no previous file with comments | « chrome/renderer/extensions/webstore_bindings.h ('k') | chrome/renderer/resources/extensions/webstore_custom_bindings.js » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698