/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 breezy/diff.py

  • Committer: Jelmer Vernooij
  • Date: 2018-07-11 21:06:20 UTC
  • mfrom: (7033 work)
  • mto: This revision was merged to the branch mainline in revision 7036.
  • Revision ID: jelmer@jelmer.uk-20180711210620-pj0v9i3xe48qnsb2
merge trunk.

Show diffs side-by-side

added added

removed removed

Lines of Context:
47
47
from .registry import (
48
48
    Registry,
49
49
    )
 
50
from .sixish import text_type
50
51
from .trace import mutter, note, warning
51
52
from .tree import FileTimestampUnavailable
52
53
 
73
74
        self.opcodes = None
74
75
 
75
76
 
76
 
def internal_diff(old_filename, oldlines, new_filename, newlines, to_file,
 
77
def internal_diff(old_label, oldlines, new_label, newlines, to_file,
77
78
                  allow_binary=False, sequence_matcher=None,
78
79
                  path_encoding='utf8', context_lines=DEFAULT_CONTEXT_AMOUNT):
79
80
    # FIXME: difflib is wrong if there is no trailing newline.
92
93
 
93
94
    if sequence_matcher is None:
94
95
        sequence_matcher = patiencediff.PatienceSequenceMatcher
95
 
    ud = patiencediff.unified_diff(oldlines, newlines,
96
 
                      fromfile=old_filename.encode(path_encoding, 'replace'),
97
 
                      tofile=new_filename.encode(path_encoding, 'replace'),
 
96
    ud = patiencediff.unified_diff_bytes(oldlines, newlines,
 
97
                      fromfile=old_label.encode(path_encoding, 'replace'),
 
98
                      tofile=new_label.encode(path_encoding, 'replace'),
98
99
                      n=context_lines, sequencematcher=sequence_matcher)
99
100
 
100
101
    ud = list(ud)
103
104
    # work-around for difflib being too smart for its own good
104
105
    # if /dev/null is "1,0", patch won't recognize it as /dev/null
105
106
    if not oldlines:
106
 
        ud[2] = ud[2].replace('-1,0', '-0,0')
 
107
        ud[2] = ud[2].replace(b'-1,0', b'-0,0')
107
108
    elif not newlines:
108
 
        ud[2] = ud[2].replace('+1,0', '+0,0')
 
109
        ud[2] = ud[2].replace(b'+1,0', b'+0,0')
109
110
 
110
111
    for line in ud:
111
112
        to_file.write(line)
112
 
        if not line.endswith('\n'):
113
 
            to_file.write("\n\\ No newline at end of file\n")
114
 
    to_file.write('\n')
 
113
        if not line.endswith(b'\n'):
 
114
            to_file.write(b"\n\\ No newline at end of file\n")
 
115
    to_file.write(b'\n')
115
116
 
116
117
 
117
118
def _spawn_external_diff(diffcmd, capture_errors=True):
185
186
    return diff_opts
186
187
 
187
188
 
188
 
def external_diff(old_filename, oldlines, new_filename, newlines, to_file,
 
189
def external_diff(old_label, oldlines, new_label, newlines, to_file,
189
190
                  diff_opts):
190
191
    """Display a diff by calling out to the external diff program."""
191
192
    # make sure our own output is properly ordered before the diff
215
216
        if sys.platform == 'win32':
216
217
            # Popen doesn't do the proper encoding for external commands
217
218
            # Since we are dealing with an ANSI api, use mbcs encoding
218
 
            old_filename = old_filename.encode('mbcs')
219
 
            new_filename = new_filename.encode('mbcs')
 
219
            old_label = old_label.encode('mbcs')
 
220
            new_label = new_label.encode('mbcs')
220
221
        diffcmd = ['diff',
221
 
                   '--label', old_filename,
 
222
                   '--label', old_label,
222
223
                   old_abspath,
223
 
                   '--label', new_filename,
 
224
                   '--label', new_label,
224
225
                   new_abspath,
225
226
                   '--binary',
226
227
                  ]
235
236
        rc = pipe.returncode
236
237
 
237
238
        # internal_diff() adds a trailing newline, add one here for consistency
238
 
        out += '\n'
 
239
        out += b'\n'
239
240
        if rc == 2:
240
241
            # 'diff' gives retcode == 2 for all sorts of errors
241
242
            # one of those is 'Binary files differ'.
248
249
            out, err = pipe.communicate()
249
250
 
250
251
            # Write out the new i18n diff response
251
 
            to_file.write(out+'\n')
 
252
            to_file.write(out+b'\n')
252
253
            if pipe.returncode != 2:
253
254
                raise errors.BzrError(
254
255
                               'external diff failed with exit code 2'
255
256
                               ' when run with LANG=C and LC_ALL=C,'
256
257
                               ' but not when run natively: %r' % (diffcmd,))
257
258
 
258
 
            first_line = lang_c_out.split('\n', 1)[0]
 
259
            first_line = lang_c_out.split(b'\n', 1)[0]
259
260
            # Starting with diffutils 2.8.4 the word "binary" was dropped.
260
 
            m = re.match('^(binary )?files.*differ$', first_line, re.I)
 
261
            m = re.match(b'^(binary )?files.*differ$', first_line, re.I)
261
262
            if m is None:
262
263
                raise errors.BzrError('external diff failed with exit code 2;'
263
264
                                      ' command: %r' % (diffcmd,))
611
612
 
612
613
    def diff_symlink(self, old_target, new_target):
613
614
        if old_target is None:
614
 
            self.to_file.write('=== target is %r\n' % new_target)
 
615
            self.to_file.write(b'=== target is \'%s\'\n' %
 
616
                new_target.encode(self.path_encoding, 'replace'))
615
617
        elif new_target is None:
616
 
            self.to_file.write('=== target was %r\n' % old_target)
 
618
            self.to_file.write(b'=== target was \'%s\'\n' %
 
619
                old_target.encode(self.path_encoding, 'replace'))
617
620
        else:
618
 
            self.to_file.write('=== target changed %r => %r\n' %
619
 
                              (old_target, new_target))
 
621
            self.to_file.write(b'=== target changed \'%s\' => \'%s\'\n' %
 
622
                              (old_target.encode(self.path_encoding, 'replace'),
 
623
                               new_target.encode(self.path_encoding, 'replace')))
620
624
        return self.CHANGED
621
625
 
622
626
 
662
666
            to_file_id = None
663
667
        else:
664
668
            return self.CANNOT_DIFF
665
 
        from_label = '%s%s\t%s' % (self.old_label, old_path, old_date)
666
 
        to_label = '%s%s\t%s' % (self.new_label, new_path, new_date)
 
669
        from_label = '%s%s\t%s' % (self.old_label, old_path,
 
670
                old_date)
 
671
        to_label = '%s%s\t%s' % (self.new_label, new_path,
 
672
                new_date)
667
673
        return self.diff_text(old_path, new_path, from_label, to_label,
668
674
            from_file_id, to_file_id)
669
675
 
1037
1043
 
1038
1044
    def _diff(self, old_path, new_path, old_kind, new_kind, file_id):
1039
1045
        result = DiffPath._diff_many(self.differs, file_id, old_path,
1040
 
                                       new_path, old_kind, new_kind)
 
1046
                                     new_path, old_kind, new_kind)
1041
1047
        if result is DiffPath.CANNOT_DIFF:
1042
1048
            error_path = new_path
1043
1049
            if error_path is None: