[pypy-svn] r59624 - in pypy/build/testrunner: . test test/examples/stall

pedronis at codespeak.net pedronis at codespeak.net
Sat Nov 1 15:56:24 CET 2008


Author: pedronis
Date: Sat Nov  1 15:56:22 2008
New Revision: 59624

Added:
   pypy/build/testrunner/test/examples/stall/
   pypy/build/testrunner/test/examples/stall/example.py   (contents, props changed)
Modified:
   pypy/build/testrunner/runner.py
   pypy/build/testrunner/test/test_runner.py
Log:
support for timeouts in the testrunner



Modified: pypy/build/testrunner/runner.py
==============================================================================
--- pypy/build/testrunner/runner.py	(original)
+++ pypy/build/testrunner/runner.py	Sat Nov  1 15:56:22 2008
@@ -24,6 +24,8 @@
         except OSError:
             pass
 
+TIMEDOUT = -999
+
 def run(args, cwd, out, timeout=None):
     f = out.open('w')
     try:
@@ -41,18 +43,18 @@
                 if (tnow-t0) > timeout:
                     if timedout:
                         _kill(p.pid, signal.SIGKILL)
-                        return -999
+                        return TIMEDOUT
                     else:
-                        timedout = -999
+                        timedout = TIMEDOUT
                         _kill(p.pid, signal.SIGTERM)
                 time.sleep(min(timeout, 10))
     finally:
         f.close()
 
-def dry_run(args, cwd, out):
+def dry_run(args, cwd, out, timeout=None):
     f = out.open('w')
     try:
-        f.write("run %s with cwd='%s'\n" % (args, cwd))
+        f.write("run %s with cwd='%s' timeout=%s\n" % (args, cwd, timeout))
     finally:
         f.close()
     return 0
@@ -64,7 +66,7 @@
     return 'signal %d' % (n,)
 
 def execute_test(cwd, test, out, logfname, interp, test_driver,
-                 do_dry_run=False):
+                 do_dry_run=False, timeout=None):
     args = interp+test_driver
     args += ['--resultlog=%s' % logfname, test]
 
@@ -74,7 +76,7 @@
     else:
         runfunc = run
     
-    exitcode = runfunc(args, cwd, out)
+    exitcode = runfunc(args, cwd, out, timeout=timeout)
     
     return exitcode
 
@@ -85,6 +87,8 @@
         if exitcode != 1:
             if exitcode > 0:
                 msg = "Exit code %d." % exitcode
+            elif exitcode == TIMEDOUT:
+                msg = "TIMEOUT"
             else:
                 msg = "Killed by %s." % getsignalname(-exitcode)
             extralog = "! %s\n %s\n" % (test, msg)
@@ -98,6 +102,7 @@
     test_driver = run_param.test_driver
     interp = run_param.interp
     dry_run = run_param.dry_run
+    timeout = run_param.timeout
     # xxx cfg thread start
     while 1:
         try:
@@ -112,7 +117,8 @@
         num += n
 
         exitcode = execute_test(root, test, one_output, logfname,
-                                interp, test_driver, do_dry_run=dry_run)
+                                interp, test_driver, do_dry_run=dry_run,
+                                timeout=timeout)
 
         # xxx cfg cleanup after testdir
         
@@ -191,6 +197,7 @@
     interp = [os.path.abspath(sys.executable)]
     test_driver = [os.path.abspath(os.path.join('py', 'bin', 'py.test'))]
     parallel_runs = 1
+    timeout = None
     
     def __init__(self, root):
         self.root = root
@@ -245,7 +252,10 @@
                       help="number of parallel test runs")
     parser.add_option("--dry-run", dest="dry_run", default=False,
                       action="store_true",
-                      help="dry run")    
+                      help="dry run")
+    parser.add_option("--timeout", dest="timeout", default=None,
+                      type="int",
+                      help="timeout in secs for test processes")
         
     opts, args = parser.parse_args(args)
 
@@ -279,6 +289,8 @@
 
     if opts.parallel_runs:
         run_param.parallel_runs = opts.parallel_runs
+    if opts.timeout:
+        run_param.timeout = opts.timeout
     run_param.dry_run = opts.dry_run
 
     if run_param.dry_run:

Added: pypy/build/testrunner/test/examples/stall/example.py
==============================================================================
--- (empty file)
+++ pypy/build/testrunner/test/examples/stall/example.py	Sat Nov  1 15:56:22 2008
@@ -0,0 +1,5 @@
+
+
+def test_hanging():
+    while True:
+        pass

