From 78495272aa010d32e811b67cf50b6ec16e8c705b Mon Sep 17 00:00:00 2001 From: hpk Date: Fri, 20 Mar 2009 03:13:31 +0100 Subject: [PATCH] [svn r63107] cleanup event handling of dsession --HG-- branch : trunk --- py/test/dsession/dsession.py | 64 +++++++++++++---------- py/test/dsession/testing/test_dsession.py | 23 ++++---- 2 files changed, 48 insertions(+), 39 deletions(-) diff --git a/py/test/dsession/dsession.py b/py/test/dsession/dsession.py index dec382ce2..7cab45662 100644 --- a/py/test/dsession/dsession.py +++ b/py/test/dsession/dsession.py @@ -13,7 +13,8 @@ from py.__.test import outcome import Queue class LoopState(object): - def __init__(self, colitems): + def __init__(self, dsession, colitems): + self.dsession = dsession self.colitems = colitems self.exitstatus = None # loopstate.dowork is False after reschedule events @@ -23,6 +24,30 @@ class LoopState(object): self.shuttingdown = False self.testsfailed = False + def pyevent_itemtestreport(self, event): + if event.colitem in self.dsession.item2host: + self.dsession.removeitem(event.colitem) + if event.failed: + self.testsfailed = True + + def pyevent_collectionreport(self, event): + if event.passed: + self.colitems.extend(event.result) + + def pyevent_testnodeready(self, event): + self.dsession.addhost(event.host) + + def pyevent_testnodedown(self, event): + pending = self.dsession.removehost(event.host) + if pending: + crashitem = pending[0] + self.dsession.handle_crashitem(crashitem, event.host) + self.colitems.extend(pending[1:]) + + def pyevent_rescheduleitems(self, event): + self.colitems.extend(event.items) + self.dowork = False # avoid busywait + class DSession(Session): """ Session drives the collection and running of tests @@ -36,7 +61,6 @@ class DSession(Session): self.queue = Queue.Queue() self.host2pending = {} self.item2host = {} - self._testsfailed = False if self.config.getvalue("executable") and \ not self.config.getvalue("numprocesses"): self.config.option.numprocesses = 1 @@ -83,8 +107,8 @@ class DSession(Session): if loopstate.shuttingdown: return self.loop_once_shutdown(loopstate) colitems = loopstate.colitems - if loopstate.dowork and loopstate.colitems: - self.triggertesting(colitems) + if loopstate.dowork and colitems: + self.triggertesting(loopstate.colitems) colitems[:] = [] # we use a timeout here so that control-C gets through while 1: @@ -94,31 +118,9 @@ class DSession(Session): except Queue.Empty: continue loopstate.dowork = True - + eventname, args, kwargs = eventcall self.bus.notify(eventname, *args, **kwargs) - if args: - ev, = args - else: - ev = None - if eventname == "itemtestreport": - self.removeitem(ev.colitem) - if ev.failed: - loopstate.testsfailed = True - elif eventname == "collectionreport": - if ev.passed: - colitems.extend(ev.result) - elif eventname == "testnodeready": - self.addhost(ev.host) - elif eventname == "testnodedown": - pending = self.removehost(ev.host) - if pending: - crashitem = pending.pop(0) - self.handle_crashitem(crashitem, ev.host) - colitems.extend(pending) - elif eventname == "rescheduleitems": - colitems.extend(ev.items) - loopstate.dowork = False # avoid busywait # termination conditions if ((loopstate.testsfailed and self.config.option.exitfirst) or @@ -143,9 +145,14 @@ class DSession(Session): else: loopstate.exitstatus = outcome.EXIT_OK + def _initloopstate(self, colitems): + loopstate = LoopState(self, colitems) + self.config.bus.register(loopstate) + return loopstate + def loop(self, colitems): try: - loopstate = LoopState(colitems) + loopstate = self._initloopstate(colitems) loopstate.dowork = False # first receive at least one HostUp events while 1: self.loop_once(loopstate) @@ -157,6 +164,7 @@ class DSession(Session): except: self.bus.notify("internalerror", event.InternalException()) exitstatus = outcome.EXIT_INTERNALERROR + self.config.bus.unregister(loopstate) if exitstatus == 0 and self._testsfailed: exitstatus = outcome.EXIT_TESTSFAILED return exitstatus diff --git a/py/test/dsession/testing/test_dsession.py b/py/test/dsession/testing/test_dsession.py index eb8e6b8d1..dc4fe647e 100644 --- a/py/test/dsession/testing/test_dsession.py +++ b/py/test/dsession/testing/test_dsession.py @@ -1,4 +1,4 @@ -from py.__.test.dsession.dsession import DSession, LoopState +from py.__.test.dsession.dsession import DSession from py.__.test.dsession.masterslave import maketestnodeready from py.__.execnet.gwmanage import GatewaySpec from py.__.test.runner import basic_collect_report @@ -120,7 +120,7 @@ class TestDSession: host1.node = MockNode() session.addhost(host1) ev = event.RescheduleItems([item]) - loopstate = LoopState([]) + loopstate = session._initloopstate([]) session.queueevent("rescheduleitems", ev) session.loop_once(loopstate) # check that RescheduleEvents are not immediately @@ -148,7 +148,7 @@ class TestDSession: ev = event.HostDown(host1, None) session.queueevent("testnodedown", ev) - loopstate = LoopState([item]) + loopstate = session._initloopstate([item]) loopstate.dowork = False session.loop_once(loopstate) dumpqueue(session.queue) @@ -178,7 +178,8 @@ class TestDSession: ev = event.HostDown(host, None) session.queueevent("testnodedown", ev) evrec = EventRecorder(session.bus) - loopstate = LoopState([]) + print session.item2host + loopstate = session._initloopstate([]) session.loop_once(loopstate) assert loopstate.colitems == [item2] # do not reschedule crash item @@ -195,7 +196,7 @@ class TestDSession: host1 = GatewaySpec("localhost") testnodeready = maketestnodeready(host1) session.queueevent("testnodeready", testnodeready) - loopstate = LoopState([item]) + loopstate = session._initloopstate([item]) loopstate.dowork = False assert len(session.host2pending) == 0 session.loop_once(loopstate) @@ -207,7 +208,7 @@ class TestDSession: evrec = EventRecorder(session.bus) session.queueevent("NOPevent", 42) - session.loop_once(LoopState([])) + session.loop_once(session._initloopstate([])) assert evrec.getfirstnamed('NOPevent') def runthrough(self, item): @@ -215,7 +216,7 @@ class TestDSession: host1 = GatewaySpec("localhost") host1.node = MockNode() session.addhost(host1) - loopstate = LoopState([item]) + loopstate = session._initloopstate([item]) session.queueevent("NOP") session.loop_once(loopstate) @@ -263,7 +264,7 @@ class TestDSession: session.queueevent("itemtestreport", ev1) # a failing one session.queueevent("itemtestreport", ev2) # now call the loop - loopstate = LoopState(items) + loopstate = session._initloopstate(items) session.loop_once(loopstate) assert loopstate.testsfailed assert loopstate.shuttingdown @@ -273,7 +274,7 @@ class TestDSession: session = DSession(item.config) host = GatewaySpec("localhost") session.addhost(host) - loopstate = LoopState([]) + loopstate = session._initloopstate([]) loopstate.shuttingdown = True evrec = EventRecorder(session.bus) session.queueevent("itemtestreport", run(item)) @@ -322,7 +323,7 @@ class TestDSession: session.addhost(host) session.senditems([item]) session.queueevent("itemtestreport", run(item)) - loopstate = LoopState([]) + loopstate = session._initloopstate([]) session.loop_once(loopstate) assert host.node._shutdown is True assert loopstate.exitstatus is None, "loop did not wait for testnodedown" @@ -353,7 +354,7 @@ class TestDSession: # but we have a collection pending session.queueevent("collectionreport", colreport) - loopstate = LoopState([]) + loopstate = session._initloopstate([]) session.loop_once(loopstate) assert loopstate.exitstatus is None, "loop did not care for collection report" assert not loopstate.colitems