sha*_*pan 1 python monkeypatching class
我怎样才能替换ORM类 - 所以它不应该导致递归!
问题:
原始类具有超级调用,当它被替换时 - 它会导致自我继承并导致最大递归深度超过异常.
即类orm正在调用super(orm,self)....并且orm已被另一个继承原始orm的类所取代....
addons __init__.py osv run_app.py
./addons:
__init__.py test_app1.py test.py
./osv:
__init__.py orm.py
Run Code Online (Sandbox Code Playgroud)
class orm_template(object):
def __init__(self, *args, **kw):
super(orm_template, self).__init__()
def fields_get(self, fields):
return fields
def browse(self, id):
return id
class orm(orm_template):
def __init__(self, *args, **kw):
super(orm, self).__init__(*args, **kw)
def fields_get(self, fields, context = None):
return super(orm, self).fields_get(fields)
def read(self, fields):
return fields
Run Code Online (Sandbox Code Playgroud)
import test
def main(app):
print "Running..."
__import__(app, globals(), locals())
Run Code Online (Sandbox Code Playgroud)
from osv import orm
import osv
class orm(orm.orm):
def __init__(self, *args, **kw):
super(orm, self).__init__(*args, **kw)
def fields_get(self, *args, **kw):
print "my fields get................."
return super(orm, self).fields_get(*args, **kw)
osv.orm.orm = orm
print "replaced.........................."
Run Code Online (Sandbox Code Playgroud)
from osv.orm import orm
class hello(orm):
_name = 'hellos'
def __init__(self, *args, **kw):
super(hello, self).__init__(*args, **kw)
print hello('test').fields_get(['name'])
Run Code Online (Sandbox Code Playgroud)
import addons
addons.main('test_app1')
Run Code Online (Sandbox Code Playgroud)
>>>python run_app.py
replaced..........................
Running...
...
...
super(orm, self).__init__(*args, **kw)
RuntimeError: maximum recursion depth exceeded
Run Code Online (Sandbox Code Playgroud)
我见过类似的问题
您addons/test.py
需要获取并保留对原始orm.orm
文档的引用并使用该文档而不是替换版本.即:
from osv import orm
import osv
original_orm = osv.orm
class orm(original_orm):
def __init__(self, *args, **kw):
super(orm, self).__init__(*args, **kw)
def fields_get(self, *args, **kw):
print "my fields get................."
return super(orm, self).fields_get(*args, **kw)
osv.orm.orm = orm
print "replaced.........................."
Run Code Online (Sandbox Code Playgroud)
所以monkeypatched-in类继承自原始而不是自身,就像你在你的设置中那样.顺便说一句,如果你可以通过更好的osv
模块设计来避免猴子修补(例如,用一个setter函数设置什么是orm)你会更快乐;-).