OLD | NEW |
---|---|
1 #!/usr/bin/env python | 1 #!/usr/bin/env python |
2 # Copyright (c) 2012 The Chromium Authors. All rights reserved. | 2 # Copyright (c) 2012 The Chromium Authors. All rights reserved. |
3 # Use of this source code is governed by a BSD-style license that can be | 3 # Use of this source code is governed by a BSD-style license that can be |
4 # found in the LICENSE file. | 4 # found in the LICENSE file. |
5 | 5 |
6 """Basic pyauto performance tests. | 6 """Basic pyauto performance tests. |
7 | 7 |
8 For tests that need to be run for multiple iterations (e.g., so that average | 8 For tests that need to be run for multiple iterations (e.g., so that average |
9 and standard deviation values can be reported), the default number of iterations | 9 and standard deviation values can be reported), the default number of iterations |
10 run for each of these tests is specified by |_DEFAULT_NUM_ITERATIONS|. | 10 run for each of these tests is specified by |_DEFAULT_NUM_ITERATIONS|. |
(...skipping 1710 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1721 fps = result.repeat_frame_times.GetFps() | 1721 fps = result.repeat_frame_times.GetFps() |
1722 assert fps, '%s did not scroll' % url | 1722 assert fps, '%s did not scroll' % url |
1723 logging.info('Iteration %d of %d: %f fps', iteration, | 1723 logging.info('Iteration %d of %d: %f fps', iteration, |
1724 self._num_iterations, fps) | 1724 self._num_iterations, fps) |
1725 results.append(result) | 1725 results.append(result) |
1726 self._PrintSummaryResults( | 1726 self._PrintSummaryResults( |
1727 description, [r.repeat_frame_times.GetFps() for r in results], | 1727 description, [r.repeat_frame_times.GetFps() for r in results], |
1728 'FPS', graph_name) | 1728 'FPS', graph_name) |
1729 | 1729 |
1730 | 1730 |
1731 class BaseWebPageReplay(object): | |
1732 """Run tests with network simulation via Web Page Replay. | |
1733 | |
1734 Web Page Replay is a proxy that can record and "replay" web pages with | |
1735 simulated network characteristics -- without having to edit the pages | |
1736 by hand. With WPR, tests can use "real" web content, and catch | |
1737 performance issues that may result from introducing network delays and | |
1738 bandwidth throttling. | |
1739 | |
1740 This class provides a minimum set of settings for running tests with | |
1741 Web Page Replay. | |
1742 | |
1743 Environment Variables: | |
1744 WPR_RECORD: if set, puts Web Page Replay in record mode instead of replay. | |
1745 WPR_REPLAY_DIR: path to alternate Web Page Replay source (for development). | |
1746 WPR_ARCHIVE_PATH: path to alternate archive file (e.g. '/tmp/foo.wpr'). | |
1747 """ | |
1748 _BASE_DIR = os.path.abspath(os.path.join(os.path.dirname(__file__), | |
1749 '..', '..', '..', '..')) | |
1750 | |
1751 def Path(self, key, **kwargs): | |
1752 """Provide paths for tests using Web Page Replay.""" | |
1753 chromium_path = self._paths[key].format(**kwargs) | |
1754 return os.path.join(self._BASE_DIR, *chromium_path.split('/')) | |
1755 | |
1756 def _ArchivePath(self, test_name): | |
1757 archive_path = self.archive_path or self.Path('archive', | |
1758 test_name=test_name) | |
1759 | |
slamm_google
2012/07/25 17:20:48
Remove extra blank line.
fdeng1
2012/07/25 22:53:28
Done.
| |
1760 if self.is_record_mode: | |
1761 archive_dir = os.path.dirname(archive_path) | |
1762 assert os.path.exists(archive_dir), \ | |
1763 'Archive directory does not exist: %s' % archive_dir | |
1764 else: | |
1765 assert os.path.exists(archive_path), \ | |
1766 'Archive file path does not exist: %s' % archive_path | |
1767 return archive_path | |
1768 | |
1769 def __init__(self): | |
slamm_google
2012/07/25 17:20:48
Move __init__ before Path().
fdeng1
2012/07/25 22:53:28
Done.
| |
1770 # Initialize Web Page Replay related paths | |
dennis_jeffrey
2012/07/24 21:03:19
add period at end of sentence
slamm_google
2012/07/25 17:20:48
How about dropping the comment? And the others too
fdeng1
2012/07/25 22:53:28
Done.
| |
1771 self._paths = { | |
1772 'archive': os.path.join(os.getcwd(), '{test_name}.wpr'), | |
1773 'replay': 'src/third_party/webpagereplay', | |
1774 'logs': 'src/webpagereplay_logs', | |
1775 } | |
1776 | |
1777 # Initialize extra flags for chrome. | |
1778 self.chrome_flags = [ | |
1779 ('--host-resolver-rules=MAP * %s,EXCLUDE localhost' % | |
1780 webpagereplay.REPLAY_HOST), | |
1781 '--testing-fixed-http-port=%s' % webpagereplay.HTTP_PORT, | |
1782 '--testing-fixed-https-port=%s' % webpagereplay.HTTPS_PORT, | |
1783 '--ignore-certificate-errors', | |
1784 ] | |
1785 | |
1786 # Initialize Web Page Replay flags. | |
1787 self._replay_flags = ['--no-dns_forwarding'] | |
1788 | |
1789 self.archive_path = os.environ.get('WPR_ARCHIVE_PATH') | |
1790 self.replay_dir = os.environ.get('WPR_REPLAY_DIR', self.Path('replay')) | |
1791 self.is_record_mode = 'WPR_RECORD' in os.environ | |
1792 if self.is_record_mode: | |
1793 self._num_iterations = 1 | |
slamm_google
2012/07/25 17:20:48
This is a bug from an earlier change. Need to find
fdeng1
2012/07/25 22:53:28
I moved it the setSep() functions in PageCyclerNet
| |
1794 | |
1795 def GetReplayServer(self, test_name): | |
1796 """Create a replay server. | |
1797 | |
1798 Args: | |
1799 test_name: the name of the test which is starting the server. | |
1800 | |
1801 Returns: | |
1802 A replay server. | |
1803 """ | |
1804 replay_flags = self._replay_flags | |
1805 if self.is_record_mode: | |
1806 replay_flags += ['--record'] | |
1807 | |
1808 return webpagereplay.ReplayServer( | |
1809 self.replay_dir, | |
1810 self._ArchivePath(test_name), | |
1811 self.Path('logs'), | |
1812 replay_flags) | |
1813 | |
1814 | |
1815 class PerfWebPageReplay(BaseWebPageReplay): | |
1816 """Run page cycler and scroll tests with network simulation. | |
1817 | |
1818 This class allows customized settings for page cycler and scroll tests. | |
1819 """ | |
1820 | |
1821 def __init__(self): | |
1822 # Call parent __init__ | |
slamm_google
2012/07/25 17:20:48
The comments in this method do not add any value a
fdeng1
2012/07/25 22:53:28
Done.
| |
1823 super(PerfWebPageReplay, self).__init__() | |
1824 | |
1825 # Extra paths for Web Page Replay | |
1826 extra_paths = { | |
1827 'archive': 'src/data/page_cycler/webpagereplay/{test_name}.wpr', | |
1828 'page_sets': 'src/tools/page_cycler/webpagereplay/tests/{test_name}.js', | |
1829 'start_page': 'src/tools/page_cycler/webpagereplay/start.html', | |
1830 'extension': 'src/tools/page_cycler/webpagereplay/extension', | |
1831 } | |
1832 self._paths.update(extra_paths) | |
1833 | |
1834 # Extra chrome flags | |
1835 extra_chrome_flags = [ | |
1836 '--log-level=0', | |
1837 '--disable-background-networking', | |
1838 '--enable-experimental-extension-apis', | |
1839 ' --enable-logging', | |
slamm_google
2012/07/25 17:20:48
Remove the extra whitespace from the flag.
fdeng1
2012/07/25 22:53:28
Done.
| |
1840 '--enable-stats-table', | |
1841 '--enable-benchmarking', | |
1842 '--metrics-recording-only', | |
1843 '--activate-on-launch', | |
1844 ] | |
1845 self.chrome_flags.extend(extra_chrome_flags) | |
1846 | |
1847 | |
1731 class PopularSitesScrollTest(BaseScrollTest): | 1848 class PopularSitesScrollTest(BaseScrollTest): |
1732 """Measures scrolling performance on recorded versions of popular sites.""" | 1849 """Measures scrolling performance on recorded versions of popular sites.""" |
1733 | 1850 |
1851 _web_page_replay = PerfWebPageReplay() | |
1852 | |
1734 def ExtraChromeFlags(self): | 1853 def ExtraChromeFlags(self): |
1735 """Ensures Chrome is launched with custom flags. | 1854 """Ensures Chrome is launched with custom flags. |
1736 | 1855 |
1737 Returns: | 1856 Returns: |
1738 A list of extra flags to pass to Chrome when it is launched. | 1857 A list of extra flags to pass to Chrome when it is launched. |
1739 """ | 1858 """ |
1740 return super(PopularSitesScrollTest, | 1859 return super(PopularSitesScrollTest, |
1741 self).ExtraChromeFlags() + WebPageReplay.CHROME_FLAGS | 1860 self).ExtraChromeFlags() + self._web_page_replay.chrome_flags |
1742 | 1861 |
1743 def _GetUrlList(self, test_name): | 1862 def _GetUrlList(self, test_name): |
1744 """Returns list of recorded sites.""" | 1863 """Returns list of recorded sites.""" |
1745 with open(WebPageReplay.Path('page_sets', test_name=test_name)) as f: | 1864 with open( |
1865 self._web_page_replay.Path('page_sets', test_name=test_name)) as f: | |
1746 sites_text = f.read() | 1866 sites_text = f.read() |
1747 js = """ | 1867 js = """ |
1748 %s | 1868 %s |
1749 window.domAutomationController.send(JSON.stringify(pageSets)); | 1869 window.domAutomationController.send(JSON.stringify(pageSets)); |
1750 """ % sites_text | 1870 """ % sites_text |
1751 page_sets = eval(self.ExecuteJavascript(js)) | 1871 page_sets = eval(self.ExecuteJavascript(js)) |
1752 return list(itertools.chain(*page_sets))[1:] # Skip first. | 1872 return list(itertools.chain(*page_sets))[1:] # Skip first. |
1753 | 1873 |
1754 def _PrintScrollResults(self, results): | 1874 def _PrintScrollResults(self, results): |
1755 self._PrintSummaryResults( | 1875 self._PrintSummaryResults( |
(...skipping 11 matching lines...) Expand all Loading... | |
1767 [r.repeat_frame_times.GetPercentBelow60Fps() for r in results], | 1887 [r.repeat_frame_times.GetPercentBelow60Fps() for r in results], |
1768 'percent', 'PercentBelow60FPS') | 1888 'percent', 'PercentBelow60FPS') |
1769 self._PrintSummaryResults( | 1889 self._PrintSummaryResults( |
1770 'first_paint_time', [r.first_paint_time for r in results], | 1890 'first_paint_time', [r.first_paint_time for r in results], |
1771 'ms', 'FirstPaintTime') | 1891 'ms', 'FirstPaintTime') |
1772 | 1892 |
1773 def test2012Q3(self): | 1893 def test2012Q3(self): |
1774 test_name = '2012Q3' | 1894 test_name = '2012Q3' |
1775 urls = self._GetUrlList(test_name) | 1895 urls = self._GetUrlList(test_name) |
1776 results = [] | 1896 results = [] |
1777 with WebPageReplay().GetReplayServer(test_name): | 1897 with self._web_page_replay.GetReplayServer(test_name): |
1778 for iteration in range(self._num_iterations): | 1898 for iteration in range(self._num_iterations): |
1779 for url in urls: | 1899 for url in urls: |
1780 result = self.RunSingleInvocation(url) | 1900 result = self.RunSingleInvocation(url) |
1781 fps = result.initial_frame_times.GetFps() | 1901 fps = result.initial_frame_times.GetFps() |
1782 assert fps, '%s did not scroll' % url | 1902 assert fps, '%s did not scroll' % url |
1783 logging.info('Iteration %d of %d: %f fps', iteration, | 1903 logging.info('Iteration %d of %d: %f fps', iteration, |
1784 self._num_iterations, fps) | 1904 self._num_iterations, fps) |
1785 results.append(result) | 1905 results.append(result) |
1786 self._PrintScrollResults(results) | 1906 self._PrintScrollResults(results) |
1787 | 1907 |
(...skipping 380 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2168 def testIntl2File(self): | 2288 def testIntl2File(self): |
2169 self.RunPageCyclerTest('intl2', 'Intl2File') | 2289 self.RunPageCyclerTest('intl2', 'Intl2File') |
2170 | 2290 |
2171 def testMozFile(self): | 2291 def testMozFile(self): |
2172 self.RunPageCyclerTest('moz', 'MozFile') | 2292 self.RunPageCyclerTest('moz', 'MozFile') |
2173 | 2293 |
2174 def testMoz2File(self): | 2294 def testMoz2File(self): |
2175 self.RunPageCyclerTest('moz2', 'Moz2File') | 2295 self.RunPageCyclerTest('moz2', 'Moz2File') |
2176 | 2296 |
2177 | 2297 |
2178 class WebPageReplay(object): | |
2179 """Run page cycler tests with network simulation via Web Page Replay. | |
2180 | |
2181 Web Page Replay is a proxy that can record and "replay" web pages with | |
2182 simulated network characteristics -- without having to edit the pages | |
2183 by hand. With WPR, tests can use "real" web content, and catch | |
2184 performance issues that may result from introducing network delays and | |
2185 bandwidth throttling. | |
2186 | |
2187 Environment Variables: | |
2188 WPR_RECORD: if set, puts Web Page Replay in record mode instead of replay. | |
2189 WPR_REPLAY_DIR: path to alternate Web Page Replay source (for development). | |
2190 WPR_ARCHIVE_PATH: path to alternate archive file (e.g. '/tmp/foo.wpr'). | |
2191 """ | |
2192 _PATHS = { | |
2193 'archive': 'src/data/page_cycler/webpagereplay/{test_name}.wpr', | |
2194 'page_sets': 'src/tools/page_cycler/webpagereplay/tests/{test_name}.js', | |
2195 'start_page': 'src/tools/page_cycler/webpagereplay/start.html', | |
2196 'extension': 'src/tools/page_cycler/webpagereplay/extension', | |
2197 'replay': 'src/third_party/webpagereplay', | |
2198 'logs': 'src/webpagereplay_logs', | |
2199 } | |
2200 | |
2201 _BASE_DIR = os.path.abspath(os.path.join(os.path.dirname(__file__), | |
2202 '..', '..', '..', '..')) | |
2203 CHROME_FLAGS = [ | |
2204 '--host-resolver-rules=MAP * %s' % webpagereplay.REPLAY_HOST, | |
2205 '--testing-fixed-http-port=%s' % webpagereplay.HTTP_PORT, | |
2206 '--testing-fixed-https-port=%s' % webpagereplay.HTTPS_PORT, | |
2207 '--log-level=0', | |
2208 '--disable-background-networking', | |
2209 '--enable-experimental-extension-apis', | |
2210 '--enable-logging', | |
2211 '--enable-stats-table', | |
2212 '--enable-benchmarking', | |
2213 '--ignore-certificate-errors', | |
2214 '--metrics-recording-only', | |
2215 '--activate-on-launch', | |
2216 '--no-first-run', | |
2217 '--no-proxy-server', | |
2218 ] | |
2219 | |
2220 @classmethod | |
2221 def Path(cls, key, **kwargs): | |
2222 """Provide paths for tests using Web Page Replay.""" | |
2223 chromium_path = cls._PATHS[key].format(**kwargs) | |
2224 return os.path.join(cls._BASE_DIR, *chromium_path.split('/')) | |
2225 | |
2226 def _ArchivePath(self, test_name): | |
2227 archive_path = self.archive_path or self.Path('archive', | |
2228 test_name=test_name) | |
2229 if self.is_record_mode: | |
2230 archive_dir = os.path.dirname(archive_path) | |
2231 assert os.path.exists(archive_dir), \ | |
2232 'Archive directory does not exist: %s' % archive_dir | |
2233 else: | |
2234 assert os.path.exists(archive_path), \ | |
2235 'Archive file path does not exist: %s' % archive_path | |
2236 return archive_path | |
2237 | |
2238 def __init__(self): | |
2239 self.archive_path = os.environ.get('WPR_ARCHIVE_PATH') | |
2240 self.replay_dir = os.environ.get('WPR_REPLAY_DIR', self.Path('replay')) | |
2241 self.is_record_mode = 'WPR_RECORD' in os.environ | |
2242 if self.is_record_mode: | |
2243 self._num_iterations = 1 | |
2244 | |
2245 def GetReplayServer(self, test_name): | |
2246 replay_options = [] | |
2247 replay_options.append('--no-dns_forwarding') | |
2248 if self.is_record_mode: | |
2249 replay_options.append('--record') | |
2250 return webpagereplay.ReplayServer( | |
2251 self.replay_dir, | |
2252 self._ArchivePath(test_name), | |
2253 self.Path('logs'), | |
2254 replay_options) | |
2255 | |
2256 | |
2257 class PageCyclerNetSimTest(BasePageCyclerTest): | 2298 class PageCyclerNetSimTest(BasePageCyclerTest): |
2258 """Tests to run Web Page Replay backed page cycler tests.""" | 2299 """Tests to run Web Page Replay backed page cycler tests.""" |
2259 MAX_ITERATION_SECONDS = 180 | 2300 MAX_ITERATION_SECONDS = 180 |
2301 _web_page_replay = PerfWebPageReplay() | |
2260 | 2302 |
2261 def ExtraChromeFlags(self): | 2303 def ExtraChromeFlags(self): |
2262 """Ensures Chrome is launched with custom flags. | 2304 """Ensures Chrome is launched with custom flags. |
2263 | 2305 |
2264 Returns: | 2306 Returns: |
2265 A list of extra flags to pass to Chrome when it is launched. | 2307 A list of extra flags to pass to Chrome when it is launched. |
2266 """ | 2308 """ |
2267 flags = super(PageCyclerNetSimTest, self).ExtraChromeFlags() | 2309 flags = super(PageCyclerNetSimTest, self).ExtraChromeFlags() |
2268 flags.append('--load-extension=%s' % WebPageReplay.Path('extension')) | 2310 flags.append('--load-extension=%s' % |
2269 flags.extend(WebPageReplay.CHROME_FLAGS) | 2311 self._web_page_replay.Path('extension')) |
2312 flags.extend(self._web_page_replay.chrome_flags) | |
2270 return flags | 2313 return flags |
2271 | 2314 |
2272 def StartUrl(self, test_name, iterations): | 2315 def StartUrl(self, test_name, iterations): |
2273 start_url = 'file://%s?test=%s&iterations=%d' % ( | 2316 start_url = 'file://%s?test=%s&iterations=%d' % ( |
2274 WebPageReplay.Path('start_page'), test_name, iterations) | 2317 self._web_page_replay.Path('start_page'), test_name, iterations) |
2275 if self.use_auto: | 2318 if self.use_auto: |
2276 start_url += '&auto=1' | 2319 start_url += '&auto=1' |
2277 return start_url | 2320 return start_url |
2278 | 2321 |
2279 def RunPageCyclerTest(self, test_name, description): | 2322 def RunPageCyclerTest(self, test_name, description): |
2280 """Runs the specified PageCycler test. | 2323 """Runs the specified PageCycler test. |
2281 | 2324 |
2282 Args: | 2325 Args: |
2283 test_name: name for archive (.wpr) and config (.js) files. | 2326 test_name: name for archive (.wpr) and config (.js) files. |
2284 description: a string description for the test | 2327 description: a string description for the test |
2285 """ | 2328 """ |
2286 with WebPageReplay().GetReplayServer(test_name): | 2329 with self._web_page_replay.GetReplayServer(test_name): |
2287 super_self = super(PageCyclerNetSimTest, self) | 2330 super_self = super(PageCyclerNetSimTest, self) |
2288 super_self.RunPageCyclerTest(test_name, description) | 2331 super_self.RunPageCyclerTest(test_name, description) |
2289 | 2332 |
2290 def test2012Q2(self): | 2333 def test2012Q2(self): |
2291 self.RunPageCyclerTest('2012Q2', '2012Q2') | 2334 self.RunPageCyclerTest('2012Q2', '2012Q2') |
2292 | 2335 |
2293 | 2336 |
2294 class MemoryTest(BasePerfTest): | 2337 class MemoryTest(BasePerfTest): |
2295 """Tests to measure memory consumption under different usage scenarios.""" | 2338 """Tests to measure memory consumption under different usage scenarios.""" |
2296 | 2339 |
(...skipping 327 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2624 """Identifies the port number to which the server is currently bound. | 2667 """Identifies the port number to which the server is currently bound. |
2625 | 2668 |
2626 Returns: | 2669 Returns: |
2627 The numeric port number to which the server is currently bound. | 2670 The numeric port number to which the server is currently bound. |
2628 """ | 2671 """ |
2629 return self._server.server_address[1] | 2672 return self._server.server_address[1] |
2630 | 2673 |
2631 | 2674 |
2632 if __name__ == '__main__': | 2675 if __name__ == '__main__': |
2633 pyauto_functional.Main() | 2676 pyauto_functional.Main() |
OLD | NEW |