~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/delta.py

  • Committer: Martin Pool
  • Date: 2005-08-04 22:30:50 UTC
  • Revision ID: mbp@sourcefrog.net-20050804223050-01256e5e26a90b1d
- merge patch to take ranges to diff -r option

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
#! /usr/bin/env python
1
2
# -*- coding: UTF-8 -*-
2
3
 
3
4
# This program is free software; you can redistribute it and/or modify
14
15
# along with this program; if not, write to the Free Software
15
16
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
16
17
 
17
 
from bzrlib.inventory import InventoryEntry
18
18
from bzrlib.trace import mutter
19
19
 
20
20
class TreeDelta(object):
27
27
    removed
28
28
        (path, id, kind)
29
29
    renamed
30
 
        (oldpath, newpath, id, kind, text_modified, meta_modified)
 
30
        (oldpath, newpath, id, kind, text_modified)
31
31
    modified
32
 
        (path, id, kind, text_modified, meta_modified)
 
32
        (path, id, kind)
33
33
    unchanged
34
34
        (path, id, kind)
35
35
 
36
36
    Each id is listed only once.
37
37
 
38
38
    Files that are both modified and renamed are listed only in
39
 
    renamed, with the text_modified flag true. The text_modified
40
 
    applies either to the the content of the file or the target of the
41
 
    symbolic link, depending of the kind of file.
 
39
    renamed, with the text_modified flag true.
42
40
 
43
41
    Files are only considered renamed if their name has changed or
44
42
    their parent directory has changed.  Renaming a directory
71
69
            self.modified, self.unchanged)
72
70
 
73
71
    def has_changed(self):
74
 
        return bool(self.modified
75
 
                    or self.added
76
 
                    or self.removed
77
 
                    or self.renamed)
 
72
        changes = len(self.added) + len(self.removed) + len(self.renamed)
 
73
        changes += len(self.modified) 
 
74
        return (changes != 0)
78
75
 
79
76
    def touches_file_id(self, file_id):
80
77
        """Return True if file_id is modified by this delta."""
90
87
 
91
88
    def show(self, to_file, show_ids=False, show_unchanged=False):
92
89
        def show_list(files):
93
 
            for item in files:
94
 
                path, fid, kind = item[:3]
95
 
 
 
90
            for path, fid, kind in files:
96
91
                if kind == 'directory':
97
92
                    path += '/'
98
93
                elif kind == 'symlink':
99
94
                    path += '@'
100
 
 
101
 
                if len(item) == 5 and item[4]:
102
 
                    path += '*'
103
 
 
 
95
                    
104
96
                if show_ids:
105
97
                    print >>to_file, '  %-30s %s' % (path, fid)
106
98
                else:
114
106
            print >>to_file, 'added:'
115
107
            show_list(self.added)
116
108
 
117
 
        extra_modified = []
118
 
 
119
109
        if self.renamed:
120
110
            print >>to_file, 'renamed:'
121
 
            for (oldpath, newpath, fid, kind,
122
 
                 text_modified, meta_modified) in self.renamed:
123
 
                if text_modified or meta_modified:
124
 
                    extra_modified.append((newpath, fid, kind,
125
 
                                           text_modified, meta_modified))
126
 
                if meta_modified:
127
 
                    newpath += '*'
 
111
            for oldpath, newpath, fid, kind, text_modified in self.renamed:
128
112
                if show_ids:
129
113
                    print >>to_file, '  %s => %s %s' % (oldpath, newpath, fid)
130
114
                else:
131
115
                    print >>to_file, '  %s => %s' % (oldpath, newpath)
132
116
                    
133
 
        if self.modified or extra_modified:
 
117
        if self.modified:
134
118
            print >>to_file, 'modified:'
135
119
            show_list(self.modified)
136
 
            show_list(extra_modified)
137
120
            
138
121
        if show_unchanged and self.unchanged:
139
122
            print >>to_file, 'unchanged:'
178
161
            kind = old_ie.kind
179
162
            assert kind == new_ie.kind
180
163
            
181
 
            assert kind in InventoryEntry.known_kinds, \
 
164
            assert kind in ('file', 'directory', 'symlink', 'root_directory'), \
182
165
                   'invalid file kind %r' % kind
183
166
 
184
167
            if kind == 'root_directory':
189
172
                    and not is_inside_any(specific_files, new_inv.id2path(file_id))):
190
173
                    continue
191
174
 
192
 
            # temporary hack until all entries are populated before clients 
193
 
            # get them
194
 
            old_path = old_inv.id2path(file_id)
195
 
            new_path = new_inv.id2path(file_id)
196
 
            old_ie._read_tree_state(old_path, old_tree)
197
 
            new_ie._read_tree_state(new_path, new_tree)
198
 
            text_modified, meta_modified = new_ie.detect_changes(old_ie)
 
175
            if kind == 'file':
 
176
                old_sha1 = old_tree.get_file_sha1(file_id)
 
177
                new_sha1 = new_tree.get_file_sha1(file_id)
 
178
                text_modified = (old_sha1 != new_sha1)
 
179
            else:
 
180
                ## mutter("no text to check for %r %r" % (file_id, kind))
 
181
                text_modified = False
199
182
 
200
183
            # TODO: Can possibly avoid calculating path strings if the
201
184
            # two files are unchanged and their names and parents are
204
187
            
205
188
            if (old_ie.name != new_ie.name
206
189
                or old_ie.parent_id != new_ie.parent_id):
207
 
                delta.renamed.append((old_path,
208
 
                                      new_path,
 
190
                delta.renamed.append((old_inv.id2path(file_id),
 
191
                                      new_inv.id2path(file_id),
209
192
                                      file_id, kind,
210
 
                                      text_modified, meta_modified))
211
 
            elif text_modified or meta_modified:
212
 
                delta.modified.append((new_path, file_id, kind,
213
 
                                       text_modified, meta_modified))
 
193
                                      text_modified))
 
194
            elif text_modified:
 
195
                delta.modified.append((new_inv.id2path(file_id), file_id, kind))
214
196
            elif want_unchanged:
215
 
                delta.unchanged.append((new_path, file_id, kind))
 
197
                delta.unchanged.append((new_inv.id2path(file_id), file_id, kind))
216
198
        else:
217
199
            kind = old_inv.get_file_kind(file_id)
218
200
            if kind == 'root_directory':
225
207
 
226
208
    mutter('start looking for new files')
227
209
    for file_id in new_inv:
228
 
        if file_id in old_inv or file_id not in new_tree:
 
210
        if file_id in old_inv:
229
211
            continue
230
212
        kind = new_inv.get_file_kind(file_id)
231
213
        if kind == 'root_directory':