~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/smart/medium.py

  • Committer: Patch Queue Manager
  • Date: 2014-04-09 13:36:25 UTC
  • mfrom: (6592.1.2 1303879-py27-issues)
  • Revision ID: pqm@pqm.ubuntu.com-20140409133625-s24spv3kha2w2860
(vila) Fix python-2.7.6 test failures. (Vincent Ladeuil)

Show diffs side-by-side

added added

removed removed

Lines of Context:
24
24
bzrlib/transport/smart/__init__.py.
25
25
"""
26
26
 
 
27
from __future__ import absolute_import
 
28
 
27
29
import errno
28
30
import os
29
31
import sys
30
32
import time
31
 
import urllib
32
33
 
33
34
import bzrlib
34
35
from bzrlib.lazy_import import lazy_import
42
43
    debug,
43
44
    errors,
44
45
    trace,
 
46
    transport,
45
47
    ui,
46
48
    urlutils,
47
49
    )
840
842
        """
841
843
        medium_base = urlutils.join(self.base, '/')
842
844
        rel_url = urlutils.relative_url(medium_base, transport.base)
843
 
        return urllib.unquote(rel_url)
 
845
        return urlutils.unquote(rel_url)
844
846
 
845
847
 
846
848
class SmartClientStreamMedium(SmartClientMedium):
881
883
        """
882
884
        return SmartClientStreamMediumRequest(self)
883
885
 
 
886
    def reset(self):
 
887
        """We have been disconnected, reset current state.
 
888
 
 
889
        This resets things like _current_request and connected state.
 
890
        """
 
891
        self.disconnect()
 
892
        self._current_request = None
 
893
 
884
894
 
885
895
class SmartSimplePipesClientMedium(SmartClientStreamMedium):
886
896
    """A client medium using simple pipes.
895
905
 
896
906
    def _accept_bytes(self, bytes):
897
907
        """See SmartClientStreamMedium.accept_bytes."""
898
 
        self._writeable_pipe.write(bytes)
 
908
        try:
 
909
            self._writeable_pipe.write(bytes)
 
910
        except IOError, e:
 
911
            if e.errno in (errno.EINVAL, errno.EPIPE):
 
912
                raise errors.ConnectionReset(
 
913
                    "Error trying to write to subprocess", e)
 
914
            raise
899
915
        self._report_activity(len(bytes), 'write')
900
916
 
901
917
    def _flush(self):
902
918
        """See SmartClientStreamMedium._flush()."""
 
919
        # Note: If flush were to fail, we'd like to raise ConnectionReset, etc.
 
920
        #       However, testing shows that even when the child process is
 
921
        #       gone, this doesn't error.
903
922
        self._writeable_pipe.flush()
904
923
 
905
924
    def _read_bytes(self, count):
924
943
 
925
944
class SmartSSHClientMedium(SmartClientStreamMedium):
926
945
    """A client medium using SSH.
927
 
    
928
 
    It delegates IO to a SmartClientSocketMedium or
 
946
 
 
947
    It delegates IO to a SmartSimplePipesClientMedium or
929
948
    SmartClientAlreadyConnectedSocketMedium (depending on platform).
930
949
    """
931
950
 
953
972
            maybe_port = ''
954
973
        else:
955
974
            maybe_port = ':%s' % self._ssh_params.port
956
 
        return "%s(%s://%s@%s%s/)" % (
 
975
        if self._ssh_params.username is None:
 
976
            maybe_user = ''
 
977
        else:
 
978
            maybe_user = '%s@' % self._ssh_params.username
 
979
        return "%s(%s://%s%s%s/)" % (
957
980
            self.__class__.__name__,
958
981
            self._scheme,
959
 
            self._ssh_params.username,
 
982
            maybe_user,
960
983
            self._ssh_params.host,
961
984
            maybe_port)
962
985
 
999
1022
            raise AssertionError(
1000
1023
                "Unexpected io_kind %r from %r"
1001
1024
                % (io_kind, self._ssh_connection))
 
1025
        for hook in transport.Transport.hooks["post_connect"]:
 
1026
            hook(self)
1002
1027
 
1003
1028
    def _flush(self):
1004
1029
        """See SmartClientStreamMedium._flush()."""
1018
1043
 
1019
1044
class SmartClientSocketMedium(SmartClientStreamMedium):
1020
1045
    """A client medium using a socket.
1021
 
    
 
1046
 
1022
1047
    This class isn't usable directly.  Use one of its subclasses instead.
1023
1048
    """
1024
1049
 
1107
1132
            raise errors.ConnectionError("failed to connect to %s:%d: %s" %
1108
1133
                    (self._host, port, err_msg))
1109
1134
        self._connected = True
 
1135
        for hook in transport.Transport.hooks["post_connect"]:
 
1136
            hook(self)
1110
1137
 
1111
1138
 
1112
1139
class SmartClientAlreadyConnectedSocketMedium(SmartClientSocketMedium):
1164
1191
        This invokes self._medium._flush to ensure all bytes are transmitted.
1165
1192
        """
1166
1193
        self._medium._flush()
1167
 
 
1168