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 """Provides stubs for os, sys and subprocess for testing | 4 """Provides stubs for os, sys and subprocess for testing |
5 | 5 |
6 This test allows one to test code that itself uses os, sys, and subprocess. | 6 This test allows one to test code that itself uses os, sys, and subprocess. |
7 """ | 7 """ |
8 import os as real_os | |
9 import subprocess as real_subprocess | |
10 | 8 |
11 class SysModuleStub(object): | 9 import os |
| 10 import shlex |
| 11 import sys as real_sys |
| 12 |
| 13 class Override(object): |
| 14 def __init__(self, base_module, module_list): |
| 15 stubs = {'adb_commands': AdbCommandsModuleStub, |
| 16 'os': OsModuleStub, |
| 17 'subprocess': SubprocessModuleStub, |
| 18 'sys': SysModuleStub, |
| 19 } |
| 20 self.adb_commands = None |
| 21 self.os = None |
| 22 self.subprocess = None |
| 23 self.sys = None |
| 24 |
| 25 self._base_module = base_module |
| 26 self._overrides = {} |
| 27 |
| 28 for module_name in module_list: |
| 29 self._overrides[module_name] = getattr(base_module, module_name) |
| 30 setattr(self, module_name, stubs[module_name]()) |
| 31 setattr(base_module, module_name, getattr(self, module_name)) |
| 32 |
| 33 if hasattr(self, 'os') and hasattr(self, 'sys'): |
| 34 self.os.path.sys = self.sys |
| 35 |
| 36 def __del__(self): |
| 37 assert not len(self._overrides) |
| 38 |
| 39 def Restore(self): |
| 40 for module_name, original_module in self._overrides.iteritems(): |
| 41 setattr(self._base_module, module_name, original_module) |
| 42 self._overrides = {} |
| 43 |
| 44 class AdbCommandsModuleStub(object): |
| 45 # adb not even found |
| 46 # android_browser_finder not returning |
| 47 class AdbCommandsStub(object): |
| 48 def __init__(self, module, device): |
| 49 self._module = module |
| 50 self._device = device |
| 51 self.is_root_enabled = True |
| 52 |
| 53 def RunShellCommand(self, args): |
| 54 if isinstance(args, basestring): |
| 55 args = shlex.split(args) |
| 56 handler = self._module.shell_command_handlers[args[0]] |
| 57 return handler(args) |
| 58 |
| 59 def IsRootEnabled(self): |
| 60 return self.is_root_enabled |
| 61 |
12 def __init__(self): | 62 def __init__(self): |
13 self.platform = '' | 63 self.attached_devices = [] |
| 64 self.shell_command_handlers = {} |
14 | 65 |
15 class OSPathModuleStub(object): | 66 def AdbCommandsStubConstructor(device=None): |
16 def __init__(self, os_module_stub): | 67 return AdbCommandsModuleStub.AdbCommandsStub(self, device) |
17 self._os_module_stub = os_module_stub | 68 self.AdbCommands = AdbCommandsStubConstructor |
18 | 69 |
19 def exists(self, path): | 70 @staticmethod |
20 return path in self._os_module_stub.files | 71 def IsAndroidSupported(): |
| 72 return True |
21 | 73 |
22 def join(self, *args): | 74 def GetAttachedDevices(self): |
23 if self._os_module_stub.sys.platform.startswith('win'): | 75 return self.attached_devices |
24 tmp = real_os.path.join(*args) | |
25 return tmp.replace('/', '\\') | |
26 else: | |
27 return real_os.path.join(*args) | |
28 | 76 |
29 def dirname(self, filename): # pylint: disable=R0201 | 77 @staticmethod |
30 return real_os.path.dirname(filename) | 78 def HasForwarder(_): |
| 79 return True |
31 | 80 |
32 class OSModuleStub(object): | 81 class OsModuleStub(object): |
33 def __init__(self, sys): | 82 class OsPathModuleStub(object): |
34 self.sys = sys | 83 def __init__(self, sys_module): |
35 self.path = OSPathModuleStub(self) | 84 self.sys = sys_module |
36 self.files = [] | 85 self.files = [] |
| 86 |
| 87 def exists(self, path): |
| 88 return path in self.files |
| 89 |
| 90 def join(self, *args): |
| 91 if self.sys.platform.startswith('win'): |
| 92 tmp = os.path.join(*args) |
| 93 return tmp.replace('/', '\\') |
| 94 else: |
| 95 return os.path.join(*args) |
| 96 |
| 97 def dirname(self, filename): # pylint: disable=R0201 |
| 98 return os.path.dirname(filename) |
| 99 |
| 100 def __init__(self, sys_module=real_sys): |
| 101 self.path = OsModuleStub.OsPathModuleStub(sys_module) |
37 self.display = ':0' | 102 self.display = ':0' |
38 self.local_app_data = None | 103 self.local_app_data = None |
| 104 self.devnull = os.devnull |
39 | 105 |
40 def getenv(self, name): | 106 def getenv(self, name): |
41 if name == 'DISPLAY': | 107 if name == 'DISPLAY': |
42 return self.display | 108 return self.display |
43 if name == 'LOCALAPPDATA': | 109 if name == 'LOCALAPPDATA': |
44 return self.local_app_data | 110 return self.local_app_data |
45 raise Exception('Unsupported getenv') | 111 raise Exception('Unsupported getenv') |
46 | 112 |
47 class PopenStub(object): | 113 class SubprocessModuleStub(object): |
48 def __init__(self, communicate_result): | 114 class PopenStub(object): |
49 self.communicate_result = communicate_result | 115 def __init__(self): |
| 116 self.communicate_result = ('', '') |
50 | 117 |
51 def communicate(self): | 118 def __call__(self, args, **kwargs): |
52 return self.communicate_result | 119 return self |
53 | 120 |
54 class SubprocessModuleStub(object): | 121 def communicate(self): |
| 122 return self.communicate_result |
| 123 |
55 def __init__(self): | 124 def __init__(self): |
56 self.Popen_hook = None | 125 self.Popen = SubprocessModuleStub.PopenStub() |
57 self.Popen_result = None | 126 self.PIPE = None |
58 self.PIPE = real_subprocess.PIPE | |
59 | 127 |
60 def Popen(self, *args, **kwargs): | 128 def call(self, *args, **kwargs): |
61 assert self.Popen_hook or self.Popen_result | 129 raise NotImplementedError() |
62 if self.Popen_hook: | 130 |
63 return self.Popen_hook(*args, **kwargs) | 131 class SysModuleStub(object): |
64 else: | 132 def __init__(self): |
65 return self.Popen_result | 133 self.platform = '' |
OLD | NEW |