Ticket #2491: registry.patch

File registry.patch, 8.9 KB (added by Michael, 6 years ago)
  • twisted/python/deprecate.py

    diff --git twisted/python/deprecate.py twisted/python/deprecate.py
    index 02c107c..59716ca 100644
    def warnAboutFunction(offender, warningString): 
    470470    filename = inspect.getabsfile(offenderModule)
    471471    lineStarts = list(findlinestarts(offender.func_code))
    472472    lastLineNo = lineStarts[-1][1]
     473    globals = offender.func_globals
    473474
    474475    kwargs = dict(
    475476        category=DeprecationWarning,
    476477        filename=filename,
    477478        lineno=lastLineNo,
    478         module='', # offenderModule.__name__,
    479         registry={}, # getattr(offenderModule, "__warningregistry__", {}),
    480         module_globals={}, # offenderModule.__dict__
     479        module=offenderModule.__name__,
     480        registry=globals.setdefault("__warningregistry__", {}),
     481        module_globals=offenderModule.__dict__,  # used by linecache to load source code from zip files
    481482        )
    482483
    483     if sys.version < (2, 5):
     484    if sys.version_info[:2] < (2, 5):
    484485        kwargs.pop('module_globals')
     486
    485487    warn_explicit(warningString, **kwargs)
  • twisted/python/test/test_deprecate.py

    diff --git twisted/python/test/test_deprecate.py twisted/python/test/test_deprecate.py
    index cc4b157..1955435 100644
    Tests for Twisted's deprecation framework, L{twisted.python.deprecate}. 
    66"""
    77
    88import sys, types
     9import warnings
     10import zipfile
     11import linecache
    912
    1013from twisted.trial.unittest import TestCase
    1114
    deprecatedModuleAttribute( 
    513516        # make sure it's the right module.
    514517        self.assertEquals(module.__file__.rsplit(".", 1)[0],
    515518                          package.child('module.py').path.rsplit(".", 1)[0])
    516         warnings = self.flushWarnings([self.test_deprecatedModule])
    517         self.assertEquals(len(warnings), 1)
     519        warningsShown = self.flushWarnings([self.test_deprecatedModule])
     520        self.assertEquals(len(warningsShown), 1)
    518521
    519522
    520523
    def callTestFunction(): 
    558561        def aFunc():
    559562            pass
    560563        deprecate.warnAboutFunction(aFunc, 'A Warning Message')
    561         warnings = self.flushWarnings()
     564        warningsShown = self.flushWarnings()
    562565        filename = __file__
    563566        if filename.lower().endswith('.pyc'):
    564567            filename = filename[:-1]
    565         self.assertEquals(warnings[0]["filename"], filename)
    566         self.assertEquals(warnings[0]["message"], "A Warning Message")
     568        self.assertEquals(warningsShown[0]["filename"], filename)
     569        self.assertEquals(warningsShown[0]["message"], "A Warning Message")
    567570
    568571
    569572    def test_warningLineNumber(self):
    def callTestFunction(): 
    573576        """
    574577        from twisted_private_helper import module
    575578        module.callTestFunction()
    576         warnings = self.flushWarnings()
     579        warningsShown = self.flushWarnings()
    577580        self.assertEquals(
    578             warnings[0]["filename"],
     581            warningsShown[0]["filename"],
    579582            self.package.dirname() + '/twisted_private_helper/module.py')
    580583        # Line number 9 is the last line in the testFunction in the helper
    581584        # module.
    582         self.assertEquals(warnings[0]["lineno"], 9)
    583         self.assertEquals(warnings[0]["message"], "A Warning String")
    584         self.assertEquals(len(warnings), 1)
     585        self.assertEquals(warningsShown[0]["lineno"], 9)
     586        self.assertEquals(warningsShown[0]["message"], "A Warning String")
     587        self.assertEquals(len(warningsShown), 1)
    585588
    586589
    587590    def test_renamedFile(self):
    def callTestFunction(): 
    606609        self.addCleanup(sys.modules.pop, module.__name__)
    607610
    608611        module.callTestFunction()
    609         warnings = self.flushWarnings()
     612        warningsShown = self.flushWarnings()
    610613        self.assertEquals(
    611             warnings[0]["filename"],
     614            warningsShown[0]["filename"],
    612615            self.package.dirname() + '/twisted_renamed_helper/module.py')
    613         self.assertEquals(warnings[0]["lineno"], 9)
    614         self.assertEquals(warnings[0]["message"], "A Warning String")
    615         self.assertEquals(len(warnings), 1)
     616        self.assertEquals(warningsShown[0]["lineno"], 9)
     617        self.assertEquals(warningsShown[0]["message"], "A Warning String")
     618        self.assertEquals(len(warningsShown), 1)
     619
     620
     621    def test_filtered_warning(self):
     622        """
     623        L{deprecate.warnAboutFunction} emits a warning that will be
     624        filtered if L{warnings.filterwarning} is called with the
     625        module name of the deprecated function.
     626        """
     627       
     628        # must remove the warnings.simplefilter("always") that
     629        # unittest._collectWarnings adds otherwise we can't filter
     630        # a warning
     631        always_simplefilter = warnings.filters.pop(0) 
     632        self.assertEquals(always_simplefilter, ("always", None, Warning, None, 0))
     633        self.addCleanup(warnings.filters.insert, 0, always_simplefilter)
     634
     635        warnings.filterwarnings(action="ignore", module="twisted_private_helper", append=True)
     636        self.addCleanup(warnings.filters.pop)
     637
     638        from twisted_private_helper import module
     639        module.callTestFunction()
     640       
     641        warningsShown = self.flushWarnings()
     642        self.assertEquals(len(warningsShown), 0)
     643
     644
     645    def test_filtered_once_warning(self):
     646        """
     647        L{deprecate.warnAboutFunction} emits a warning that will be
     648        filtered once if L{warnings.filterwarning} is called with the
     649        module name of the deprecated function and an action of once.
     650        """
     651       
     652        # must remove the warnings.simplefilter("always") that
     653        # unittest._collectWarnings adds otherwise we can't filter
     654        # a warning
     655        always_simplefilter = warnings.filters.pop(0) 
     656        self.assertEquals(always_simplefilter, ("always", None, Warning, None, 0))
     657        self.addCleanup(warnings.filters.insert, 0, always_simplefilter)
     658
     659        warnings.filterwarnings(action="module", module="twisted_private_helper", append=True)
     660        self.addCleanup(warnings.filters.pop)
     661
     662        from twisted_private_helper import module
     663        module.callTestFunction()
     664        module.callTestFunction()
     665       
     666        warningsShown = self.flushWarnings()
     667        self.assertEquals(len(warningsShown), 1)
     668        message = warningsShown[0]['message']
     669        category = warningsShown[0]['category']
     670        filename = warningsShown[0]['filename']
     671        lineno = warningsShown[0]['lineno']
     672        msg = warnings.formatwarning(message, category, filename, lineno)
     673        print msg
     674
     675class WarnAboutFunctionTestsInZipFiles(TestCase):
     676    """
     677    Tests for L{twisted.python.deprecate.warnAboutFunction} which
     678    allows the callers of a function to issue a C{DeprecationWarning}
     679    about that function located in zip file.
     680    """
     681    def setUp(self):
     682        """
     683        Create a file that will have known line numbers when emitting warnings.
     684        """
     685        self.package = FilePath(self.mktemp())
     686        self.package.makedirs()
     687        self.package.child('zipped_twisted_private_helper.py').setContent('''
     688"A module string"
     689
     690from twisted.python import deprecate
     691
     692def testFunction():
     693    "A doc string"
     694    a = 1 + 2
     695    return a
     696
     697def callTestFunction():
     698    b = testFunction()
     699    if b == 3:
     700        deprecate.warnAboutFunction(testFunction, "A Warning String")
     701''')
     702        temp = FilePath(self.mktemp())
     703        temp.makedirs()
     704        self.zipname = temp.child('zipped_twisted_private_helper.zip').path
     705        z = zipfile.ZipFile(self.zipname, 'w')
     706        z.write(self.package.child('zipped_twisted_private_helper.py').path,
     707                'zipped_twisted_private_helper.py')
     708        z.close()
     709        sys.path.insert(0, self.zipname)
     710        self.addCleanup(sys.path.remove, self.zipname)
     711
     712    def test_zipped_modules(self):
     713        """
     714        L{deprecate.warnAboutFunction} emits a warning that will can
     715        contain the line when the function is loaded from a module in
     716        a zipfile.
     717        """
     718        import zipped_twisted_private_helper
     719        # def dump(*args, **kwargs):
     720        #     print '%r' % args
     721        #     print '%r' % kwargs
     722        # orig = warnings.warn_explicit
     723        # warnings.warn_explicit = dump
     724        zipped_twisted_private_helper.callTestFunction()
     725        warningsShown = self.flushWarnings()
     726        self.assertEquals(
     727            warningsShown[0]["filename"],
     728            self.zipname + '/zipped_twisted_private_helper.py')
     729        # Line number 9 is the last line in the testFunction in the helper
     730        # module.
     731        self.assertEquals(warningsShown[0]["lineno"], 9)
     732        self.assertEquals(warningsShown[0]["message"], "A Warning String")
     733        self.assertEquals(len(warningsShown), 1)
     734        self.assertEquals(linecache.cache.keys(),
     735                          self.zipname+'/zipped_twisted_private_helper.py')
     736        line = linecache.cache[self.zipname + '/zipped_twisted_private_helper.py']
     737        self.assertEquals(line, '    return a\n')