扭曲测试 - 成功和错误回调都会在延迟时触发

Twisted test - both success and error callback fire on deferred

正在为扭曲的应用程序编写单元测试。一旦延迟被新连接(协议实例)解决,尝试执行一些断言,但是看到成功和错误回调都被触发(根据控制台中打印的 SUCCESSFAIL 来判断) .

def test_send_to_new_connection(self):
    # Given
    peerAddr = ('10.22.22.190', 5060)

    # If
    self.tcp_transport.send_to('test', peerAddr)

    # Then
    assert peerAddr in self.tcp_transport._connections
    assert True == isinstance(self.tcp_transport._connections[peerAddr], Deferred)

    connection = _string_transport_connection(self.hostAddr, peerAddr, None, self.tcp_transport.connectionMade)

    def assert_cache_updated_on_connection(connection):
        print('--------- SUCCESS ----------')
        peer = connection.transport.getPeer()
        peerAddr = (peer.host, peer.port)

        assert peerAddr in self.tcp_transport._connections
        assert True == isinstance(self.tcp_transport._connections[peerAddr], Protocol)

    def assert_fail(fail):
        print('--------- FAIL ----------')

    self.tcp_transport._connections[peerAddr].addCallback(assert_cache_updated_on_connection)
    self.tcp_transport._connections[peerAddr].addErrback(assert_fail)
    # Forcing deferred to fire with mock connection
    self.tcp_transport._connections[peerAddr].callback(connection)

我认为 Callbacks 和 Errbacks 的执行是相互排斥的。 IE。只有一个或其他人 运行 取决于延迟解决。为什么 assert_fail() 也被调用?

参见 Deferred Reference 中的 "railroad" 图:

注意从回调端到 errback 端的对角线箭头,反之亦然。在任何 单一 位置(其中 "position" 是一对并排的方框,一个绿色和一个红色,位置随着图表的向下移动而增加)在callback/errback 链只会调用 callback 或 errback 之一。但是,由于链中有多个位置,您可以在单个 Deferred 上调用多个回调和错误返回。

对于您的代码:

  ....addCallback(assert_cache_updated_on_connection)
  ....addErrback(assert_fail)

有两个职位。第一个有一个回调,第二个有一个 errback。如果回调信号失败,执行切换到下一个位置的 errback 端 - 正是你有 assert_fail.

的位置