Modified: pypy/build/testrunner/test/test_runner.py
==============================================================================
--- pypy/build/testrunner/test/test_runner.py	(original)
+++ pypy/build/testrunner/test/test_runner.py	Sat Nov  1 15:56:22 2008
@@ -56,8 +56,8 @@
         cls.called = []
         cls.exitcode = [0]
         
-        def fake_run(args, cwd, out):
-            cls.called = (args, cwd, out)
+        def fake_run(args, cwd, out, timeout):
+            cls.called = (args, cwd, out, timeout)
             return cls.exitcode[0]
         runner.run = fake_run
 
@@ -67,14 +67,15 @@
     def test_explicit(self):
         res = runner.execute_test('/wd', 'test_one', 'out', 'LOGFILE',
                                   interp=['INTERP', 'IARG'],
-                                  test_driver=['driver', 'darg'])
+                                  test_driver=['driver', 'darg'],
+                                  timeout='secs')
 
         expected = ['INTERP', 'IARG', 
                     'driver', 'darg',
                     '--resultlog=LOGFILE',
                     'test_one']
 
-        assert self.called == (expected, '/wd', 'out')        
+        assert self.called == (expected, '/wd', 'out', 'secs')        
         assert res == 0
     
 
@@ -126,27 +127,31 @@
         
         cls.udir = py.path.local.make_numbered_dir(prefix='usession-runner-',
                                               keep=3)
+        cls.manydir = cls.udir.join('many').ensure(dir=1)
 
-        def fill_test_dir(test_dir):       
+        def fill_test_dir(test_dir, fromdir='normal'):       
             for p in py.path.local(__file__).dirpath(
-                'examples', 'normal').listdir("*.py"):
+                'examples', fromdir).listdir("*.py"):
                 p.copy(test_dir.join('test_'+p.basename))
 
 
-        test_normal_dir0 = cls.udir.join('one', 'test_normal').ensure(dir=1)
-        cls.one_test_dir = cls.udir.join('one')
+        test_normal_dir0 = cls.manydir.join('one', 'test_normal').ensure(dir=1)
+        cls.one_test_dir = cls.manydir.join('one')
 
         fill_test_dir(test_normal_dir0)
         
 
-        test_normal_dir1 = cls.udir.join('two', 'test_normal1').ensure(dir=1)
-        test_normal_dir2 = cls.udir.join('two', 'pkg',
+        test_normal_dir1 = cls.manydir.join('two', 'test_normal1').ensure(dir=1)
+        test_normal_dir2 = cls.manydir.join('two', 'pkg',
                                          'test_normal2').ensure(dir=1)
-        cls.two_test_dir = cls.udir.join('two')
+        cls.two_test_dir = cls.manydir.join('two')
 
         fill_test_dir(test_normal_dir1)
-        fill_test_dir(test_normal_dir2)        
-        
+        fill_test_dir(test_normal_dir2)
+
+        cls.test_stall_dir = cls.udir.join('stall').ensure(dir=1)
+        test_stall_dir0 = cls.test_stall_dir.join('zero').ensure(dir=1)
+        fill_test_dir(test_stall_dir0, 'stall')
 
     def teardown_class(cls):
         runner.invoke_in_thread = cls.real_invoke_in_thread[0]
@@ -213,7 +218,7 @@
         log = cStringIO.StringIO()
         out = cStringIO.StringIO()
 
-        run_param = runner.RunParam(self.udir)
+        run_param = runner.RunParam(self.manydir)
         run_param.test_driver = test_driver
         run_param.parallel_runs = 3
 
@@ -239,6 +244,24 @@
         assert noutcomes == 3*107
         assert nfailures == 3*6
 
+    def test_timeout(self):
+        test_driver = [py.path.local(py.__file__).dirpath('bin', 'py.test')]
+
+        log = cStringIO.StringIO()
+        out = cStringIO.StringIO()
+
+        run_param = runner.RunParam(self.test_stall_dir)
+        run_param.test_driver = test_driver
+        run_param.parallel_runs = 3
+        run_param.timeout = 3
+
+        testdirs = []
+        run_param.collect_testdirs(testdirs)
+        res = runner.execute_tests(run_param, testdirs, log, out)
+        assert res
+
+        log_lines = log.getvalue().splitlines()
+        assert log_lines[1] == ' TIMEOUT'
 
 class TestRunnerNoThreads(RunnerTests):
     with_thread = False



More information about the Pypy-commit mailing list