diff options
author | tengs@chromium.org <tengs@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-10-02 00:07:01 +0000 |
---|---|---|
committer | tengs@chromium.org <tengs@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-10-02 00:07:01 +0000 |
commit | 47a017a331296c2b52c2470d1fddf6fa5205892d (patch) | |
tree | b64c40e0002db91e4135d12512a3ff1bf2ebe0b7 | |
parent | a20524cbf3a16009ebdd97ae51fb79b1e861949a (diff) | |
download | chromium_src-47a017a331296c2b52c2470d1fddf6fa5205892d.zip chromium_src-47a017a331296c2b52c2470d1fddf6fa5205892d.tar.gz chromium_src-47a017a331296c2b52c2470d1fddf6fa5205892d.tar.bz2 |
Fix for extension binding race condition when evaluating JS.
A bug causing extension bindings not to be initialized was fixed in
revision 155947. This patch adds a workaround for older Chrome versions.
BUG=251913
TEST=manual
NOTRY=true
Committed: https://src.chromium.org/viewvc/chrome?view=rev&revision=217384
Review URL: https://codereview.chromium.org/19774009
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@226358 0039d316-1c4b-4281-b951-d872f2087c98
7 files changed, 43 insertions, 5 deletions
diff --git a/tools/telemetry/telemetry/core/backends/chrome/chrome_browser_backend.py b/tools/telemetry/telemetry/core/backends/chrome/chrome_browser_backend.py index 9d72dc6..1d18f31 100644 --- a/tools/telemetry/telemetry/core/backends/chrome/chrome_browser_backend.py +++ b/tools/telemetry/telemetry/core/backends/chrome/chrome_browser_backend.py @@ -138,8 +138,22 @@ class ChromeBrowserBackend(browser_backend.BrowserBackend): if not e.extension_id in self._extension_dict_backend: return False extension_object = self._extension_dict_backend[e.extension_id] - res = extension_object.EvaluateJavaScript( - extension_ready_js % e.extension_id) + try: + res = extension_object.EvaluateJavaScript( + extension_ready_js % e.extension_id) + except exceptions.EvaluateException: + # If the inspected page is not ready, we will get an error + # when we evaluate a JS expression, but we can just keep polling + # until the page is ready (crbug.com/251913). + res = None + + # TODO(tengs): We don't have full support for getting the Chrome + # version before launch, so for now we use a generic workaround to + # check for an extension binding bug in old versions of Chrome. + # See crbug.com/263162 for details. + if res and extension_object.EvaluateJavaScript( + 'chrome.runtime == null'): + extension_object.Reload() if not res: return False return True diff --git a/tools/telemetry/telemetry/core/backends/chrome/extension_dict_backend.py b/tools/telemetry/telemetry/core/backends/chrome/extension_dict_backend.py index 40e76d0..b45bb6c 100644 --- a/tools/telemetry/telemetry/core/backends/chrome/extension_dict_backend.py +++ b/tools/telemetry/telemetry/core/backends/chrome/extension_dict_backend.py @@ -45,6 +45,8 @@ class ExtensionDictBackend(object): if not extension_info or not 'webSocketDebuggerUrl' in extension_info: raise ExtensionNotFoundException() return extension_page.ExtensionPage( + extension_id, + extension_info['url'], self._CreateInspectorBackendForDebuggerUrl( extension_info['webSocketDebuggerUrl'])) diff --git a/tools/telemetry/telemetry/core/backends/chrome/inspector_page.py b/tools/telemetry/telemetry/core/backends/chrome/inspector_page.py index 505a398..99890c3 100644 --- a/tools/telemetry/telemetry/core/backends/chrome/inspector_page.py +++ b/tools/telemetry/telemetry/core/backends/chrome/inspector_page.py @@ -14,13 +14,15 @@ class InspectorPage(object): self._OnNotification, self._OnClose) self._navigation_pending = False + self._navigation_url = "" def _OnNotification(self, msg): logging.debug('Notification: %s', json.dumps(msg, indent=2)) if msg['method'] == 'Page.frameNavigated' and self._navigation_pending: url = msg['params']['frame']['url'] - if (not url == 'chrome://newtab/' and not url == 'about:blank' - and not 'parentId' in msg['params']['frame']): + if (self._navigation_url == url or + (not url == 'chrome://newtab/' and not url == 'about:blank' + and not 'parentId' in msg['params']['frame'])): # Marks the navigation as complete and unblocks the # PerformActionAndWaitForNavigate call. self._navigation_pending = False @@ -93,6 +95,7 @@ class InspectorPage(object): } } self._inspector_backend.SendAndIgnoreResponse(request) + self._navigation_url = url self.PerformActionAndWaitForNavigate(DoNavigate, timeout) def GetCookieByName(self, name, timeout=60): diff --git a/tools/telemetry/telemetry/core/extension_page.py b/tools/telemetry/telemetry/core/extension_page.py index 0ca5d29..3402878 100644 --- a/tools/telemetry/telemetry/core/extension_page.py +++ b/tools/telemetry/telemetry/core/extension_page.py @@ -5,8 +5,18 @@ from telemetry.core import web_contents class ExtensionPage(web_contents.WebContents): """Represents a an extension page in the browser""" - def __init__(self, inspector_backend): + def __init__(self, extension_id, url, inspector_backend): super(ExtensionPage, self).__init__(inspector_backend) + self.extension_id = extension_id + self.url = url + assert url.startswith('chrome-extension://' + extension_id) def __del__(self): super(ExtensionPage, self).__del__() + + def Reload(self): + """ Reloading an extension page is used as a workaround for an extension + binding bug for old versions of Chrome (crbug.com/263162). After Navigate + returns, we are guaranteed that the inspected page is in the correct state. + """ + self._inspector_backend.Navigate(self.url, None, 10) diff --git a/tools/telemetry/telemetry/core/extension_unittest.py b/tools/telemetry/telemetry/core/extension_unittest.py index b15fd99..1b33021 100644 --- a/tools/telemetry/telemetry/core/extension_unittest.py +++ b/tools/telemetry/telemetry/core/extension_unittest.py @@ -44,6 +44,8 @@ class ExtensionTest(unittest.TestCase): logging.warning('Did not find a browser that supports extensions, ' 'skipping test.') return + self.assertTrue( + self._extension.EvaluateJavaScript('chrome.runtime != null')) self._extension.ExecuteJavaScript('setTestVar("abcdef")') self.assertEquals('abcdef', self._extension.EvaluateJavaScript('_testVar')) @@ -125,6 +127,8 @@ class MultipleExtensionTest(unittest.TestCase): for load_extension in self._extensions_to_load: extension = self._browser.extensions[load_extension] assert extension + self.assertTrue( + extension.EvaluateJavaScript('chrome.runtime != null')) extension.ExecuteJavaScript('setTestVar("abcdef")') self.assertEquals('abcdef', extension.EvaluateJavaScript('_testVar')) @@ -147,6 +151,8 @@ class ComponentExtensionTest(unittest.TestCase): with browser_to_create.Create() as b: b.Start() extension = b.extensions[load_extension] + self.assertTrue( + extension.EvaluateJavaScript('chrome.runtime != null')) extension.ExecuteJavaScript('setTestVar("abcdef")') self.assertEquals('abcdef', extension.EvaluateJavaScript('_testVar')) diff --git a/tools/telemetry/telemetry/core/tab_unittest.py b/tools/telemetry/telemetry/core/tab_unittest.py index f555dc2..3bc3089 100644 --- a/tools/telemetry/telemetry/core/tab_unittest.py +++ b/tools/telemetry/telemetry/core/tab_unittest.py @@ -44,6 +44,7 @@ class TabTest(tab_test_case.TabTestCase): self.assertTrue(_IsDocumentVisible(self._tab)) new_tab = self._browser.tabs.New() + new_tab.Navigate('about:blank') util.WaitFor(lambda: _IsDocumentVisible(new_tab), timeout=5) self.assertFalse(_IsDocumentVisible(self._tab)) self._tab.Activate() diff --git a/tools/telemetry/telemetry/unittest/tab_test_case.py b/tools/telemetry/telemetry/unittest/tab_test_case.py index 9ccd504..402109e 100644 --- a/tools/telemetry/telemetry/unittest/tab_test_case.py +++ b/tools/telemetry/telemetry/unittest/tab_test_case.py @@ -28,6 +28,8 @@ class TabTestCase(unittest.TestCase): self._browser = browser_to_create.Create() self._browser.Start() self._tab = self._browser.tabs[0] + self._tab.Navigate('about:blank') + except: self.tearDown() raise |