~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/transport/ftp/__init__.py

  • Committer: Vincent Ladeuil
  • Date: 2009-10-06 15:58:12 UTC
  • mfrom: (4725.3.3 443041-ftp-append-bytes)
  • mto: This revision was merged to the branch mainline in revision 4729.
  • Revision ID: v.ladeuil+lp@free.fr-20091006155812-mie06vdxp373lqxd
Fix gssapi ftp client mode handling

Show diffs side-by-side

added added

removed removed

Lines of Context:
25
25
"""
26
26
 
27
27
from cStringIO import StringIO
28
 
import errno
29
28
import ftplib
30
29
import getpass
31
30
import os
32
 
import os.path
33
 
import urlparse
34
31
import random
35
32
import socket
36
33
import stat
37
34
import time
38
 
from warnings import warn
39
35
 
40
36
from bzrlib import (
41
37
    config,
51
47
    register_urlparse_netloc_protocol,
52
48
    Server,
53
49
    )
54
 
from bzrlib.transport.local import LocalURLServer
55
 
import bzrlib.ui
56
50
 
57
51
 
58
52
register_urlparse_netloc_protocol('aftp')
99
93
            self.is_active = True
100
94
        else:
101
95
            self.is_active = False
102
 
        
103
 
        # Most modern FTP servers support the APPE command. If ours doesn't, we (re)set this flag accordingly later.
 
96
 
 
97
        # Most modern FTP servers support the APPE command. If ours doesn't, we
 
98
        # (re)set this flag accordingly later.
104
99
        self._has_append = True
105
100
 
106
101
    def _get_FTP(self):
113
108
            self._set_connection(connection, credentials)
114
109
        return connection
115
110
 
 
111
    connection_class = ftplib.FTP
 
112
 
116
113
    def _create_connection(self, credentials=None):
117
114
        """Create a new connection with the provided credentials.
118
115
 
138
135
               ((self._host, self._port, user, '********',
139
136
                self.is_active),))
140
137
        try:
141
 
            connection = ftplib.FTP()
 
138
            connection = self.connection_class()
142
139
            connection.connect(host=self._host, port=self._port)
143
 
            if user and user != 'anonymous' and \
144
 
                    password is None: # '' is a valid password
145
 
                password = auth.get_password('ftp', self._host, user,
146
 
                                             port=self._port)
147
 
            connection.login(user=user, passwd=password)
 
140
            self._login(connection, auth, user, password)
148
141
            connection.set_pasv(not self.is_active)
149
142
            # binary mode is the default
150
143
            connection.voidcmd('TYPE I')
157
150
                                        " %s" % str(e), orig_error=e)
158
151
        return connection, (user, password)
159
152
 
 
153
    def _login(self, connection, auth, user, password):
 
154
        # '' is a valid password
 
155
        if user and user != 'anonymous' and password is None:
 
156
            password = auth.get_password('ftp', self._host,
 
157
                                         user, port=self._port)
 
158
        connection.login(user=user, passwd=password)
 
159
 
160
160
    def _reconnect(self):
161
161
        """Create a new connection with the previously used credentials"""
162
162
        credentials = self._get_credentials()
391
391
        location.
392
392
        """
393
393
        text = f.read()
394
 
        
395
394
        abspath = self._remote_path(relpath)
396
395
        if self.has(relpath):
397
396
            ftp = self._get_FTP()
426
425
        except ftplib.error_perm, e:
427
426
            # Check whether the command is not supported (reply code 502)
428
427
            if str(e).startswith('502 '):
429
 
                warning("FTP server does not support file appending natively. " \
430
 
                    "Performance may be severely degraded! (%s)", e)
 
428
                warning("FTP server does not support file appending natively. "
 
429
                        "Performance may be severely degraded! (%s)", e)
431
430
                self._has_append = False
432
431
                self._fallback_append(relpath, text, mode)
433
432
            else:
434
433
                self._translate_perm_error(e, abspath, extra='error appending',
435
434
                    unknown_exc=errors.NoSuchFile)
436
 
            
437
435
        except ftplib.error_temp, e:
438
436
            if retries > _number_of_retries:
439
 
                raise errors.TransportError("FTP temporary error during APPEND %s." \
440
 
                        "Aborting." % abspath, orig_error=e)
 
437
                raise errors.TransportError(
 
438
                    "FTP temporary error during APPEND %s. Aborting."
 
439
                    % abspath, orig_error=e)
441
440
            else:
442
441
                warning("FTP temporary error: %s. Retrying.", str(e))
443
442
                self._reconnect()
445
444
 
446
445
    def _fallback_append(self, relpath, text, mode = None):
447
446
        remote = self.get(relpath)
448
 
        remote.seek(0, 2)
 
447
        remote.seek(0, os.SEEK_END)
449
448
        remote.write(text)
450
 
        remote.seek(0, 0)
 
449
        remote.seek(0)
451
450
        return self.put_file(relpath, remote, mode)
452
451
 
453
452
    def _setmode(self, relpath, mode):