OLD | NEW |
(Empty) | |
| 1 #!/usr/bin/python |
| 2 # Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 3 # Use of this source code is governed by a BSD-style license that can be |
| 4 # found in the LICENSE file. |
| 5 |
| 6 import logging |
| 7 import os |
| 8 |
| 9 import android_commands |
| 10 from chrome_test_server_spawner import SpawningServer |
| 11 from flag_changer import FlagChanger |
| 12 import lighttpd_server |
| 13 import run_tests_helper |
| 14 |
| 15 FORWARDER_PATH = '/data/local/tmp/forwarder' |
| 16 # These ports must match up with the constants in net/test/test_server.cc |
| 17 TEST_SERVER_SPAWNER_PORT = 8001 |
| 18 TEST_SERVER_PORT = 8002 |
| 19 TEST_SYNC_SERVER_PORT = 8003 |
| 20 |
| 21 |
| 22 class BaseTestRunner(object): |
| 23 """Base class for running tests on a single device.""" |
| 24 |
| 25 def __init__(self, device): |
| 26 """ |
| 27 Args: |
| 28 device: Tests will run on the device of this ID. |
| 29 """ |
| 30 self.device = device |
| 31 self.adb = android_commands.AndroidCommands(device=device) |
| 32 # Synchronize date/time between host and device. Otherwise same file on |
| 33 # host and device may have different timestamp which may cause |
| 34 # AndroidCommands.PushIfNeeded failed, or a test which may compare timestamp |
| 35 # got from http head and local time could be failed. |
| 36 self.adb.SynchronizeDateTime() |
| 37 self._http_server = None |
| 38 self._forwarder = None |
| 39 self._spawning_server = None |
| 40 self._spawner_forwarder = None |
| 41 self._forwarder_device_port = 8000 |
| 42 self._forwarder_base_url = ('http://localhost:%d' % |
| 43 self._forwarder_device_port) |
| 44 self._flags = FlagChanger(self.adb) |
| 45 |
| 46 def RunTests(self): |
| 47 # TODO(bulach): this should actually do SetUp / RunTestsInternal / TearDown. |
| 48 # Refactor the various subclasses to expose a RunTestsInternal without |
| 49 # any params. |
| 50 raise NotImplementedError |
| 51 |
| 52 def SetUp(self): |
| 53 """Called before tests run.""" |
| 54 pass |
| 55 |
| 56 def TearDown(self): |
| 57 """Called when tests finish running.""" |
| 58 self.ShutdownHelperToolsForTestSuite() |
| 59 |
| 60 def CopyTestData(self, test_data_paths, dest_dir): |
| 61 """Copies |test_data_paths| list of files/directories to |dest_dir|. |
| 62 |
| 63 Args: |
| 64 test_data_paths: A list of files or directories relative to |dest_dir| |
| 65 which should be copied to the device. The paths must exist in |
| 66 |CHROME_DIR|. |
| 67 dest_dir: Absolute path to copy to on the device. |
| 68 """ |
| 69 for p in test_data_paths: |
| 70 self.adb.PushIfNeeded( |
| 71 os.path.join(run_tests_helper.CHROME_DIR, p), |
| 72 os.path.join(dest_dir, p)) |
| 73 |
| 74 def LaunchTestHttpServer(self, document_root, extra_config_contents=None): |
| 75 """Launches an HTTP server to serve HTTP tests. |
| 76 |
| 77 Args: |
| 78 document_root: Document root of the HTTP server. |
| 79 extra_config_contents: Extra config contents for the HTTP server. |
| 80 """ |
| 81 self._http_server = lighttpd_server.LighttpdServer( |
| 82 document_root, extra_config_contents=extra_config_contents) |
| 83 if self._http_server.StartupHttpServer(): |
| 84 logging.info('http server started: http://localhost:%s', |
| 85 self._http_server.port) |
| 86 else: |
| 87 logging.critical('Failed to start http server') |
| 88 # Root access needed to make the forwarder executable work. |
| 89 self.adb.EnableAdbRoot() |
| 90 self.StartForwarderForHttpServer() |
| 91 |
| 92 def StartForwarderForHttpServer(self): |
| 93 """Starts a forwarder for the HTTP server. |
| 94 |
| 95 The forwarder forwards HTTP requests and responses between host and device. |
| 96 """ |
| 97 # Sometimes the forwarder device port may be already used. We have to kill |
| 98 # all forwarder processes to ensure that the forwarder can be started since |
| 99 # currently we can not associate the specified port to related pid. |
| 100 # TODO(yfriedman/wangxianzhu): This doesn't work as most of the time the |
| 101 # port is in use but the forwarder is already dead. Killing all forwarders |
| 102 # is overly destructive and breaks other tests which make use of forwarders. |
| 103 # if IsDevicePortUsed(self.adb, self._forwarder_device_port): |
| 104 # self.adb.KillAll('forwarder') |
| 105 self._forwarder = run_tests_helper.ForwardDevicePorts( |
| 106 self.adb, [(self._forwarder_device_port, self._http_server.port)]) |
| 107 |
| 108 def RestartHttpServerForwarderIfNecessary(self): |
| 109 """Restarts the forwarder if it's not open.""" |
| 110 # Checks to see if the http server port is being used. If not forwards the |
| 111 # request. |
| 112 # TODO(dtrainor): This is not always reliable because sometimes the port |
| 113 # will be left open even after the forwarder has been killed. |
| 114 if not run_tests_helper.IsDevicePortUsed(self.adb, |
| 115 self._forwarder_device_port): |
| 116 self.StartForwarderForHttpServer() |
| 117 |
| 118 def ShutdownHelperToolsForTestSuite(self): |
| 119 """Shuts down the server and the forwarder.""" |
| 120 # Forwarders should be killed before the actual servers they're forwarding |
| 121 # to as they are clients potentially with open connections and to allow for |
| 122 # proper hand-shake/shutdown. |
| 123 if self._forwarder or self._spawner_forwarder: |
| 124 # Kill all forwarders on the device and then kill the process on the host |
| 125 # (if it exists) |
| 126 self.adb.KillAll('forwarder') |
| 127 if self._forwarder: |
| 128 self._forwarder.kill() |
| 129 if self._spawner_forwarder: |
| 130 self._spawner_forwarder.kill() |
| 131 if self._http_server: |
| 132 self._http_server.ShutdownHttpServer() |
| 133 if self._spawning_server: |
| 134 self._spawning_server.Stop() |
| 135 self._flags.Restore() |
| 136 |
| 137 def LaunchChromeTestServerSpawner(self): |
| 138 """Launches test server spawner.""" |
| 139 self._spawning_server = SpawningServer(TEST_SERVER_SPAWNER_PORT, |
| 140 TEST_SERVER_PORT) |
| 141 self._spawning_server.Start() |
| 142 # TODO(yfriedman): Ideally we'll only try to start up a port forwarder if |
| 143 # there isn't one already running but for now we just get an error message |
| 144 # and the existing forwarder still works. |
| 145 self._spawner_forwarder = run_tests_helper.ForwardDevicePorts( |
| 146 self.adb, [(TEST_SERVER_SPAWNER_PORT, TEST_SERVER_SPAWNER_PORT), |
| 147 (TEST_SERVER_PORT, TEST_SERVER_PORT)]) |
OLD | NEW |