pypy / _pytest /

""" recording warnings during test function execution. """

import py
import sys, os

def pytest_funcarg__recwarn(request):
    """Return a WarningsRecorder instance that provides these methods:

    * ``pop(category=None)``: return last warning matching the category.
    * ``clear()``: clear list of warnings
    See for information
    on warning categories.
    if sys.version_info >= (2,7):
        import warnings
        oldfilters = warnings.filters[:]
        def reset_filters():
            warnings.filters[:] = oldfilters
    wrec = WarningsRecorder()
    return wrec

def pytest_namespace():
    return {'deprecated_call': deprecated_call}

def deprecated_call(func, *args, **kwargs):
    """ assert that calling ``func(*args, **kwargs)``
    triggers a DeprecationWarning.
    warningmodule = py.std.warnings
    l = []
    oldwarn_explicit = getattr(warningmodule, 'warn_explicit')
    def warn_explicit(*args, **kwargs):
        oldwarn_explicit(*args, **kwargs)
    oldwarn = getattr(warningmodule, 'warn')
    def warn(*args, **kwargs):
        oldwarn(*args, **kwargs)

    warningmodule.warn_explicit = warn_explicit
    warningmodule.warn = warn
        ret = func(*args, **kwargs)
        warningmodule.warn_explicit = warn_explicit
        warningmodule.warn = warn
    if not l:
        #print warningmodule
        __tracebackhide__ = True
        raise AssertionError("%r did not produce DeprecationWarning" %(func,))
    return ret

class RecordedWarning:
    def __init__(self, message, category, filename, lineno, line):
        self.message = message
        self.category = category
        self.filename = filename
        self.lineno = lineno
        self.line = line

class WarningsRecorder:
    def __init__(self):
        warningmodule = py.std.warnings
        self.list = []
        def showwarning(message, category, filename, lineno, line=0):
                message, category, filename, lineno, line))
                self.old_showwarning(message, category,
                    filename, lineno, line=line)
            except TypeError:
                # < python2.6
                self.old_showwarning(message, category, filename, lineno)
        self.old_showwarning = warningmodule.showwarning
        warningmodule.showwarning = showwarning

    def pop(self, cls=Warning):
        """ pop the first recorded warning, raise exception if not exists."""
        for i, w in enumerate(self.list):
            if issubclass(w.category, cls):
                return self.list.pop(i)
        __tracebackhide__ = True
        assert 0, "%r not found in %r" %(cls, self.list)

    #def resetregistry(self):
    #    import warnings
    #    warnings.onceregistry.clear()
    #    warnings.__warningregistry__.clear()

    def clear(self):
        self.list[:] = []

    def finalize(self):
        py.std.warnings.showwarning = self.old_showwarning