我正在實現一個庫模塊以用作couchdb更改通知的客戶端。我想讓庫處於「連續」模式,也就是說,連接必須永遠保持打開狀態,或者至少在連接已關閉的情況下它必須重新連接,以便couchdb有一個通道來通知發生在數據庫。然後,我將處理這些通知以生成特定事件(這尚未實施)。以扭曲形式實現重新連接http客戶端
我選擇的方法是使用ReconnectingClientFactory(它根據詳細的算法自動重新連接)作爲我的協議工廠的基礎。無論何時建立連接,都會調用buildProtocol方法。在這個方法中,我創建了協議實例,然後觸發一個callLater(立即)來表明連接已準備就緒。在cdConnected函數中,我發送請求並添加一個回調來處理接收到的數據(cbReceived)。
代碼中並重新連接如預期,但我有兩個不同的問題:
- 請求失敗(沒有數據通過TCP連接發送的),但我不知道爲什麼。
- 即使連接完全關閉,也會生成錯誤。
也許有人知道我做錯了什麼?
謝謝!
(編輯:在「連接被完全關閉。」正在打印由自己的錯誤,所以可以忽略不計)
下面是代碼:
from twisted.internet import defer
from twisted.internet.protocol import ReconnectingClientFactory
from twisted.web._newclient import HTTP11ClientProtocol
from twisted.web._newclient import Request
from twisted.web.client import _parse
class MyReconnectingClientFactory(ReconnectingClientFactory):
def __init__(self, reactor, cbConnected):
self.reactor = reactor
self.cbConnected = cbConnected
def startedConnecting(self, connector):
print 'Started to connect ...'
def buildProtocol(self, addr):
print 'Resetting reconnection delay'
self.resetDelay()
proto = HTTP11ClientProtocol()
self.reactor.callLater(0, self.cbConnected, proto)
return proto
def clientConnectionLost(self, connector, reason):
print 'Lost connection. Reason:', reason
ReconnectingClientFactory.clientConnectionLost(self, connector, reason)
def clientConnectionFailed(self, connector, reason):
print 'Connection failed. Reason:', reason
ReconnectingClientFactory.clientConnectionFailed(self, connector, reason)
def cbReceived(response):
print response
def printError(failure):
print "printError > %s" % (str(failure))
def cbConnected(proto):
print "Sending request ..."
req = Request(method, path, headers, bodyProducer)
d = proto.request(req)
d.addCallback(cbReceived).addErrback(printError)
return d
from twisted.internet import reactor
uri='http://localhost:5984/cn/_changes?feed=continuous'
method='GET'
headers=None
bodyProducer=None
scheme, host, port, path = _parse(uri)
factory = MyReconnectingClientFactory(reactor, cbConnected)
reactor.connectTCP(host, port, factory)
reactor.run()
這裏是輸出:
Started to connect ...
Resetting reconnection delay
Sending request ...
printError > [Failure instance: Traceback (failure with no frames): <class 'twisted.web._newclient.RequestGenerationFailed'>: [<twisted.python.failure.Failure <type 'exceptions.AttributeError'>>]
]
Lost connection. Reason: [Failure instance: Traceback (failure with no frames): <class 'twisted.internet.error.ConnectionDone'>: Connection was closed cleanly.
]
Started to connect ...
Resetting reconnection delay
Sending request ...
printError > [Failure instance: Traceback (failure with no frames): <class 'twisted.web._newclient.RequestGenerationFailed'>: [<twisted.python.failure.Failure <type 'exceptions.AttributeError'>>]
]
Lost connection. Reason: [Failure instance: Traceback (failure with no frames): <class 'twisted.internet.error.ConnectionDone'>: Connection was closed cleanly.
]
'_newclient'是Twisted中的私有模塊。請注意,如果您從中導入名稱,則任何新版本的Twisted中的代碼都可能會中斷而不會發出警告。如果您需要支持此私有模塊的功能,請在http://twistedmatrix.com/上提交錯誤。 – Glyph