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

Unified Diff: tools/perf/profile_creators/fast_navigation_profile_extender.py

Issue 1124543006: Telemetry: Update exception handling in FastNavigationProfileExtender. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Comments from nednguyen. Created 5 years, 7 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: tools/perf/profile_creators/fast_navigation_profile_extender.py
diff --git a/tools/perf/profile_creators/fast_navigation_profile_extender.py b/tools/perf/profile_creators/fast_navigation_profile_extender.py
index d5b3da74caea6f517258f50e6b0c5dd16037b862..f37bc5da24b7e7a22b2847e9784333f61184afdf 100644
--- a/tools/perf/profile_creators/fast_navigation_profile_extender.py
+++ b/tools/perf/profile_creators/fast_navigation_profile_extender.py
@@ -5,6 +5,7 @@ import time
from profile_creators import profile_extender
from telemetry.core import exceptions
+from telemetry.core import util
class FastNavigationProfileExtender(profile_extender.ProfileExtender):
@@ -36,11 +37,13 @@ class FastNavigationProfileExtender(profile_extender.ProfileExtender):
# The number of tabs to use.
self._NUM_TABS = maximum_batch_size
- # The amount of time to wait for a batch of pages to finish loading.
- self._BATCH_PAGE_LOAD_TIMEOUT_IN_SECONDS = 10
+ # The amount of additional time to wait for a batch of pages to finish
+ # loading for each page in the batch.
+ self._BATCH_TIMEOUT_PER_PAGE_IN_SECONDS = 20
- # The default amount of time to wait for the retrieval of the URL of a tab.
- self._TAB_URL_RETRIEVAL_TIMEOUT_IN_SECONDS = 1
+ # The amount of time to wait for a page to quiesce. Some pages will never
+ # quiesce.
+ self._TIME_TO_WAIT_FOR_PAGE_TO_QUIESCE_IN_SECONDS = 10
def Run(self):
"""Superclass override."""
@@ -50,6 +53,21 @@ class FastNavigationProfileExtender(profile_extender.ProfileExtender):
finally:
self.TearDownBrowser()
+ # When there hasn't been an exception, verify that the profile was
+ # correctly extended.
+ # TODO(erikchen): I've intentionally omitted my implementation of
+ # VerifyProfileWasExtended() in small_profile_extender, since the profile
+ # is not being correctly extended. http://crbug.com/484833
+ # http://crbug.com/484880
+ self.VerifyProfileWasExtended()
+
+ def VerifyProfileWasExtended(self):
+ """Verifies that the profile was correctly extended.
+
+ Can be overridden by subclasses.
+ """
+ pass
+
def GetUrlIterator(self):
"""Gets URLs for the browser to navigate to.
@@ -75,21 +93,6 @@ class FastNavigationProfileExtender(profile_extender.ProfileExtender):
"""
pass
- def _AddNewTab(self):
- """Adds a new tab to the browser."""
-
- # Adding a new tab requires making a request over devtools. This can fail
- # for a variety of reasons. Retry 3 times.
- retry_count = 3
- for i in range(retry_count):
- try:
- self._navigation_tabs.append(self._browser.tabs.New())
- except exceptions.Error:
- if i == retry_count - 1:
- raise
- else:
- break
-
def _RefreshNavigationTabs(self):
"""Updates the member self._navigation_tabs to contain self._NUM_TABS
elements, each of which is not crashed. The crashed tabs are intentionally
@@ -104,7 +107,7 @@ class FastNavigationProfileExtender(profile_extender.ProfileExtender):
self._navigation_tabs = live_tabs
while len(self._navigation_tabs) < self._NUM_TABS:
- self._AddNewTab()
+ self._navigation_tabs.append(self._browser.tabs.New())
def _RemoveNavigationTab(self, tab):
"""Removes a tab which is no longer in a useable state from
@@ -114,23 +117,23 @@ class FastNavigationProfileExtender(profile_extender.ProfileExtender):
def _RetrieveTabUrl(self, tab, timeout):
"""Retrives the URL of the tab."""
- try:
- return tab.EvaluateJavaScript('document.URL', timeout)
- except exceptions.Error:
- return None
+ # TODO(erikchen): Use tab.url instead, which talks to the browser process
+ # instead of the renderer process. http://crbug.com/486119
+ return tab.EvaluateJavaScript('document.URL', timeout)
+
+ def _WaitForUrlToChange(self, tab, initial_url, end_time):
+ """Waits for the tab to navigate away from its initial url.
- def _WaitForUrlToChange(self, tab, initial_url, timeout):
- """Waits for the tab to navigate away from its initial url."""
- end_time = time.time() + timeout
+ If time.time() is larger than end_time, the function does nothing.
+ Otherwise, the function tries to return no later than end_time.
+ """
while True:
seconds_to_wait = end_time - time.time()
- seconds_to_wait = max(0, seconds_to_wait)
-
- if seconds_to_wait == 0:
+ if seconds_to_wait <= 0:
break
current_url = self._RetrieveTabUrl(tab, seconds_to_wait)
- if current_url != initial_url:
+ if current_url != initial_url and current_url != "":
break
# Retrieving the current url is a non-trivial operation. Add a small
@@ -138,6 +141,26 @@ class FastNavigationProfileExtender(profile_extender.ProfileExtender):
# navigation.
time.sleep(0.01)
+ def _WaitForTabToBeReady(self, tab, end_time):
+ """Waits for the tab to be ready.
+
+ If time.time() is larger than end_time, the function does nothing.
+ Otherwise, the function tries to return no later than end_time.
+ """
+ seconds_to_wait = end_time - time.time()
+ if seconds_to_wait <= 0:
+ return
+ tab.WaitForDocumentReadyStateToBeComplete(seconds_to_wait)
+
+ # Wait up to 10 seconds for the page to quiesce. If the page hasn't
+ # quiesced in 10 seconds, it will probably never quiesce.
+ seconds_to_wait = end_time - time.time()
+ seconds_to_wait = max(0, seconds_to_wait)
+ try:
+ util.WaitFor(tab.HasReachedQuiescence, seconds_to_wait)
+ except exceptions.TimeoutException:
+ pass
+
def _BatchNavigateTabs(self, batch):
"""Performs a batch of tab navigations with minimal delay.
@@ -148,21 +171,22 @@ class FastNavigationProfileExtender(profile_extender.ProfileExtender):
A list of tuples (tab, initial_url). |initial_url| is the url of the
|tab| prior to a navigation command being sent to it.
"""
- timeout_in_seconds = 0
+ # Attempting to pass in a timeout of 0 seconds results in a synchronous
+ # socket error from the websocket library. Pass in a very small timeout
+ # instead so that the websocket library raises a Timeout exception. This
+ # prevents the logic from accidentally catching different socket
+ # exceptions.
+ timeout_in_seconds = 0.01
queued_tabs = []
for tab, url in batch:
- initial_url = self._RetrieveTabUrl(tab,
- self._TAB_URL_RETRIEVAL_TIMEOUT_IN_SECONDS)
-
+ initial_url = self._RetrieveTabUrl(tab, 20)
try:
tab.Navigate(url, None, timeout_in_seconds)
- except exceptions.Error:
- # We expect a time out. It's possible for other problems to arise, but
- # this method is not responsible for dealing with them. Ignore all
- # exceptions.
+ except exceptions.TimeoutException:
+ # We expect to receive a timeout exception, since we're not waiting for
+ # the navigation to complete.
pass
-
queued_tabs.append((tab, initial_url))
return queued_tabs
@@ -173,30 +197,14 @@ class FastNavigationProfileExtender(profile_extender.ProfileExtender):
queued_tabs: A list of tuples (tab, initial_url). Each tab is guaranteed
to have already been sent a navigation command.
"""
- end_time = time.time() + self._BATCH_PAGE_LOAD_TIMEOUT_IN_SECONDS
+ total_batch_timeout = (len(queued_tabs) *
+ self._BATCH_TIMEOUT_PER_PAGE_IN_SECONDS)
+ end_time = time.time() + total_batch_timeout
for tab, initial_url in queued_tabs:
- seconds_to_wait = end_time - time.time()
- seconds_to_wait = max(0, seconds_to_wait)
-
- if seconds_to_wait == 0:
- break
-
- # Since we don't wait any time for the tab url navigation to commit, it's
+ # Since we didn't wait any time for the tab url navigation to commit, it's
# possible that the tab hasn't started navigating yet.
- self._WaitForUrlToChange(tab, initial_url, seconds_to_wait)
-
- seconds_to_wait = end_time - time.time()
- seconds_to_wait = max(0, seconds_to_wait)
-
- try:
- tab.WaitForDocumentReadyStateToBeComplete(seconds_to_wait)
- except exceptions.TimeoutException:
- # Ignore time outs.
- pass
- except exceptions.Error:
- # If any error occurs, remove the tab. it's probably in an
- # unrecoverable state.
- self._RemoveNavigationTab(tab)
+ self._WaitForUrlToChange(tab, initial_url, end_time)
+ self._WaitForTabToBeReady(tab, end_time)
def _GetUrlsToNavigate(self, url_iterator):
"""Returns an array of urls to navigate to, given a url_iterator."""
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698