~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/osutils.py

  • Committer: Aaron Bentley
  • Date: 2005-09-29 21:07:17 UTC
  • mfrom: (1393.1.6)
  • mto: (1185.25.1)
  • mto: This revision was merged to the branch mainline in revision 1419.
  • Revision ID: abentley@panoramicfeedback.com-20050929210717-cd73981590f17017
Merged the weave changes

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
# Bazaar-NG -- distributed version control
2
 
 
 
2
#
3
3
# Copyright (C) 2005 by Canonical Ltd
4
 
 
 
4
#
5
5
# This program is free software; you can redistribute it and/or modify
6
6
# it under the terms of the GNU General Public License as published by
7
7
# the Free Software Foundation; either version 2 of the License, or
8
8
# (at your option) any later version.
9
 
 
 
9
#
10
10
# This program is distributed in the hope that it will be useful,
11
11
# but WITHOUT ANY WARRANTY; without even the implied warranty of
12
12
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
13
# GNU General Public License for more details.
14
 
 
 
14
#
15
15
# You should have received a copy of the GNU General Public License
16
16
# along with this program; if not, write to the Free Software
17
17
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18
18
 
19
 
import os, types, re, time, errno, sys
 
19
from shutil import copyfile
20
20
from stat import (S_ISREG, S_ISDIR, S_ISLNK, ST_MODE, ST_SIZE,
21
 
        S_ISCHR, S_ISBLK, S_ISFIFO, S_ISSOCK)
 
21
                  S_ISCHR, S_ISBLK, S_ISFIFO, S_ISSOCK)
 
22
from cStringIO import StringIO
 
23
import errno
 
24
import os
 
25
import re
 
26
import sha
 
27
import sys
 
28
import time
 
29
import types
22
30
 
 
31
import bzrlib
23
32
from bzrlib.errors import BzrError
24
33
from bzrlib.trace import mutter
25
 
import bzrlib
26
 
from shutil import copyfile
 
34
 
27
35
 
28
36
def make_readonly(filename):
29
37
    """Make a filename read-only."""
30
 
    # TODO: probably needs to be fixed for windows
31
38
    mod = os.stat(filename).st_mode
32
39
    mod = mod & 0777555
33
40
    os.chmod(filename, mod)
50
57
    # TODO: I'm not really sure this is the best format either.x
51
58
    global _QUOTE_RE
52
59
    if _QUOTE_RE == None:
53
 
        _QUOTE_RE = re.compile(r'([^a-zA-Z0-9.,:/_~-])')
 
60
        _QUOTE_RE = re.compile(r'([^a-zA-Z0-9.,:/\\_~-])')
54
61
        
55
62
    if _QUOTE_RE.search(f):
56
63
        return '"' + f + '"'
89
96
        raise BzrError('invalid file kind %r' % kind)
90
97
 
91
98
 
92
 
 
93
99
def backup_file(fn):
94
100
    """Copy a file to a backup.
95
101
 
97
103
 
98
104
    If the file is already a backup, it's not copied.
99
105
    """
100
 
    import os
101
106
    if fn[-1] == '~':
102
107
        return
103
108
    bfn = fn + '~'
114
119
    finally:
115
120
        outf.close()
116
121
 
117
 
def rename(path_from, path_to):
118
 
    """Basically the same as os.rename() just special for win32"""
119
 
    if sys.platform == 'win32':
120
 
        try:
121
 
            os.remove(path_to)
122
 
        except OSError, e:
123
 
            if e.errno != e.ENOENT:
124
 
                raise
125
 
    os.rename(path_from, path_to)
126
 
 
127
 
 
128
 
 
 
122
if os.name == 'nt':
 
123
    import shutil
 
124
    rename = shutil.move
 
125
else:
 
126
    rename = os.rename
129
127
 
130
128
 
131
129
def isdir(f):
136
134
        return False
137
135
 
138
136
 
139
 
 
140
137
def isfile(f):
141
138
    """True if f is a regular file."""
142
139
    try:
155
152
    The empty string as a dir name is taken as top-of-tree and matches 
156
153
    everything.
157
154
    
158
 
    >>> is_inside('src', 'src/foo.c')
 
155
    >>> is_inside('src', os.path.join('src', 'foo.c'))
159
156
    True
160
157
    >>> is_inside('src', 'srccontrol')
161
158
    False
162
 
    >>> is_inside('src', 'src/a/a/a/foo.c')
 
159
    >>> is_inside('src', os.path.join('src', 'a', 'a', 'a', 'foo.c'))
163
160
    True
164
161
    >>> is_inside('foo.c', 'foo.c')
165
162
    True
175
172
    
176
173
    if dir == '':
177
174
        return True
178
 
    
 
175
 
179
176
    if dir[-1] != os.sep:
180
177
        dir += os.sep
181
 
    
 
178
 
182
179
    return fname.startswith(dir)
183
180
 
184
181
 
196
193
    tofile.write(fromfile.read())
197
194
 
198
195
 
199
 
def uuid():
200
 
    """Return a new UUID"""
201
 
    try:
202
 
        return file('/proc/sys/kernel/random/uuid').readline().rstrip('\n')
203
 
    except IOError:
204
 
        return chomp(os.popen('uuidgen').readline())
205
 
 
206
 
 
207
196
def sha_file(f):
208
 
    import sha
209
197
    if hasattr(f, 'tell'):
210
198
        assert f.tell() == 0
211
199
    s = sha.new()
218
206
    return s.hexdigest()
219
207
 
220
208
 
 
209
 
 
210
def sha_strings(strings):
 
211
    """Return the sha-1 of concatenation of strings"""
 
212
    s = sha.new()
 
213
    map(s.update, strings)
 
214
    return s.hexdigest()
 
215
 
 
216
 
221
217
def sha_string(f):
222
 
    import sha
223
218
    s = sha.new()
224
219
    s.update(f)
225
220
    return s.hexdigest()
226
221
 
227
222
 
228
 
 
229
223
def fingerprint_file(f):
230
 
    import sha
231
224
    s = sha.new()
232
225
    b = f.read()
233
226
    s.update(b)
243
236
    
244
237
    TODO: Global option --config-dir to override this.
245
238
    """
246
 
    return os.path.expanduser("~/.bzr.conf")
 
239
    return os.path.join(os.path.expanduser("~"), ".bzr.conf")
247
240
 
248
241
 
249
242
def _auto_user_id():
353
346
    if e:
354
347
        m = re.search(r'[\w+.-]+@[\w+.-]+', e)
355
348
        if not m:
356
 
            raise BzrError("%r doesn't seem to contain a reasonable email address" % e)
 
349
            raise BzrError("%r doesn't seem to contain "
 
350
                           "a reasonable email address" % e)
357
351
        return m.group(0)
358
352
 
359
353
    return _auto_user_id()[1]
360
 
    
361
354
 
362
355
 
363
356
def compare_files(a, b):
372
365
            return True
373
366
 
374
367
 
375
 
 
376
368
def local_time_offset(t=None):
377
369
    """Return offset of local zone from GMT, either at present or at time t."""
378
370
    # python2.3 localtime() can't take None
500
492
            return None
501
493
        raise
502
494
 
 
495
 
 
496
def split_lines(s):
 
497
    """Split s into lines, but without removing the newline characters."""
 
498
    return StringIO(s).readlines()
 
499
 
 
500
 
503
501
def hardlinks_good():
504
502
    return sys.platform not in ('win32', 'cygwin', 'darwin')
505
503
 
 
504
 
506
505
def link_or_copy(src, dest):
507
506
    """Hardlink a file, or copy it if it can't be hardlinked."""
508
507
    if not hardlinks_good():