def test_normal_serialization(self): from tests.sampletest.hellotest import HelloTest hello = HelloTest() data = serialization.dumps(hello) deserialized_case = serialization.loads(data) self.assertEqual(type(deserialized_case), HelloTest) for attr in ["owner", "timeout", "priority", "status", "tags", "test_doc"]: self.assertEqual(getattr(deserialized_case, attr), getattr(hello, attr))
def test_serialize_testsuite(self): from tests.sampletest.hellotest import HelloTest, TimeoutTest foo_test = datadrive.load_datadrive_tests(FooTest, 1)[0] testsuite = SeqTestSuite([HelloTest(), TimeoutTest(), foo_test]) data = serialization.dumps(testsuite) deserialized_testsuite = serialization.loads(data) self.assertEqual(len(deserialized_testsuite), len(testsuite)) for deserialized_test, test in zip(deserialized_testsuite, testsuite): self.assertEqual(type(deserialized_test), type(test)) for attr in ["owner", "timeout", "priority", "status", "tags", "test_doc"]: self.assertEqual(getattr(deserialized_test, attr), getattr(test, attr))
def test_datadrive_serialization(self): tests = datadrive.load_datadrive_tests(FooTest, 1) self.assertEqual(len(tests), 1) test = tests[0] deserialized_test = serialization.loads(serialization.dumps(test)) self.assertEqual(deserialized_test.owner, "bar") self.assertEqual(deserialized_test.timeout, 5) self.assertEqual(deserialized_test.priority, TestCase.EnumPriority.BVT) self.assertEqual(deserialized_test.status, TestCase.EnumStatus.Implement) self.assertEqual(deserialized_test.tags, set(["a", "b", "c"])) self.assertEqual(deserialized_test.test_doc, "demo")
def _worker_process(worker_id, ctrl_msg_queue, msg_queue, rsp_queue, result_factory_type, result_factory_data, resmgr): '''执行测试的子进程过程 :param worker_id: 工作者ID,全局唯一 :type worker_id: string :param ctrl_msg_queue: 控制进程通信的消息队列 :type ctrl_msg_queue: multiprocessing.Queue :param msg_queue: 本进程的消息队列 :type msg_queue: multiprocessing.Queue :param rsp_queue: 对本进程请求结果的答复消息队列 :type rsp_queue: multiprocessing.Queue :param result_factory_type: 测试结果工厂类 :type result_factory_type: type :param result_factory_data: 测试结果工厂序列化后数据 :type result_factory_data: object :param resmgr: 资源管理器 :type resmgr: TestResourceManager ''' try: result_factory = _EmptyClass() result_factory.__class__ = result_factory_type result_factory.loads(result_factory_data) result_manager = TestResultStubManager(rsp_queue) report = TestReportProxy(worker_id, ctrl_msg_queue, result_factory, result_manager) while True: msg = msg_queue.get() msg_type = msg[0] msg_data = msg[1:] if msg_type == EnumProcessMsgType.Worker_Quit: break elif msg_type == EnumProcessMsgType.Worker_RunTest: testcase = serialization.loads(msg_data[0]) t = threading.Thread(target=_run_test_thread, args=(worker_id, ctrl_msg_queue, testcase, report, resmgr)) t.daemon = True t.start() elif msg_type == EnumProcessMsgType.Result_GetAttr: objid, name = msg_data result_manager.get_result_attr(objid, name) elif msg_type == EnumProcessMsgType.Result_CallFunc: objid, func, args, kwargs = msg_data result_manager.call_result_func(objid, func, args, kwargs) except: ctrl_msg_queue.put((EnumProcessMsgType.Worker_Error, worker_id, traceback.format_exc()))
def _worker_process( worker_id, ctrl_msg_queue, msg_queue, rsp_queue, result_factory_type, result_factory_data): '''执行测试的子进程过程 :param worker_id: 工作者ID,全局唯一 :type worker_id: string :param ctrl_msg_queue: 控制进程通信的消息队列 :type ctrl_msg_queue: multiprocessing.Queue :param msg_queue: 本进程的消息队列 :type msg_queue: multiprocessing.Queue :param rsp_queue: 对本进程请求结果的答复消息队列 :type rsp_queue: multiprocessing.Queue :param result_factory_type: 测试结果工厂类 :type result_factory_type: type :param result_factory_data: 测试结果工厂序列化后数据 :type result_factory_data: object ''' try: result_factory = _EmptyClass() result_factory.__class__ = result_factory_type result_factory.loads(result_factory_data) result_manager = TestResultStubManager(rsp_queue) report = TestReportProxy(worker_id, ctrl_msg_queue, result_factory, result_manager) while True: msg = msg_queue.get() msg_type = msg[0] msg_data = msg[1:] if msg_type == EnumProcessMsgType.Worker_Quit: break elif msg_type == EnumProcessMsgType.Worker_RunTest: testcase = serialization.loads(msg_data[0]) t = threading.Thread(target=_run_test_thread, args=(worker_id, ctrl_msg_queue, testcase, report)) t.daemon = True t.start() elif msg_type == EnumProcessMsgType.Result_GetAttr: objid, name = msg_data result_manager.get_result_attr(objid, name) elif msg_type == EnumProcessMsgType.Result_CallFunc: objid, func, args, kwargs = msg_data result_manager.call_result_func(objid, func, args, kwargs) except: ctrl_msg_queue.put((EnumProcessMsgType.Worker_Error, worker_id, traceback.format_exc()))
def run_all_tests(self, tests): '''执行全部的测试用例 :param test: 测试用例对象列表 :type tests: list ''' if len(tests) < self.concurrency: self.concurrency = len(tests) random.shuffle(tests) tests_queue = collections.deque(tests) tests_retry_dict = {} msg_queue = multiprocessing.Queue() result_factory = self.report.get_testresult_factory() for i in range(self.concurrency): worker = TestWorker(i, msg_queue, result_factory, self._resmgr) worker.start() worker.run_testcase(tests_queue.popleft()) self._workers_dict[i] = worker idle_workers = [] error_counts = {} while True: msg = msg_queue.get() msg_type = msg[0] if msg_type == EnumProcessMsgType.Report_LogTestResult: worker = self._workers_dict[msg[1]] testcase = serialization.loads(msg[2]) objid, passed = msg[3], msg[4] self.report.log_test_result( testcase, TestResultProxy(worker, objid, passed, testcase)) elif msg_type == EnumProcessMsgType.Report_LogRecord: self.report.log_record(msg[1], msg[2], msg[3], msg[4]) elif msg_type == EnumProcessMsgType.Worker_Idle: worker = self._workers_dict[msg[1]] test = serialization.loads(msg[2]) passed = msg[3] if not passed: tests_retry_dict.setdefault(test.test_name, 0) if tests_retry_dict[test.test_name] < self._retries: tests_retry_dict[test.test_name] += 1 tests_queue.append(test) if len(tests_queue) > 0: worker.run_testcase(tests_queue.popleft()) else: idle_workers.append(worker) if len(idle_workers) == len(self._workers_dict): break elif msg_type == EnumProcessMsgType.Worker_Error: if msg[1] not in self._workers_dict: continue worker = self._workers_dict[msg[1]] err_msg = msg[2] self.report.error('RUNNER', 'runner process %s error occurred: %s' % (msg[1], err_msg), record=dict(err_msg=err_msg)) error_count = error_counts.get(msg[1], 0) if error_count >= 4: self.report.error( 'RUNNER', 'worker with id=%s failed to run for up 3 times' % msg[1]) worker.stop() del self._workers_dict[msg[1]] if len(idle_workers) == len(self._workers_dict): break else: error_counts[msg[1]] = error_count + 1 if worker not in idle_workers: tests_queue.append(worker.current_testcase()) worker.restart() worker.run_testcase(tests_queue.popleft())
def run_all_tests(self, tests): '''执行全部的测试用例 :param test: 测试用例对象列表 :type tests: list ''' if len(tests) < self._process_cnt: self._process_cnt = len(tests) random.shuffle(tests) tests_queue = collections.deque(tests) tests_retry_dict = {} msg_queue = multiprocessing.Queue() workers_dict = {} result_factory = self.report.get_testresult_factory() for i in range(self._process_cnt): worker = TestWorker(i, msg_queue, result_factory) worker.start() worker.run_testcase(tests_queue.popleft()) workers_dict[i] = worker idle_workers = [] while True: msg = msg_queue.get() msg_type = msg[0] if msg_type == EnumProcessMsgType.Report_LogTestResult: worker = workers_dict[msg[1]] testcase = serialization.loads(msg[2]) objid, passed = msg[3], msg[4] self.report.log_test_result( testcase, TestResultProxy(worker, objid, passed)) elif msg_type == EnumProcessMsgType.Report_LogRecord: self.report.log_record(msg[1], msg[2], msg[3], msg[4]) elif msg_type == EnumProcessMsgType.Worker_Idle: worker = workers_dict[msg[1]] test = serialization.loads(msg[2]) passed = msg[3] if not passed: tests_retry_dict.setdefault(test.test_name, 0) if tests_retry_dict[test.test_name] < self._retries: tests_retry_dict[test.test_name] += 1 tests_queue.append(test) if len(tests_queue) > 0: worker.run_testcase(tests_queue.popleft()) else: idle_workers.append(worker) if len(idle_workers) == len(workers_dict): break elif msg_type == EnumProcessMsgType.Worker_Error: worker = workers_dict[msg[1]] err_msg = msg[2] self.report.error('RUNNER', 'runner process %s error occur: %s' % (msg[1], err_msg), record=dict(err_msg=err_msg)) if worker not in idle_workers: tests_queue.append(worker.current_testcase()) worker.restart() worker.run_testcase(tests_queue.popleft()) for it in workers_dict.values(): it.stop()
def loads(self, buf): '''反序列化 ''' from testbase import serialization self._testcases = [serialization.loads(it) for it in buf]
def loads(self, buf ): '''反序列化 ''' from testbase import serialization self._testcases = [serialization.loads(it) for it in buf]
def run_all_tests(self, tests ): '''执行全部的测试用例 :param test: 测试用例对象列表 :type tests: list ''' if len(tests) < self._process_cnt: self._process_cnt = len(tests) random.shuffle(tests) tests_queue = collections.deque(tests) tests_retry_dict = {} msg_queue = multiprocessing.Queue() workers_dict = {} result_factory = self.report.get_testresult_factory() for i in range(self._process_cnt): worker = TestWorker(i, msg_queue, result_factory) worker.start() worker.run_testcase(tests_queue.popleft()) workers_dict[i] = worker idle_workers = [] while True: msg = msg_queue.get() msg_type = msg[0] if msg_type == EnumProcessMsgType.Report_LogTestResult: worker = workers_dict[msg[1]] testcase = serialization.loads(msg[2]) objid, passed = msg[3], msg[4] self.report.log_test_result(testcase, TestResultProxy(worker, objid, passed)) elif msg_type == EnumProcessMsgType.Report_LogRecord: self.report.log_record(msg[1], msg[2], msg[3], msg[4]) elif msg_type == EnumProcessMsgType.Worker_Idle: worker = workers_dict[msg[1]] test = serialization.loads(msg[2]) passed = msg[3] if not passed: tests_retry_dict.setdefault(test.test_name, 0) if tests_retry_dict[test.test_name] < self._retries: tests_retry_dict[test.test_name] += 1 tests_queue.append(test) if len(tests_queue) > 0: worker.run_testcase(tests_queue.popleft()) else: idle_workers.append(worker) if len(idle_workers) == len(workers_dict): break elif msg_type == EnumProcessMsgType.Worker_Error: worker = workers_dict[msg[1]] err_msg = msg[2] self.report.error('RUNNER', 'runner process %s error occur: %s' % (msg[1], err_msg), record=dict(err_msg=err_msg)) if worker not in idle_workers: tests_queue.append(worker.current_testcase()) worker.restart() worker.run_testcase(tests_queue.popleft()) for it in workers_dict.values(): it.stop()