Why can't Python decorators be chained across definitions? -
why arn't following 2 scripts equivalent?
(taken question: understanding python decorators)
def makebold(fn): def wrapped(): return "<b>" + fn() + "</b>" return wrapped def makeitalic(fn): def wrapped(): return "<i>" + fn() + "</i>" return wrapped @makebold @makeitalic def hello(): return "hello world" print hello() ## returns <b><i>hello world</i></b>
and decorated decorator:
def makebold(fn): def wrapped(): return "<b>" + fn() + "</b>" return wrapped @makebold def makeitalic(fn): def wrapped(): return "<i>" + fn() + "</i>" return wrapped @makeitalic def hello(): return "hello world" print hello() ## typeerror: wrapped() takes no arguments (1 given)
why want know? i've written retry
decorator catch mysqldb exceptions - if exception transient (e.g. timeout) re-call function after sleeping bit.
i've got modifies_db
decorator takes care of cache-related housekeeping. modifies_db
decorated retry
, assumed functions decorated modifies_db
retry implicitly. did go wrong?
the problem second example that
@makebold def makeitalic(fn): def wrapped(): return "<i>" + fn() + "</i>" return wrapped
is trying decorate makeitalic
, decorator, , not wrapped
, function returns.
you can think intend this:
def makeitalic(fn): @makebold def wrapped(): return "<i>" + fn() + "</i>" return wrapped
here makeitalic
uses makebold
decorate wrapped
.
Comments
Post a Comment