OLD | NEW |
---|---|
1 # Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 # Copyright (c) 2012 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 """Constrained network server (CNS) test base.""" | 5 """Constrained network server (CNS) test base.""" |
6 | 6 |
7 import logging | 7 import logging |
8 import os | 8 import os |
9 import Queue | 9 import Queue |
10 import subprocess | 10 import subprocess |
11 import sys | 11 import sys |
12 import threading | 12 import threading |
13 import urllib2 | 13 import urllib2 |
14 | 14 |
15 import pyauto | 15 import pyauto |
16 import pyauto_paths | 16 import pyauto_paths |
17 | 17 |
18 WINDOWS = 'win32' in sys.platform | |
19 | 18 |
20 # List of commonly used network constraints settings. | 19 # List of commonly used network constraints settings. |
21 # Each setting is a tuppe of the form: | 20 # Each setting is a tuppe of the form: |
22 # ('TEST_NAME', [BANDWIDTH_Kbps, LATENCY_ms, PACKET_LOSS_%]) | 21 # ('TEST_NAME', [BANDWIDTH_Kbps, LATENCY_ms, PACKET_LOSS_%]) |
23 # | 22 # |
24 # Note: The test name should satisfy the regex [\w\.-]+ (check | 23 # Note: The test name should satisfy the regex [\w\.-]+ (check |
25 # tools/perf_expectations/tests/perf_expectations_unittest.py for details). It | 24 # tools/perf_expectations/tests/perf_expectations_unittest.py for details). It |
26 # is used to name the result graphs on the dashboards. | 25 # is used to name the result graphs on the dashboards. |
27 # | 26 # |
28 # The WiFi, DSL, and Cable settings were taken from webpagetest.org as | 27 # The WiFi, DSL, and Cable settings were taken from webpagetest.org as |
29 # approximations of their respective real world networks. The settings were | 28 # approximations of their respective real world networks. The settings were |
30 # based on 2011 FCC Broadband Data report (http://www.fcc.gov/document/ | 29 # based on 2011 FCC Broadband Data report (http://www.fcc.gov/document/ |
31 # measuring-broadband-america-report-consumer-broadband-performance-us). | 30 # measuring-broadband-america-report-consumer-broadband-performance-us). |
32 DialUp = ('DialUp', [56, 120, 5]) | 31 DialUp = ('DialUp', [56, 120, 5]) |
33 Slow = ('Slow', [256, 105, 1]) | 32 Slow = ('Slow', [256, 105, 1]) |
34 Wifi = ('Wifi', [1024, 60, 0]) | 33 Wifi = ('Wifi', [1024, 60, 0]) |
35 DSL = ('DSL', [1541, 50, 0]) | 34 DSL = ('DSL', [1541, 50, 0]) |
36 Cable = ('Cable', [5120, 28, 0]) | 35 Cable = ('Cable', [5120, 28, 0]) |
37 NoConstraints = ('NoConstraints', [0, 0, 0]) | 36 NoConstraints = ('NoConstraints', [0, 0, 0]) |
38 | 37 |
39 # Path to CNS executable relative to source root. | 38 # Path to CNS executable relative to source root. |
40 _CNS_PATH = os.path.join( | 39 _CNS_PATH = os.path.join( |
41 'media', 'tools', 'constrained_network_server', 'cns.py') | 40 'media', 'tools', 'constrained_network_server', 'cns.py') |
42 | 41 |
43 # Port to start the CNS on. | 42 # Port to start the CNS on. |
44 _CNS_PORT = 9000 | 43 _CNS_PORT = 9000 |
45 | 44 |
45 # A flag to determine whether to launch a local CNS instance or to connect | |
46 # to the external CNS server. Default to False since all current bots use an | |
47 # external instance. | |
48 # If not on Windows, set USE_LOCAL_CNS=1 env variable to switch the flag. | |
49 USE_LOCAL_CNS = False | |
DaleCurtis
2012/08/16 19:54:59
USE_LOCAL_CNS = ('win' not in sys.platform or ('US
shadi
2012/08/16 20:27:03
s/or/and right?
| |
50 if 'win' not in sys.platform: | |
51 try: | |
52 USE_LOCAL_CNS = (os.environ['USE_LOCAL_CNS'] == '1') | |
53 except: | |
54 pass | |
55 | |
46 # Base CNS URL, only requires & separated parameter names appended. | 56 # Base CNS URL, only requires & separated parameter names appended. |
47 if WINDOWS: | 57 if USE_LOCAL_CNS: |
58 CNS_BASE_URL = 'http://127.0.0.1:%d/ServeConstrained?' % _CNS_PORT | |
59 else: | |
48 CNS_BASE_URL = 'http://chromeperf34:%d/ServeConstrained?' % _CNS_PORT | 60 CNS_BASE_URL = 'http://chromeperf34:%d/ServeConstrained?' % _CNS_PORT |
49 else: | 61 CNS_CLEANUP_URL = 'http://chromeperf34:%d/Cleanup' % _CNS_PORT |
50 CNS_BASE_URL = 'http://127.0.0.1:%d/ServeConstrained?' % _CNS_PORT | |
51 | 62 |
52 # Used for server sanity check. | 63 # Used for server sanity check. |
53 _TEST_VIDEO = 'roller.webm' | 64 _TEST_VIDEO = 'roller.webm' |
54 | 65 |
55 # Directory root to serve files from. | 66 # Directory root to serve files from. |
56 _ROOT_PATH = os.path.join(pyauto.PyUITest.DataDir(), 'pyauto_private', 'media') | 67 _ROOT_PATH = os.path.join(pyauto.PyUITest.DataDir(), 'pyauto_private', 'media') |
57 | 68 |
58 | 69 |
59 class CNSTestBase(pyauto.PyUITest): | 70 class CNSTestBase(pyauto.PyUITest): |
60 """CNS test base hadles startup and teardown of CNS server.""" | 71 """CNS test base hadles startup and teardown of CNS server.""" |
61 | 72 |
62 def __init__(self, *args, **kwargs): | 73 def __init__(self, *args, **kwargs): |
63 """Initialize CNSTestBase by setting the arguments for CNS server. | 74 """Initialize CNSTestBase by setting the arguments for CNS server. |
64 | 75 |
65 Args: | 76 Args: |
66 Check cns.py command line argument list for details. | 77 Check cns.py command line argument list for details. |
67 """ | 78 """ |
68 self._port = kwargs.get('port', _CNS_PORT) | 79 self._port = kwargs.get('port', _CNS_PORT) |
69 self._interface = kwargs.get('interface', 'lo') | 80 self._interface = kwargs.get('interface', 'lo') |
70 self._www_root = kwargs.get('www_root', _ROOT_PATH) | 81 self._www_root = kwargs.get('www_root', _ROOT_PATH) |
71 self._verbose = kwargs.get('verbose', True) | 82 self._verbose = kwargs.get('verbose', True) |
72 self._expiry_time = kwargs.get('expiry_time', 0) | 83 self._expiry_time = kwargs.get('expiry_time', 0) |
73 self._socket_timeout = kwargs.get('socket_timeout') | 84 self._socket_timeout = kwargs.get('socket_timeout') |
74 pyauto.PyUITest.__init__(self, *args, **kwargs) | 85 pyauto.PyUITest.__init__(self, *args, **kwargs) |
75 | 86 |
76 def setUp(self): | 87 def setUp(self): |
77 """Ensures the Constrained Network Server (CNS) server is up and running.""" | 88 """Ensures the Constrained Network Server (CNS) server is up and running.""" |
78 if WINDOWS: | 89 if USE_LOCAL_CNS: |
79 self._SetUpWin() | 90 self._SetUpLocal() |
80 else: | 91 else: |
81 self._SetUpLinux() | 92 self._SetUpExternal() |
82 | 93 |
83 def _SetUpWin(self): | 94 def _SetUpExternal(self): |
84 """Ensures the test can connect to the external CNS server.""" | 95 """Ensures the test can connect to the external CNS server.""" |
85 if self.WaitUntil(self._CanAccessServer, retry_sleep=3, timeout=30, | 96 if self.WaitUntil(self._CanAccessServer, retry_sleep=3, timeout=30, |
86 debug=False): | 97 debug=False): |
87 pyauto.PyUITest.setUp(self) | 98 pyauto.PyUITest.setUp(self) |
88 else: | 99 else: |
89 self.fail('Failed to connect to CNS.') | 100 self.fail('Failed to connect to CNS.') |
90 | 101 |
91 def _SetUpLinux(self): | 102 def _SetUpLocal(self): |
92 """Starts the CNS server locally.""" | 103 """Starts the CNS server locally.""" |
93 cmd = [sys.executable, os.path.join(pyauto_paths.GetSourceDir(), _CNS_PATH), | 104 cmd = [sys.executable, os.path.join(pyauto_paths.GetSourceDir(), _CNS_PATH), |
94 '--port', str(self._port), | 105 '--port', str(self._port), |
95 '--interface', self._interface, | 106 '--interface', self._interface, |
96 '--www-root', self._www_root, | 107 '--www-root', self._www_root, |
97 '--expiry-time', str(self._expiry_time)] | 108 '--expiry-time', str(self._expiry_time)] |
98 | 109 |
99 if self._socket_timeout: | 110 if self._socket_timeout: |
100 cmd.extend(['--socket-timeout', str(self._socket_timeout)]) | 111 cmd.extend(['--socket-timeout', str(self._socket_timeout)]) |
101 if self._verbose: | 112 if self._verbose: |
(...skipping 13 matching lines...) Expand all Loading... | |
115 def _CanAccessServer(self): | 126 def _CanAccessServer(self): |
116 """Checks if the CNS server can serve a file with no network constraints.""" | 127 """Checks if the CNS server can serve a file with no network constraints.""" |
117 test_url = ''.join([CNS_BASE_URL, 'f=', _TEST_VIDEO]) | 128 test_url = ''.join([CNS_BASE_URL, 'f=', _TEST_VIDEO]) |
118 try: | 129 try: |
119 return urllib2.urlopen(test_url) is not None | 130 return urllib2.urlopen(test_url) is not None |
120 except Exception: | 131 except Exception: |
121 return False | 132 return False |
122 | 133 |
123 def tearDown(self): | 134 def tearDown(self): |
124 """Stops the Constrained Network Server (CNS).""" | 135 """Stops the Constrained Network Server (CNS).""" |
125 pyauto.PyUITest.tearDown(self) | 136 if USE_LOCAL_CNS: |
126 if not WINDOWS: | |
127 logging.debug('Stopping CNS server.') | 137 logging.debug('Stopping CNS server.') |
128 # Do not use process.kill(), it will not clean up cns. | 138 # Do not use process.kill(), it will not clean up cns. |
129 self.Kill(self._cns_process.pid) | 139 self.Kill(self._cns_process.pid) |
130 # Need to wait since the process logger has a lock on the process stderr. | 140 # Need to wait since the process logger has a lock on the process stderr. |
131 self._cns_process.wait() | 141 self._cns_process.wait() |
132 self.assertFalse(self._cns_process.returncode is None) | 142 self.assertFalse(self._cns_process.returncode is None) |
133 logging.debug('CNS server stopped.') | 143 logging.debug('CNS server stopped.') |
144 else: | |
145 # Call CNS Cleanup to remove all ports created by this client. | |
146 self.NavigateToURL(CNS_CLEANUP_URL) | |
147 pyauto.PyUITest.tearDown(self) | |
134 | 148 |
135 | 149 |
136 class ProcessLogger(threading.Thread): | 150 class ProcessLogger(threading.Thread): |
137 """A thread to log a process's stderr output.""" | 151 """A thread to log a process's stderr output.""" |
138 | 152 |
139 def __init__(self, process): | 153 def __init__(self, process): |
140 """Starts the process logger thread. | 154 """Starts the process logger thread. |
141 | 155 |
142 Args: | 156 Args: |
143 process: The process to log. | 157 process: The process to log. |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
182 """ | 196 """ |
183 # Convert relative test path into an absolute path. | 197 # Convert relative test path into an absolute path. |
184 tasks = Queue.Queue() | 198 tasks = Queue.Queue() |
185 for file_name in test_media_files: | 199 for file_name in test_media_files: |
186 for series_name, settings in network_constraints_settings: | 200 for series_name, settings in network_constraints_settings: |
187 logging.debug('Add test: %s\tSettings: %s\tMedia: %s', series_name, | 201 logging.debug('Add test: %s\tSettings: %s\tMedia: %s', series_name, |
188 settings, file_name) | 202 settings, file_name) |
189 tasks.put((series_name, settings, file_name)) | 203 tasks.put((series_name, settings, file_name)) |
190 | 204 |
191 return tasks | 205 return tasks |
OLD | NEW |