Rev 4898: Start direct testing of the reconnection attempts. in http://bazaar.launchpad.net/~jameinel/bzr/2.1-client-reconnect-819604

John Arbash Meinel john at arbash-meinel.com
Thu Oct 6 14:01:53 UTC 2011


At http://bazaar.launchpad.net/~jameinel/bzr/2.1-client-reconnect-819604

------------------------------------------------------------
revno: 4898
revision-id: john at arbash-meinel.com-20111006140132-k8z0kyg59z2v8bb8
parent: john at arbash-meinel.com-20111006131537-s6eizb1pn6vkmynw
committer: John Arbash Meinel <john at arbash-meinel.com>
branch nick: 2.1-client-reconnect-819604
timestamp: Thu 2011-10-06 16:01:32 +0200
message:
  Start direct testing of the reconnection attempts.
  
  Turns out that SSHConnection.close() also needs to close the read/write handles.
  It is that way in bzr.dev, just didn't notice it.
  Pipes notice that they are closed right away, sockets don't.
-------------- next part --------------
=== modified file 'bzrlib/smart/client.py'
--- a/bzrlib/smart/client.py	2011-10-03 12:33:50 +0000
+++ b/bzrlib/smart/client.py	2011-10-06 14:01:32 +0000
@@ -69,6 +69,7 @@
             self._send_request_no_retry(encoder, method, args, body=body,
                 readv_body=readv_body, body_stream=body_stream)
         except errors.ConnectionReset, e:
+            raise
             # If we fail during the _send_request_no_retry phase, then we can
             # be confident that the server did not get our request, because we
             # haven't started waiting for the reply yet. So try the request

=== modified file 'bzrlib/smart/medium.py'
--- a/bzrlib/smart/medium.py	2011-10-06 13:15:37 +0000
+++ b/bzrlib/smart/medium.py	2011-10-06 14:01:32 +0000
@@ -963,13 +963,17 @@
         self._medium._flush()
 
 
+WSAECONNABORTED = 10053
+WSAECONNRESET = 10054
+
 def _read_bytes_from_socket(sock, desired_count, report_activity):
     # We ignore the desired_count because on sockets it's more efficient to
     # read large chunks (of _MAX_READ_SIZE bytes) at a time.
     try:
         bytes = osutils.until_no_eintr(sock, _MAX_READ_SIZE)
     except socket.error, e:
-        if len(e.args) and e.args[0] in (errno.ECONNRESET, 10054):
+        if len(e.args) and e.args[0] in (errno.ECONNRESET, WSAECONNABORTED,
+                                         WSAECONNRESET):
             # The connection was closed by the other side.  Callers expect an
             # empty string to signal end-of-stream.
             bytes = ''

=== modified file 'bzrlib/tests/test_smart_transport.py'
--- a/bzrlib/tests/test_smart_transport.py	2011-10-06 13:15:37 +0000
+++ b/bzrlib/tests/test_smart_transport.py	2011-10-06 14:01:32 +0000
@@ -97,6 +97,8 @@
 
     def close(self):
         self.vendor.calls.append(('close', ))
+        self.vendor.read_from.close()
+        self.vendor.write_to.close()
 
     def get_filelike_channels(self):
         return self.vendor.read_from, self.vendor.write_to
@@ -3332,6 +3334,36 @@
         # XXX: need a test that smart_client._headers is passed to the request
         # encoder.
 
+    def test__send_request_no_retry_pipes(self):
+        client_read, server_write = create_file_pipes()
+        server_read, client_write = create_file_pipes()
+        client_medium = medium.SmartSimplePipesClientMedium(client_read,
+            client_write, base='/')
+        smart_client = client._SmartClient(client_medium)
+        # Close the server side
+        server_read.close()
+        encoder, response_handler = smart_client._construct_protocol(3)
+        self.assertRaises(errors.ConnectionReset,
+            smart_client._send_request_no_retry, encoder, 'hello', ())
+
+    def test__send_request_read_response_sockets(self):
+        listen_sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
+        listen_sock.bind(('127.0.0.1', 0))
+        listen_sock.listen(1)
+        host, port = listen_sock.getsockname()
+        client_medium = medium.SmartTCPClientMedium(host, port, '/')
+        client_medium._ensure_connection()
+        smart_client = client._SmartClient(client_medium)
+        # Accept the connection, but don't actually talk to the client.
+        server_sock, _ = listen_sock.accept()
+        server_sock.close()
+        # Sockets buffer and don't really notice that the server has closed the
+        # connection until we try to read again.
+        handler = smart_client._send_request(3, 'hello', ())
+        self.assertRaises(errors.ConnectionReset,
+            handler.read_response_tuple, expect_body=False)
+
+
 
 class LengthPrefixedBodyDecoder(tests.TestCase):
 



More information about the bazaar-commits mailing list