我目前正致力于在Python 3.5.2中编写测试运行器并实现并行测试执行的多处理。这是我第一次真正使用任何类型的多处理并运行以使其正常工作。
如果您在run
方法下方看到,我可以看到我正在使用mp.Pool
和pool.map
通过self._run_spec
运行我的测试。这实际上非常有效。我面临的问题是self._run_spec
接收插件的副本而不是实际的实例。这使原始插件实例保持不变。
我知道这是一个基于流程如何工作的限制,但不确定如何更改我的实现来解决此问题。
import sys
from typing import cast, List, Dict, Any
from seleniumspec.spec import Spec, SpecContext
import traceback
import multiprocessing as mp
from functools import partial
from seleniumspec.plugin import *
class Runner(object):
specs = []
run_specs = []
plugins = cast(List[Plugin], [])
def add_specs(self, specs: List[Spec]):
[self.add_spec(spec) for spec in specs]
def add_spec(self, spec: Spec):
self.specs.append(spec)
for param in spec.params:
self.run_specs.append({'spec': spec, 'param': param})
def add_plugins(self, plugins: List[Plugin]):
[self.add_plugin(plugin) for plugin in plugins]
def add_plugin(self, plugin: Plugin):
self.plugins.append(plugin)
def run(self):
runner_start_event = RunnerStartPluginEvent(runner=self)
runner_stop_event = RunnerStopPluginEvent(runner=self)
# Hook: Runner Start
for plugin in self.plugins:
plugin.runner_start(runner_start_event)
# Run Tests in Parallel
p = mp.Pool(2)
p.map(partial(self._run_spec, plugins=self.plugins), self.run_specs)
# Hook: Runner Stop
for plugin in self.plugins:
plugin.runner_stop(runner_stop_event)
@staticmethod
def _run_spec(run_spec, plugins=None):
spec = run_spec['spec']
param = run_spec['param']
spec_context = SpecContext()
spec_context.param = param
spec_start_event = SpecStartPluginEvent(spec=spec, context=spec_context)
spec_stop_event = SpecStopPluginEvent(spec=spec, context=spec_context)
spec_fail_event = SpecFailPluginEvent(spec=spec, context=spec_context)
# Hook: Spec Start
for plugin in plugins:
plugin.spec_start(spec_start_event)
# Hook: Spec Setup
for spec_hook in spec.setup_hooks:
spec_hook(context=spec_context)
for i, step in enumerate(spec.steps):
step_start_event = StepStartPluginEvent(step=step)
step_stop_event = StepStopPluginEvent(step=step)
try:
# Hook: Step Start
for plugin in plugins:
plugin.step_start(step_start_event)
try:
step.fn(context=spec_context)
except AssertionError as e:
raise
# Hook: Step Stop
for plugin in plugins:
plugin.step_stop(step_stop_event)
except AssertionError as e:
error = traceback.format_exc()
spec_fail_event.error = error
# Hook: Spec Fail
for plugin in plugins:
plugin.spec_fail(spec_fail_event)
break
# Hook: Spec Teardown
for spec_hook in spec.teardown_hooks:
spec_hook(context=spec_context)
# Hook: Spec Stop
for plugin in plugins:
plugin.spec_stop(spec_stop_event)
return True