~bzr-pqm/bzr/bzr.dev

907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
1
#!/usr/bin/env python
2
"""\
3
An implementation of the Transport object for local
4
filesystem access.
5
"""
6
7
from bzrlib.transport import Transport, protocol_handlers
8
import os
9
10
class LocalTransport(Transport):
11
    """This is the transport agent for local filesystem access."""
12
13
    def __init__(self, base):
14
        """Set the base path where files will be stored."""
15
        from os.path import realpath
16
        super(LocalTransport, self).__init__(realpath(base))
17
907.1.2 by John Arbash Meinel
Working on making Branch() do all of it's work over a Transport.
18
    def clone(self, offset=None):
19
        """Return a new LocalTransport with root at self.base + offset
20
        Because the local filesystem does not require a connection, 
21
        we can just return a new object.
22
        """
23
        if offset is None:
24
            return LocalTransport(self.base)
25
        else:
26
            return LocalTransport(self.abspath(offset))
27
28
    def abspath(self, *args):
29
        """Return the full url to the given relative path.
30
        This can be supplied with multiple arguments
31
        """
32
        return os.path.join(self.base, *args)
907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
33
34
    def has(self, relpath):
907.1.2 by John Arbash Meinel
Working on making Branch() do all of it's work over a Transport.
35
        return os.access(self.abspath(relpath), os.F_OK)
907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
36
37
    def get(self, relpath):
38
        """Get the file at the given relative path.
39
        """
907.1.2 by John Arbash Meinel
Working on making Branch() do all of it's work over a Transport.
40
        return open(self.abspath(relpath), 'rb')
907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
41
42
    def put(self, relpath, f):
43
        """Copy the file-like object into the location.
44
        """
45
        from bzrlib.atomicfile import AtomicFile
46
907.1.2 by John Arbash Meinel
Working on making Branch() do all of it's work over a Transport.
47
        fp = AtomicFile(self.abspath(relpath), 'wb')
48
        try:
49
            self._pump(f, fp)
50
            fp.commit()
51
        finally:
52
            fp.close()
53
54
    def mkdir(self, relpath):
55
        """Create a directory at the given path."""
56
        os.mkdir(self.abspath(relpath))
57
58
    def open(self, relpath, mode='wb'):
59
        """Open a remote file for writing.
60
        This may return a proxy object, which is written to locally, and
61
        then when the file is closed, it is uploaded using put()
62
        """
63
        return open(self.abspath(relpath), mode)
907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
64
65
    def append(self, relpath, f):
66
        """Append the text in the file-like object into the final
67
        location.
68
        """
907.1.2 by John Arbash Meinel
Working on making Branch() do all of it's work over a Transport.
69
        fp = open(self.abspath(relpath), 'a+b')
907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
70
        self._pump(f, fp)
71
72
    def copy(self, rel_from, rel_to):
73
        """Copy the item at rel_from to the location at rel_to"""
74
        import shutil
907.1.2 by John Arbash Meinel
Working on making Branch() do all of it's work over a Transport.
75
        path_from = self.abspath(rel_from)
76
        path_to = self.abspath(rel_to)
907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
77
        shutil.copy(path_from, path_to)
78
79
    def move(self, rel_from, rel_to):
80
        """Move the item at rel_from to the location at rel_to"""
907.1.2 by John Arbash Meinel
Working on making Branch() do all of it's work over a Transport.
81
        path_from = self.abspath(rel_from)
82
        path_to = self.abspath(rel_to)
907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
83
84
        os.rename(path_from, path_to)
85
86
    def delete(self, relpath):
87
        """Delete the item at relpath"""
907.1.2 by John Arbash Meinel
Working on making Branch() do all of it's work over a Transport.
88
        os.remove(self.abspath(relpath))
907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
89
90
    def async_get(self, relpath):
91
        """Make a request for an file at the given location, but
92
        don't worry about actually getting it yet.
93
94
        :rtype: AsyncFile
95
        """
96
        raise NotImplementedError
97
907.1.2 by John Arbash Meinel
Working on making Branch() do all of it's work over a Transport.
98
    def list_dir(self, relpath):
99
        """Return a list of all files at the given location.
100
        WARNING: many transports do not support this, so trying avoid using
101
        it if at all possible.
102
        """
103
        return os.listdir(self.abspath(relpath))
104
105
    def stat(self, relpath):
106
        """Return the stat information for a file.
107
        """
108
        return os.stat(self.abspath(relpath))
109
907.1.1 by John Arbash Meinel
Reworking the Branch and Store code to support an abstracted filesystem layer.
110
# If nothing else matches, try the LocalTransport
111
protocol_handlers[None] = LocalTransport
112