mirror of https://github.com/scrapy/scrapy.git
support showing subclassing deprecation warning only once
This commit is contained in:
parent
02c80ca75b
commit
23c37dee36
|
|
@ -63,6 +63,49 @@ class WarnWhenSubclassedTest(unittest.TestCase):
|
|||
)
|
||||
self.assertEqual(msg.lineno, lineno)
|
||||
|
||||
def test_warning_shown_everytime(self):
|
||||
Deprecated = create_deprecated_class('Deprecated', NewName,
|
||||
warn_category=MyWarning)
|
||||
with warnings.catch_warnings(record=True) as w:
|
||||
class U1(Deprecated):
|
||||
pass
|
||||
|
||||
class U2(Deprecated):
|
||||
pass
|
||||
|
||||
self.assertEqual(len(w), 2)
|
||||
assert issubclass(w[0].category, MyWarning)
|
||||
assert issubclass(w[1].category, MyWarning)
|
||||
|
||||
with warnings.catch_warnings(record=True) as w:
|
||||
_i1 = Deprecated()
|
||||
_i2 = Deprecated()
|
||||
|
||||
self.assertEqual(len(w), 2)
|
||||
assert issubclass(w[0].category, MyWarning)
|
||||
assert issubclass(w[1].category, MyWarning)
|
||||
|
||||
def test_warning_shown_once(self):
|
||||
Deprecated = create_deprecated_class('Deprecated', NewName,
|
||||
warn_once=True,
|
||||
warn_category=MyWarning)
|
||||
with warnings.catch_warnings(record=True) as w:
|
||||
class U1(Deprecated):
|
||||
pass
|
||||
|
||||
class U2(Deprecated):
|
||||
pass
|
||||
|
||||
self.assertEqual(len(w), 1)
|
||||
assert issubclass(w[0].category, MyWarning)
|
||||
|
||||
with warnings.catch_warnings(record=True) as w:
|
||||
_i1 = Deprecated()
|
||||
_i2 = Deprecated()
|
||||
|
||||
self.assertEqual(len(w), 1)
|
||||
assert issubclass(w[0].category, MyWarning)
|
||||
|
||||
def test_warning_auto_message(self):
|
||||
with warnings.catch_warnings(record=True) as w:
|
||||
Deprecated = create_deprecated_class('Deprecated', NewName)
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ def attribute(obj, oldattr, newattr, version='0.12'):
|
|||
|
||||
def create_deprecated_class(name, new_class, clsdict=None,
|
||||
warn_category=ScrapyDeprecationWarning,
|
||||
warn_once=False,
|
||||
subclass_warn_message="{cls} inherits from "\
|
||||
"deprecated class {old}, please inherit "\
|
||||
"from {new}.",
|
||||
|
|
@ -47,6 +48,8 @@ def create_deprecated_class(name, new_class, clsdict=None,
|
|||
class DeprecatedClass(type):
|
||||
|
||||
deprecated_class = None
|
||||
warned_on_subclass = False
|
||||
warned_on_instance = False
|
||||
|
||||
def __new__(metacls, name, bases, clsdict_):
|
||||
cls = super(DeprecatedClass, metacls).__new__(metacls, name, bases, clsdict_)
|
||||
|
|
@ -55,8 +58,10 @@ def create_deprecated_class(name, new_class, clsdict=None,
|
|||
return cls
|
||||
|
||||
def __init__(cls, name, bases, clsdict_):
|
||||
old = cls.__class__.deprecated_class
|
||||
if cls is not old:
|
||||
meta = cls.__class__
|
||||
old = meta.deprecated_class
|
||||
if (cls is not old) and not (warn_once and meta.warned_on_subclass):
|
||||
meta.warned_on_subclass = True
|
||||
msg = subclass_warn_message.format(cls=_clspath(cls),
|
||||
old=_clspath(old),
|
||||
new=_clspath(new_class))
|
||||
|
|
@ -79,7 +84,10 @@ def create_deprecated_class(name, new_class, clsdict=None,
|
|||
return any(c in candidates for c in mro)
|
||||
|
||||
def __call__(cls, *args, **kwargs):
|
||||
if cls is cls.__class__.deprecated_class:
|
||||
meta = cls.__class__
|
||||
old = meta.deprecated_class
|
||||
if (cls is old) and not (warn_once and meta.warned_on_instance):
|
||||
meta.warned_on_instance = True
|
||||
msg = instance_warn_message.format(cls=_clspath(cls),
|
||||
new=_clspath(new_class))
|
||||
warnings.warn(msg, warn_category, stacklevel=2)
|
||||
|
|
|
|||
Loading…
Reference in New Issue