2012-09-17 18 views
7

Pracuję z frameworkiem Python 2.x, a ostatnia wersja frameworka przeniosła niektóre powszechnie używane klasy bazowe z modułu A do modułu B (i klasy zostały przemianowane na bardziej przejrzyste nazwy w procesie). Moduł A definiuje kompatybilne wstecz identyfikatory dla nazw nowej klasy.Przestań używać klasy jako klasy nadrzędnej w Pythonie

B.py:

class BaseClass(object): 
    __metaclass__ = framework_meta # handles registration etc. 

A.py:

import B 
oldbase = B.BaseClass 

Teraz, aby pomóc ludziom migrować swój kod, chciałbym być w stanie wydać DeprecationWarning (używając ostrzeżenia. warn), gdy kod używający frameworka definiuje klasę wywodzącą się z A.oldbase informującą programistę o bezpośrednim odziedziczeniu po B.BaseClass.

Oczekuję, że można to osiągnąć za pomocą metaklasu. Próbowałem zadeklarować nową metaklasa powstałymi metaklasą ramowej

class deprecated_base_class(framework_meta): 
    def __new__(meta, name, bases, attrs): 
     warning = '%(class)s is deprecated' 
     for b in bases: 
      warning = getattr(b, '__deprecation_warning__', None) or warning 
     warn(warning % {'class': name}, DeprecationWarning, stacklevel=2) 
     return super(deprecated_base_class, meta).__new__(meta, name, bases, attrs) 

razem z:

A.py:

class oldbase(B.BaseClass): 
    __metaclass__ = deprecated_base_class 
    __deprecation_warning__ = 'class oldbase is deprecated. Use B.BaseClass instead' 

clientcode.py

class FooBar(oldbase): 
    pass 

Problem mam teraz, czy dostaję DeprecationWarning dla definicji oldbase. Jak mogę to naprawić?

Odpowiedz

2

chcesz wyświetlać ostrzeżenie, jeśli któryś z podstawami są nieaktualne:

class deprecated_base_class(framework_meta): 
    def __new__(meta, name, bases, attrs): 
     for b in bases: 
      if isinstance(b, deprecated_base_class): 
       warning = getattr(b, '__deprecation_warning__', '%(class)s is deprecated') 
       warn(warning % {'class': b.__name__}, DeprecationWarning, stacklevel=2) 
     return super(deprecated_base_class, meta).__new__(meta, name, bases, attrs)