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

Side by Side Diff: extensions/renderer/script_injection_manager.cc

Issue 885493007: Refactoring: de-couple Extensions from "script injection System" [render side] : 1 (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 5 years, 10 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 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/script_injection_manager.h" 5 #include "extensions/renderer/script_injection_manager.h"
6 6
7 #include "base/auto_reset.h" 7 #include "base/auto_reset.h"
8 #include "base/bind.h" 8 #include "base/bind.h"
9 #include "base/memory/weak_ptr.h" 9 #include "base/memory/weak_ptr.h"
10 #include "base/values.h" 10 #include "base/values.h"
11 #include "content/public/renderer/render_thread.h" 11 #include "content/public/renderer/render_thread.h"
12 #include "content/public/renderer/render_view.h" 12 #include "content/public/renderer/render_view.h"
13 #include "content/public/renderer/render_view_observer.h" 13 #include "content/public/renderer/render_view_observer.h"
14 #include "extensions/common/extension.h" 14 #include "extensions/common/extension.h"
15 #include "extensions/common/extension_messages.h" 15 #include "extensions/common/extension_messages.h"
16 #include "extensions/common/extension_set.h" 16 #include "extensions/common/extension_set.h"
17 #include "extensions/renderer/extension_helper.h" 17 #include "extensions/renderer/extension_helper.h"
18 #include "extensions/renderer/extension_injection_host.h"
18 #include "extensions/renderer/programmatic_script_injector.h" 19 #include "extensions/renderer/programmatic_script_injector.h"
19 #include "extensions/renderer/script_injection.h" 20 #include "extensions/renderer/script_injection.h"
20 #include "extensions/renderer/scripts_run_info.h" 21 #include "extensions/renderer/scripts_run_info.h"
21 #include "ipc/ipc_message_macros.h" 22 #include "ipc/ipc_message_macros.h"
22 #include "third_party/WebKit/public/web/WebDocument.h" 23 #include "third_party/WebKit/public/web/WebDocument.h"
23 #include "third_party/WebKit/public/web/WebFrame.h" 24 #include "third_party/WebKit/public/web/WebFrame.h"
24 #include "third_party/WebKit/public/web/WebLocalFrame.h" 25 #include "third_party/WebKit/public/web/WebLocalFrame.h"
25 #include "third_party/WebKit/public/web/WebView.h" 26 #include "third_party/WebKit/public/web/WebView.h"
26 #include "url/gurl.h" 27 #include "url/gurl.h"
27 28
(...skipping 17 matching lines...) Expand all
45 case UserScript::UNDEFINED: 46 case UserScript::UNDEFINED:
46 case UserScript::RUN_DEFERRED: 47 case UserScript::RUN_DEFERRED:
47 case UserScript::BROWSER_DRIVEN: 48 case UserScript::BROWSER_DRIVEN:
48 case UserScript::RUN_LOCATION_LAST: 49 case UserScript::RUN_LOCATION_LAST:
49 break; 50 break;
50 } 51 }
51 NOTREACHED(); 52 NOTREACHED();
52 return UserScript::RUN_LOCATION_LAST; 53 return UserScript::RUN_LOCATION_LAST;
53 } 54 }
54 55
56
57 // TODO(hanxi): let ScriptInjection own an InjectionHost to avoid constructing
58 // an ExtensionInjectionHost many times.
59 // Note: the ScriptInjection should be able to know when the backing extension
60 // is removed.
61 scoped_ptr<ExtensionInjectionHost> GetExtensionInjectionHost(
62 const std::string& extension_id, const ExtensionSet* extensions) {
63 const Extension* extension = extensions->GetByID(extension_id);
64 if (!extension)
65 return scoped_ptr<ExtensionInjectionHost>();
66 return scoped_ptr<ExtensionInjectionHost>(
67 new ExtensionInjectionHost(extension));
68 }
69
55 } // namespace 70 } // namespace
56 71
57 class ScriptInjectionManager::RVOHelper : public content::RenderViewObserver { 72 class ScriptInjectionManager::RVOHelper : public content::RenderViewObserver {
58 public: 73 public:
59 RVOHelper(content::RenderView* render_view, ScriptInjectionManager* manager); 74 RVOHelper(content::RenderView* render_view, ScriptInjectionManager* manager);
60 ~RVOHelper() override; 75 ~RVOHelper() override;
61 76
62 private: 77 private:
63 // RenderViewObserver implementation. 78 // RenderViewObserver implementation.
64 bool OnMessageReceived(const IPC::Message& message) override; 79 bool OnMessageReceived(const IPC::Message& message) override;
(...skipping 175 matching lines...) Expand 10 before | Expand all | Expand 10 after
240 content::RenderView* render_view) { 255 content::RenderView* render_view) {
241 rvo_helpers_.push_back(new RVOHelper(render_view, this)); 256 rvo_helpers_.push_back(new RVOHelper(render_view, this));
242 } 257 }
243 258
244 void ScriptInjectionManager::OnUserScriptsUpdated( 259 void ScriptInjectionManager::OnUserScriptsUpdated(
245 const std::set<std::string>& changed_extensions, 260 const std::set<std::string>& changed_extensions,
246 const std::vector<UserScript*>& scripts) { 261 const std::vector<UserScript*>& scripts) {
247 for (ScopedVector<ScriptInjection>::iterator iter = 262 for (ScopedVector<ScriptInjection>::iterator iter =
248 pending_injections_.begin(); 263 pending_injections_.begin();
249 iter != pending_injections_.end();) { 264 iter != pending_injections_.end();) {
250 if (changed_extensions.count((*iter)->extension_id()) > 0) 265 if (changed_extensions.count((*iter)->host_id().id()) > 0)
251 iter = pending_injections_.erase(iter); 266 iter = pending_injections_.erase(iter);
252 else 267 else
253 ++iter; 268 ++iter;
254 } 269 }
255 270
256 // If we are currently injecting scripts, we need to make a note that these 271 // If we are currently injecting scripts, we need to make a note that these
257 // extensions were updated. 272 // extensions were updated.
258 if (injecting_scripts_) { 273 if (injecting_scripts_) {
259 invalidated_while_injecting_.insert(changed_extensions.begin(), 274 invalidated_while_injecting_.insert(changed_extensions.begin(),
260 changed_extensions.end()); 275 changed_extensions.end());
(...skipping 109 matching lines...) Expand 10 before | Expand all | Expand 10 after
370 &frame_injections, frame, tab_id, run_location); 385 &frame_injections, frame, tab_id, run_location);
371 386
372 ScriptsRunInfo scripts_run_info; 387 ScriptsRunInfo scripts_run_info;
373 for (ScopedVector<ScriptInjection>::iterator iter = frame_injections.begin(); 388 for (ScopedVector<ScriptInjection>::iterator iter = frame_injections.begin();
374 iter != frame_injections.end();) { 389 iter != frame_injections.end();) {
375 // If a blocking script was injected, there is potentially a possibility 390 // If a blocking script was injected, there is potentially a possibility
376 // that the frame has been invalidated in the time since. Check. 391 // that the frame has been invalidated in the time since. Check.
377 if (!IsFrameValid(frame)) 392 if (!IsFrameValid(frame))
378 break; 393 break;
379 394
395 const std::string extension_id = (*iter)->host_id().id();
396 scoped_ptr<ExtensionInjectionHost> extension_injection_host =
397 GetExtensionInjectionHost(extension_id, extensions_);
380 // Try to inject the script if the extension is not "dirty" (invalidated by 398 // Try to inject the script if the extension is not "dirty" (invalidated by
381 // an update). If the injection does not finish (i.e., it is waiting for 399 // an update). If the injection does not finish (i.e., it is waiting for
382 // permission), add it to the list of pending injections. 400 // permission), add it to the list of pending injections.
383 if (invalidated_while_injecting_.count((*iter)->extension_id()) == 0 && 401 if (invalidated_while_injecting_.count(extension_id) == 0 &&
384 !(*iter)->TryToInject(run_location, 402 !(*iter)->TryToInject(run_location,
385 extensions_->GetByID((*iter)->extension_id()), 403 extension_injection_host.get(),
386 &scripts_run_info)) { 404 &scripts_run_info)) {
387 pending_injections_.insert(pending_injections_.begin(), *iter); 405 pending_injections_.insert(pending_injections_.begin(), *iter);
388 iter = frame_injections.weak_erase(iter); 406 iter = frame_injections.weak_erase(iter);
389 } else { 407 } else {
390 ++iter; 408 ++iter;
391 } 409 }
392 } 410 }
393 411
394 if (IsFrameValid(frame)) 412 if (IsFrameValid(frame))
395 scripts_run_info.LogRun(frame, run_location); 413 scripts_run_info.LogRun(frame, run_location);
(...skipping 16 matching lines...) Expand all
412 "No main frame", 430 "No main frame",
413 GURL(std::string()), 431 GURL(std::string()),
414 base::ListValue())); 432 base::ListValue()));
415 return; 433 return;
416 } 434 }
417 435
418 scoped_ptr<ScriptInjection> injection(new ScriptInjection( 436 scoped_ptr<ScriptInjection> injection(new ScriptInjection(
419 scoped_ptr<ScriptInjector>( 437 scoped_ptr<ScriptInjector>(
420 new ProgrammaticScriptInjector(params, main_frame)), 438 new ProgrammaticScriptInjector(params, main_frame)),
421 main_frame, 439 main_frame,
422 params.extension_id, 440 HostID(HostID::EXTENSIONS, params.extension_id),
441 params.is_web_view ? params.instance_id : HostID::kDefaultInstanceId,
Devlin 2015/02/11 00:00:48 I think there was a thread on this part that I los
Xi Han 2015/02/11 16:00:24 Sorry I might not make myself clear. I add this ch
Devlin 2015/02/11 20:19:44 But we already explicitly set params.instance_id t
Xi Han 2015/02/11 21:19:09 As discussed offline, we will remove this check he
423 static_cast<UserScript::RunLocation>(params.run_at), 442 static_cast<UserScript::RunLocation>(params.run_at),
424 ExtensionHelper::Get(render_view)->tab_id())); 443 ExtensionHelper::Get(render_view)->tab_id()));
425 444
426 ScriptsRunInfo scripts_run_info; 445 ScriptsRunInfo scripts_run_info;
427 FrameStatusMap::const_iterator iter = frame_statuses_.find(main_frame); 446 FrameStatusMap::const_iterator iter = frame_statuses_.find(main_frame);
447
448 scoped_ptr<ExtensionInjectionHost> extension_injection_host =
449 GetExtensionInjectionHost(injection->host_id().id(), extensions_);
450
428 if (!injection->TryToInject( 451 if (!injection->TryToInject(
429 iter == frame_statuses_.end() ? UserScript::UNDEFINED : iter->second, 452 iter == frame_statuses_.end() ? UserScript::UNDEFINED : iter->second,
430 extensions_->GetByID(injection->extension_id()), 453 extension_injection_host.get(),
431 &scripts_run_info)) { 454 &scripts_run_info)) {
432 pending_injections_.push_back(injection.release()); 455 pending_injections_.push_back(injection.release());
433 } 456 }
434 } 457 }
435 458
436 void ScriptInjectionManager::HandleExecuteDeclarativeScript( 459 void ScriptInjectionManager::HandleExecuteDeclarativeScript(
437 blink::WebFrame* web_frame, 460 blink::WebFrame* web_frame,
438 int tab_id, 461 int tab_id,
439 const ExtensionId& extension_id, 462 const ExtensionId& extension_id,
440 int script_id, 463 int script_id,
441 const GURL& url) { 464 const GURL& url) {
465 scoped_ptr<ExtensionInjectionHost> extension_injection_host =
466 GetExtensionInjectionHost(extension_id, extensions_);
442 const Extension* extension = extensions_->GetByID(extension_id); 467 const Extension* extension = extensions_->GetByID(extension_id);
443 // TODO(dcheng): This function signature should really be a WebLocalFrame, 468 // TODO(dcheng): This function signature should really be a WebLocalFrame,
444 // rather than trying to coerce it here. 469 // rather than trying to coerce it here.
445 scoped_ptr<ScriptInjection> injection = 470 scoped_ptr<ScriptInjection> injection =
446 user_script_set_manager_->GetInjectionForDeclarativeScript( 471 user_script_set_manager_->GetInjectionForDeclarativeScript(
447 script_id, 472 script_id,
448 web_frame->toWebLocalFrame(), 473 web_frame->toWebLocalFrame(),
449 tab_id, 474 tab_id,
450 url, 475 url,
451 extension); 476 extension);
452 if (injection.get()) { 477 if (injection.get()) {
453 ScriptsRunInfo scripts_run_info; 478 ScriptsRunInfo scripts_run_info;
454 // TODO(markdittmer): Use return value of TryToInject for error handling. 479 // TODO(markdittmer): Use return value of TryToInject for error handling.
455 injection->TryToInject(UserScript::BROWSER_DRIVEN, 480 injection->TryToInject(UserScript::BROWSER_DRIVEN,
456 extension, 481 extension_injection_host.get(),
457 &scripts_run_info); 482 &scripts_run_info);
458 scripts_run_info.LogRun(web_frame, UserScript::BROWSER_DRIVEN); 483 scripts_run_info.LogRun(web_frame, UserScript::BROWSER_DRIVEN);
459 } 484 }
460 } 485 }
461 486
462 void ScriptInjectionManager::HandlePermitScriptInjection(int64 request_id) { 487 void ScriptInjectionManager::HandlePermitScriptInjection(int64 request_id) {
463 ScopedVector<ScriptInjection>::iterator iter = 488 ScopedVector<ScriptInjection>::iterator iter =
464 pending_injections_.begin(); 489 pending_injections_.begin();
465 for (; iter != pending_injections_.end(); ++iter) { 490 for (; iter != pending_injections_.end(); ++iter) {
466 if ((*iter)->request_id() == request_id) 491 if ((*iter)->request_id() == request_id)
467 break; 492 break;
468 } 493 }
469 if (iter == pending_injections_.end()) 494 if (iter == pending_injections_.end())
470 return; 495 return;
471 496
472 // At this point, because the request is present in pending_injections_, we 497 // At this point, because the request is present in pending_injections_, we
473 // know that this is the same page that issued the request (otherwise, 498 // know that this is the same page that issued the request (otherwise,
474 // RVOHelper's DidStartProvisionalLoad callback would have caused it to be 499 // RVOHelper's DidStartProvisionalLoad callback would have caused it to be
475 // cleared out). 500 // cleared out).
476 501
477 scoped_ptr<ScriptInjection> injection(*iter); 502 scoped_ptr<ScriptInjection> injection(*iter);
478 pending_injections_.weak_erase(iter); 503 pending_injections_.weak_erase(iter);
479 504
480 ScriptsRunInfo scripts_run_info; 505 ScriptsRunInfo scripts_run_info;
481 if (injection->OnPermissionGranted(extensions_->GetByID( 506 scoped_ptr<ExtensionInjectionHost> extension_injection_host =
482 injection->extension_id()), 507 GetExtensionInjectionHost(injection->host_id().id(), extensions_);
508 if (injection->OnPermissionGranted(extension_injection_host.get(),
483 &scripts_run_info)) { 509 &scripts_run_info)) {
484 scripts_run_info.LogRun(injection->web_frame(), UserScript::RUN_DEFERRED); 510 scripts_run_info.LogRun(injection->web_frame(), UserScript::RUN_DEFERRED);
485 } 511 }
486 } 512 }
487 513
488 } // namespace extensions 514 } // namespace extensions
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698