/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar

« back to all changes in this revision

Viewing changes to bzrlib/annotate.py

  • Committer: Robert Collins
  • Date: 2008-02-13 03:30:01 UTC
  • mfrom: (3221 +trunk)
  • mto: This revision was merged to the branch mainline in revision 3224.
  • Revision ID: robertc@robertcollins.net-20080213033001-rw70ul0zb02ph856
Merge to fix conflicts.

Show diffs side-by-side

added added

removed removed

Lines of Context:
39
39
 
40
40
def annotate_file(branch, rev_id, file_id, verbose=False, full=False,
41
41
                  to_file=None, show_ids=False):
 
42
    """Annotate file_id at revision rev_id in branch.
 
43
 
 
44
    The branch should already be read_locked() when annotate_file is called.
 
45
 
 
46
    :param branch: The branch to look for revision numbers and history from.
 
47
    :param rev_id: The revision id to annotate.
 
48
    :param file_id: The file_id to annotate.
 
49
    :param verbose: Show all details rather than truncating to ensure
 
50
        reasonable text width.
 
51
    :param full: XXXX Not sure what this does.
 
52
    :param to_file: The file to output the annotation to; if None stdout is
 
53
        used.
 
54
    :param show_ids: Show revision ids in the annotation output.
 
55
    """
42
56
    if to_file is None:
43
57
        to_file = sys.stdout
44
58
 
154
168
        the SequenceMatcher.get_matching_blocks format.
155
169
    """
156
170
    if len(parents_lines) == 0:
157
 
        for line in new_lines:
158
 
            yield new_revision_id, line
 
171
        lines = [(new_revision_id, line) for line in new_lines]
159
172
    elif len(parents_lines) == 1:
160
 
        for data in _reannotate(parents_lines[0], new_lines, new_revision_id,
161
 
                                _left_matching_blocks):
162
 
            yield data
 
173
        lines = _reannotate(parents_lines[0], new_lines, new_revision_id,
 
174
                            _left_matching_blocks)
 
175
    elif len(parents_lines) == 2:
 
176
        left = _reannotate(parents_lines[0], new_lines, new_revision_id,
 
177
                           _left_matching_blocks)
 
178
        right = _reannotate(parents_lines[1], new_lines, new_revision_id)
 
179
        lines = []
 
180
        for idx in xrange(len(new_lines)):
 
181
            if left[idx][0] == right[idx][0]:
 
182
                # The annotations match, just return the left one
 
183
                lines.append(left[idx])
 
184
            elif left[idx][0] == new_revision_id:
 
185
                # The left parent claims a new value, return the right one
 
186
                lines.append(right[idx])
 
187
            elif right[idx][0] == new_revision_id:
 
188
                # The right parent claims a new value, return the left one
 
189
                lines.append(left[idx])
 
190
            else:
 
191
                # Both claim different origins
 
192
                lines.append((new_revision_id, left[idx][1]))
163
193
    else:
164
 
        block_list = [_left_matching_blocks] + [None] * len(parents_lines)
165
 
        reannotations = [list(_reannotate(p, new_lines, new_revision_id, b))
166
 
                         for p, b in zip(parents_lines, block_list)]
 
194
        reannotations = [_reannotate(parents_lines[0], new_lines,
 
195
                                     new_revision_id, _left_matching_blocks)]
 
196
        reannotations.extend(_reannotate(p, new_lines, new_revision_id)
 
197
                             for p in parents_lines[1:])
 
198
        lines = []
167
199
        for annos in zip(*reannotations):
168
200
            origins = set(a for a, l in annos)
169
 
            line = annos[0][1]
170
201
            if len(origins) == 1:
171
 
                yield iter(origins).next(), line
172
 
            elif len(origins) == 2 and new_revision_id in origins:
173
 
                yield (x for x in origins if x != new_revision_id).next(), line
 
202
                # All the parents agree, so just return the first one
 
203
                lines.append(annos[0])
174
204
            else:
175
 
                yield new_revision_id, line
 
205
                line = annos[0][1]
 
206
                if len(origins) == 2 and new_revision_id in origins:
 
207
                    origins.remove(new_revision_id)
 
208
                if len(origins) == 1:
 
209
                    lines.append((origins.pop(), line))
 
210
                else:
 
211
                    lines.append((new_revision_id, line))
 
212
    return lines
176
213
 
177
214
 
178
215
def _reannotate(parent_lines, new_lines, new_revision_id,
183
220
        matcher = patiencediff.PatienceSequenceMatcher(None,
184
221
            plain_parent_lines, new_lines)
185
222
        matching_blocks = matcher.get_matching_blocks()
 
223
    lines = []
186
224
    for i, j, n in matching_blocks:
187
225
        for line in new_lines[new_cur:j]:
188
 
            yield new_revision_id, line
189
 
        for data in parent_lines[i:i+n]:
190
 
            yield data
 
226
            lines.append((new_revision_id, line))
 
227
        lines.extend(parent_lines[i:i+n])
191
228
        new_cur = j + n
 
229
    return lines