Skip to content

Commit 5208d6a

Browse files
author
jomae
committed
1.2.2dev: merge [15759] from 1.0-stable (fix for #12758)
git-svn-id: http://trac.edgewall.org/intertrac/log:/branches/1.2-stable@15760 af82e41b-90c4-0310-8c96-b1721e28e2e2
2 parents 8a42f3e + b2d3d92 commit 5208d6a

File tree

3 files changed

+100
-36
lines changed

3 files changed

+100
-36
lines changed

tracopt/versioncontrol/git/PyGIT.py

+35-35
Original file line numberDiff line numberDiff line change
@@ -1010,44 +1010,44 @@ def diff_tree(self, tree1, tree2, path='', find_renames=False):
10101010
if find_renames:
10111011
diff_tree_args.append('-M')
10121012
diff_tree_args.extend([str(tree1) if tree1 else '--root',
1013-
str(tree2),
1014-
'--', path])
1013+
str(tree2), '--', path])
1014+
result = self.repo.diff_tree(*diff_tree_args)
1015+
if not result:
1016+
return
10151017

1016-
lines = self.repo.diff_tree(*diff_tree_args).split('\0')
1018+
def iter_entry(result):
1019+
start = 0
1020+
while True:
1021+
idx = result.find('\0', start)
1022+
if idx == -1:
1023+
return
1024+
yield result[start:idx]
1025+
start = idx + 1
1026+
1027+
iterate = iter_entry(result)
10171028

1018-
assert lines[-1] == ''
1019-
del lines[-1]
1029+
def next_entry():
1030+
return iterate.next()
10201031

1021-
if tree1 is None and lines:
1032+
if not tree1:
10221033
# if only one tree-sha is given on commandline,
10231034
# the first line is just the redundant tree-sha itself...
1024-
assert not lines[0].startswith(':')
1025-
del lines[0]
1026-
1027-
# FIXME: the following code is ugly, needs rewrite
1028-
1029-
chg = None
1030-
1031-
def __chg_tuple():
1032-
if len(chg) == 6:
1033-
chg.append(None)
1034-
else:
1035-
chg[6] = self._fs_to_unicode(chg[6])
1036-
chg[5] = self._fs_to_unicode(chg[5])
1035+
entry = next_entry()
1036+
assert not entry.startswith(':')
10371037

1038-
assert len(chg) == 7
1039-
return tuple(chg)
1040-
1041-
for line in lines:
1042-
if line.startswith(':'):
1043-
if chg:
1044-
yield __chg_tuple()
1045-
1046-
chg = line[1:].split()
1047-
assert len(chg) == 5
1048-
else:
1049-
chg.append(line)
1050-
1051-
# handle left-over chg entry
1052-
if chg:
1053-
yield __chg_tuple()
1038+
while True:
1039+
try:
1040+
entry = next_entry()
1041+
except StopIteration:
1042+
return
1043+
assert entry.startswith(':')
1044+
values = entry[1:].split(' ')
1045+
assert len(values) == 5
1046+
old_mode, new_mode, old_sha, new_sha, change = values
1047+
change = change[:1]
1048+
old_path = self._fs_to_unicode(next_entry())
1049+
new_path = None
1050+
if change in ('R', 'C'): # renamed or copied
1051+
new_path = self._fs_to_unicode(next_entry())
1052+
yield (old_mode, new_mode, old_sha, new_sha, change, old_path,
1053+
new_path)

tracopt/versioncontrol/git/git_fs.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -877,7 +877,7 @@ def get_changes(self):
877877
if mode2.startswith('04') or mode1.startswith('04') \
878878
else Node.FILE
879879

880-
action = GitChangeset.action_map[action[0]]
880+
action = GitChangeset.action_map[action]
881881

882882
if action == Changeset.ADD:
883883
p_path = p_rev = None

tracopt/versioncontrol/git/tests/git_fs.py

+64
Original file line numberDiff line numberDiff line change
@@ -781,6 +781,70 @@ def test_iter_nodes(self):
781781
(root_commit, 'B/b2.txt'),
782782
], [(node.created_rev, node.path) for node in nodes])
783783

784+
def test_colon_character_in_filename(self):
785+
self._git_init(data=False)
786+
self._git_fast_import(self._data_colon_character_in_filename)
787+
self._add_repository('gitrepos')
788+
repos = self._repomgr.get_repository('gitrepos')
789+
repos.sync()
790+
rev1 = '382e1e6b85ba20ce8a84af1a875eaa50b8e1e092' # root commit
791+
rev2 = 'd8001832aad079f85a39a54a388a8b15fe31093d'
792+
ADD = Changeset.ADD
793+
MOVE = Changeset.MOVE
794+
FILE = Node.FILE
795+
796+
cset = repos.get_changeset(rev1)
797+
self.assertEqual(set([('0100644', FILE, ADD, None, None),
798+
('0100644.txt', FILE, ADD, None, None),
799+
(':100644', FILE, ADD, None, None),
800+
(':100644.txt', FILE, ADD, None, None),
801+
('a100644', FILE, ADD, None, None),
802+
('a100644.txt', FILE, ADD, None, None)
803+
]),
804+
set(cset.get_changes()))
805+
806+
cset = repos.get_changeset(rev2)
807+
self.assertEqual(set([(':100666', FILE, MOVE, ':100644', rev1)]),
808+
set(cset.get_changes()))
809+
810+
_data_colon_character_in_filename = """\
811+
blob
812+
mark :1
813+
data 0
814+
815+
blob
816+
mark :2
817+
data 16
818+
...............
819+
820+
reset refs/heads/master
821+
commit refs/heads/master
822+
mark :3
823+
author Joe <[email protected]> 1491387182 +0000
824+
committer Joe <[email protected]> 1491387182 +0000
825+
data 9
826+
(#12758)
827+
M 100644 :1 0100644.txt
828+
M 100644 :1 0100644
829+
M 100644 :1 :100644.txt
830+
M 100644 :2 :100644
831+
M 100644 :1 a100644.txt
832+
M 100644 :1 a100644
833+
834+
commit refs/heads/master
835+
mark :4
836+
author Joe <[email protected]> 1491387183 +0000
837+
committer Joe <[email protected]> 1491387183 +0000
838+
data 16
839+
(#12758) rename
840+
from :3
841+
D :100644
842+
M 100644 :2 :100666
843+
844+
reset refs/heads/master
845+
from :4
846+
"""
847+
784848
def _get_quickjump_names(self, repos):
785849
return list(name for type, name, path, rev
786850
in repos.get_quickjump_entries('HEAD'))

0 commit comments

Comments
 (0)