1 // Copyright 2013 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #include "chrome/browser/extensions/chrome_extension_function.h" 6 7 #include "chrome/browser/extensions/extension_function_dispatcher.h" 8 #include "chrome/browser/extensions/window_controller.h" 9 #include "chrome/browser/extensions/window_controller_list.h" 10 #include "chrome/browser/profiles/profile.h" 11 #include "chrome/browser/ui/browser.h" 12 #include "chrome/browser/ui/browser_finder.h" 13 #include "chrome/browser/ui/tabs/tab_strip_model.h" 14 #include "content/public/browser/render_process_host.h" 15 #include "content/public/browser/render_view_host.h" 16 17 using content::RenderViewHost; 18 using content::WebContents; 19 20 ChromeAsyncExtensionFunction::ChromeAsyncExtensionFunction() {} 21 22 Profile* ChromeAsyncExtensionFunction::GetProfile() const { 23 return Profile::FromBrowserContext(context_); 24 } 25 26 bool ChromeAsyncExtensionFunction::CanOperateOnWindow( 27 const extensions::WindowController* window_controller) const { 28 const extensions::Extension* extension = GetExtension(); 29 // |extension| is NULL for unit tests only. 30 if (extension != NULL && !window_controller->IsVisibleToExtension(extension)) 31 return false; 32 33 if (GetProfile() == window_controller->profile()) 34 return true; 35 36 if (!include_incognito()) 37 return false; 38 39 return GetProfile()->HasOffTheRecordProfile() && 40 GetProfile()->GetOffTheRecordProfile() == window_controller->profile(); 41 } 42 43 // TODO(stevenjb): Replace this with GetExtensionWindowController(). 44 Browser* ChromeAsyncExtensionFunction::GetCurrentBrowser() { 45 // If the delegate has an associated browser, return it. 46 if (dispatcher()) { 47 extensions::WindowController* window_controller = 48 dispatcher()->delegate()->GetExtensionWindowController(); 49 if (window_controller) { 50 Browser* browser = window_controller->GetBrowser(); 51 if (browser) 52 return browser; 53 } 54 } 55 56 // Otherwise, try to default to a reasonable browser. If |include_incognito_| 57 // is true, we will also search browsers in the incognito version of this 58 // profile. Note that the profile may already be incognito, in which case 59 // we will search the incognito version only, regardless of the value of 60 // |include_incognito|. Look only for browsers on the active desktop as it is 61 // preferable to pretend no browser is open then to return a browser on 62 // another desktop. 63 if (render_view_host_) { 64 Profile* profile = Profile::FromBrowserContext( 65 render_view_host_->GetProcess()->GetBrowserContext()); 66 Browser* browser = chrome::FindAnyBrowser( 67 profile, include_incognito_, chrome::GetActiveDesktop()); 68 if (browser) 69 return browser; 70 } 71 72 // NOTE(rafaelw): This can return NULL in some circumstances. In particular, 73 // a background_page onload chrome.tabs api call can make it into here 74 // before the browser is sufficiently initialized to return here, or 75 // all of this profile's browser windows may have been closed. 76 // A similar situation may arise during shutdown. 77 // TODO(rafaelw): Delay creation of background_page until the browser 78 // is available. http://code.google.com/p/chromium/issues/detail?id=13284 79 return NULL; 80 } 81 82 extensions::WindowController* 83 ChromeAsyncExtensionFunction::GetExtensionWindowController() { 84 // If the delegate has an associated window controller, return it. 85 if (dispatcher()) { 86 extensions::WindowController* window_controller = 87 dispatcher()->delegate()->GetExtensionWindowController(); 88 if (window_controller) 89 return window_controller; 90 } 91 92 return extensions::WindowControllerList::GetInstance() 93 ->CurrentWindowForFunction(this); 94 } 95 96 content::WebContents* ChromeAsyncExtensionFunction::GetAssociatedWebContents() { 97 content::WebContents* web_contents = 98 UIThreadExtensionFunction::GetAssociatedWebContents(); 99 if (web_contents) 100 return web_contents; 101 102 Browser* browser = GetCurrentBrowser(); 103 if (!browser) 104 return NULL; 105 return browser->tab_strip_model()->GetActiveWebContents(); 106 } 107 108 ChromeAsyncExtensionFunction::~ChromeAsyncExtensionFunction() {} 109 110 ChromeSyncExtensionFunction::ChromeSyncExtensionFunction() {} 111 112 void ChromeSyncExtensionFunction::Run() { SendResponse(RunImpl()); } 113 114 ChromeSyncExtensionFunction::~ChromeSyncExtensionFunction() {} 115