[英]What does “<exception caught here>” line in twisted traceback mean?
例如:
Unhandled error in Deferred:
Unhandled Error
Traceback (most recent call last):
File "/opt/zenoss/lib/python/twisted/internet/defer.py", line 388, in errback
self._startRunCallbacks(fail)
File "/opt/zenoss/lib/python/twisted/internet/defer.py", line 455, in _startRunCallbacks
self._runCallbacks()
File "/opt/zenoss/lib/python/twisted/internet/defer.py", line 542, in _runCallbacks
current.result = callback(current.result, *args, **kw)
File "/opt/zenoss/lib/python/twisted/internet/defer.py", line 1076, in gotResult
_inlineCallbacks(r, g, deferred)
--- <exception caught here> ---
File "/opt/zenoss/lib/python/twisted/internet/defer.py", line 1018, in _inlineCallbacks
result = result.throwExceptionIntoGenerator(g)
File "/opt/zenoss/lib/python/twisted/python/failure.py", line 352, in throwExceptionIntoGenerator
return g.throw(self.type, self.value, self.tb)
exceptions.TypeError: exceptions must be classes, or instances, not str
如果它在那里被捕獲,為什么它仍在下面傳播兩幀? 以及如何從扔出的地方找出來?
這實際上不是追溯。 這就是twisted.python.failure.Failure
本身如何“打印”的方式(盡管要確保事情是模棱兩可的,但這樣做的方法是printTraceback
)。
--- <exception caught here> ---
位於中間的原因是,它正在分割與異常相關的調用堆棧的兩個不同部分有關的信息。
在標記上方,堆棧框架描述了決定創建Failure
實例的異常處理程序之上的內容(來自異常和回溯狀態)。
例如,考慮以下簡單程序:
from twisted.python.failure import Failure
def a():
b()
def b():
try:
c()
except:
return Failure()
def c():
1 / 0
f = a()
f.printTraceback()
如果運行此命令,則會在標記線上方看到以下內容:
File "someprog.py", line 16, in <module>
f = a()
File "someprog.py", line 5, in a
return b()
如果調用堆棧是一個堆棧,則可以看到這是在捕獲異常並創建Failure
的幀之前被壓入其中的兩個幀。
在標記線下方,您將得到:
File "someprog.py", line 9, in b
c()
File "someprog.py", line 14, in c
1 / 0
這是調用堆棧上的兩個幀,並因引發異常而彈出。
通常,只有標記下方的框架才是有趣的。 標記上方的框架以這種格式分開,因為它們通常是Twisted某些部分的詳細實現細節。 由於Twisted是協作式多任務處理系統,因此在實現中的堆棧框架通常不會告訴您很多有關異常上下文的信息(因為Python中的協作式多任務處理系統無法保持正在處理的邏輯操作與正在處理的Python框架對象)。
最重要的是,所涉及的代碼使用inlineCallbacks
使得了解回溯變得更加復雜。 這會在調用堆棧中起到進一步的作用,通常會破壞您得到的所有回溯。
File "/opt/zenoss/lib/python/twisted/internet/defer.py", line 1018, in _inlineCallbacks
result = result.throwExceptionIntoGenerator(g)
File "/opt/zenoss/lib/python/twisted/python/failure.py", line 352, in throwExceptionIntoGenerator
return g.throw(self.type, self.value, self.tb)
exceptions.TypeError: exceptions must be classes, or instances, not str
但是,我注意到的是,通過inlineCallbacks
的實現將異常引發到生成器中的嘗試本身就是在引發另一個異常。
此TypeError
表示self.type
是str
的實例。 由此我可能會猜測其中涉及的某些代碼濫用了Failure
或者此應用程序正在使用Twisted Spread(濫用了Failure
)。 我想在這里給出的簡短答案是不要將Twisted Spread和inlineCallbacks
結合inlineCallbacks
:它們不能很好地協同工作。
由於我在路徑中看到了Zenoss,因此我懷疑您並未編寫大部分代碼,因此答案可能對您沒有太大幫助...
如果可以,並且如果確實涉及Twisted Spread,則可以嘗試升級Twisted以查看此問題是否消失。 我認為這是幾年前已修復的http://tm.tl/4520的症狀(該修復程序首次包含在Twisted 11.1.0中)。
如果不涉及“扭曲傳播”,那么您可能需要跟蹤其他濫用Failure
代碼並進行糾正。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.