41
40
raise tests.TestSkipped(
42
41
"format %s doesn't support tags" % branch._format)
43
def make_branch_with_revisions(self, relpath, revisions):
44
builder = self.make_branch_builder(relpath)
45
builder.start_series()
46
for revid in revisions:
47
builder.build_commit(rev_id=revid)
48
builder.finish_series()
49
return builder.get_branch()
44
51
def test_tags_initially_empty(self):
45
52
b = self.make_branch('b')
46
53
tags = b.tags.get_tag_dict()
47
54
self.assertEqual(tags, {})
49
56
def test_make_and_lookup_tag(self):
50
b = self.make_branch('b')
57
b = self.make_branch_with_revisions('b',
58
['target-revid-1', 'target-revid-2'])
51
59
b.tags.set_tag('tag-name', 'target-revid-1')
52
60
b.tags.set_tag('other-name', 'target-revid-2')
53
61
# then reopen the branch and see they're still there
64
72
self.assertFalse(b.tags.has_tag('imaginary'))
66
74
def test_reverse_tag_dict(self):
67
b = self.make_branch('b')
75
b = self.make_branch_with_revisions('b',
76
['target-revid-1', 'target-revid-2'])
68
77
b.tags.set_tag('tag-name', 'target-revid-1')
69
78
b.tags.set_tag('other-name', 'target-revid-2')
70
79
# then reopen the branch and check reverse map id->tags list
71
80
b = branch.Branch.open('b')
72
self.assertEqual(b.tags.get_reverse_tag_dict(),
81
self.assertEqual(dict(b.tags.get_reverse_tag_dict()),
73
82
{'target-revid-1': ['tag-name'],
74
83
'target-revid-2': ['other-name'],
86
def test_ghost_tag(self):
87
b = self.make_branch('b')
88
if not b._format.supports_tags_referencing_ghosts():
89
self.assertRaises(errors.GhostTagsNotSupported,
90
b.tags.set_tag, "ghost", "idontexist")
92
b.tags.set_tag("ghost", "idontexist")
93
self.assertEqual("idontexist", b.tags.lookup_tag("ghost"))
77
95
def test_no_such_tag(self):
78
96
b = self.make_branch('b')
80
98
b.tags.lookup_tag('bosko')
81
99
except errors.NoSuchTag, e:
82
self.assertEquals(e.tag_name, 'bosko')
83
self.assertEquals(str(e), 'No such tag: bosko')
100
self.assertEqual(e.tag_name, 'bosko')
101
self.assertEqual(str(e), 'No such tag: bosko')
85
103
self.fail("didn't get expected exception")
87
105
def test_merge_tags(self):
88
b1 = self.make_branch('b1')
89
b2 = self.make_branch('b2')
106
b1 = self.make_branch_with_revisions('b1', ['revid', 'revid-1'])
107
b2 = self.make_branch_with_revisions('b2', ['revid', 'revid-2'])
90
108
# if there are tags in the source and not the destination, then they
92
110
b1.tags.set_tag('tagname', 'revid')
93
111
b1.tags.merge_to(b2.tags)
94
self.assertEquals(b2.tags.lookup_tag('tagname'), 'revid')
112
self.assertEqual(b2.tags.lookup_tag('tagname'), 'revid')
95
113
# if a tag is in the destination and not in the source, it is not
96
114
# removed when we merge them
97
115
b2.tags.set_tag('in-destination', 'revid')
98
result = b1.tags.merge_to(b2.tags)
99
self.assertEquals(list(result), [])
100
self.assertEquals(b2.tags.lookup_tag('in-destination'), 'revid')
116
updates, conflicts = b1.tags.merge_to(b2.tags)
117
self.assertEqual(list(conflicts), [])
118
self.assertEqual(updates, {})
119
self.assertEqual(b2.tags.lookup_tag('in-destination'), 'revid')
101
120
# if there's a conflicting tag, it's reported -- the command line
102
121
# interface will say "these tags couldn't be copied"
103
122
b1.tags.set_tag('conflicts', 'revid-1')
104
123
b2.tags.set_tag('conflicts', 'revid-2')
105
result = b1.tags.merge_to(b2.tags)
106
self.assertEquals(list(result),
124
updates, conflicts = b1.tags.merge_to(b2.tags)
125
self.assertEqual(list(conflicts),
107
126
[('conflicts', 'revid-1', 'revid-2')])
108
127
# and it keeps the same value
109
self.assertEquals(b2.tags.lookup_tag('conflicts'), 'revid-2')
128
self.assertEqual(updates, {})
129
self.assertEqual(b2.tags.lookup_tag('conflicts'), 'revid-2')
111
131
def test_unicode_tag(self):
112
b1 = self.make_branch('b')
113
132
tag_name = u'\u3070'
114
133
# in anticipation of the planned change to treating revision ids as
115
134
# just 8bit strings
116
135
revid = ('revid' + tag_name).encode('utf-8')
136
b1 = self.make_branch_with_revisions('b', [revid])
117
137
b1.tags.set_tag(tag_name, revid)
118
self.assertEquals(b1.tags.lookup_tag(tag_name), revid)
138
self.assertEqual(b1.tags.lookup_tag(tag_name), revid)
120
140
def test_delete_tag(self):
121
b = self.make_branch('b')
122
141
tag_name = u'\N{GREEK SMALL LETTER ALPHA}'
123
142
revid = ('revid' + tag_name).encode('utf-8')
143
b = self.make_branch_with_revisions('b', [revid])
124
144
b.tags.set_tag(tag_name, revid)
125
145
# now try to delete it
126
146
b.tags.delete_tag(tag_name)
327
354
child.bind(master)
329
356
master.tags.delete_tag('foo')
330
tag_conflicts = other.tags.merge_to(child.tags)
357
tag_updates, tag_conflicts = other.tags.merge_to(child.tags)
331
358
# Conflict in child, so it is unchanged.
332
self.assertEquals('rev-2', child.tags.lookup_tag('foo'))
359
self.assertEqual('rev-2', child.tags.lookup_tag('foo'))
333
360
# No conflict in the master, so the 'foo' tag equals other's value here.
334
self.assertEquals('rev-1', master.tags.lookup_tag('foo'))
361
self.assertEqual('rev-1', master.tags.lookup_tag('foo'))
335
362
# The conflict is reported.
336
self.assertEquals([(u'foo', 'rev-1', 'rev-2')], list(tag_conflicts))
363
self.assertEqual([(u'foo', 'rev-1', 'rev-2')], list(tag_conflicts))
364
self.assertEqual({u'foo': 'rev-1'}, tag_updates)
338
366
def test_merge_to_conflict_in_master_only(self):
339
367
"""When new_tags.merge_to(child.tags) conflicts with the master but not
346
374
child.bind(master)
348
376
master.tags.set_tag('foo', 'rev-2')
349
tag_conflicts = other.tags.merge_to(child.tags)
377
tag_updates, tag_conflicts = other.tags.merge_to(child.tags)
350
378
# No conflict in the child, so the 'foo' tag equals other's value here.
351
self.assertEquals('rev-1', child.tags.lookup_tag('foo'))
379
self.assertEqual('rev-1', child.tags.lookup_tag('foo'))
352
380
# Conflict in master, so it is unchanged.
353
self.assertEquals('rev-2', master.tags.lookup_tag('foo'))
381
self.assertEqual('rev-2', master.tags.lookup_tag('foo'))
354
382
# The conflict is reported.
355
self.assertEquals([(u'foo', 'rev-1', 'rev-2')], list(tag_conflicts))
383
self.assertEqual({u'foo': 'rev-1'}, tag_updates)
384
self.assertEqual([(u'foo', 'rev-1', 'rev-2')], list(tag_conflicts))
357
386
def test_merge_to_same_conflict_in_master_and_child(self):
358
387
"""When new_tags.merge_to(child.tags) conflicts the same way with the
365
394
child = self.make_branch('child')
366
395
child.bind(master)
368
tag_conflicts = other.tags.merge_to(child.tags)
397
tag_updates, tag_conflicts = other.tags.merge_to(child.tags)
369
398
# Both master and child conflict, so both stay as rev-2
370
self.assertEquals('rev-2', child.tags.lookup_tag('foo'))
371
self.assertEquals('rev-2', master.tags.lookup_tag('foo'))
399
self.assertEqual('rev-2', child.tags.lookup_tag('foo'))
400
self.assertEqual('rev-2', master.tags.lookup_tag('foo'))
372
401
# The conflict is reported exactly once, even though it occurs in both
373
402
# master and child.
374
self.assertEquals([(u'foo', 'rev-1', 'rev-2')], list(tag_conflicts))
403
self.assertEqual({}, tag_updates)
404
self.assertEqual([(u'foo', 'rev-1', 'rev-2')], list(tag_conflicts))
376
406
def test_merge_to_different_conflict_in_master_and_child(self):
377
407
"""When new_tags.merge_to(child.tags) conflicts differently in the
387
417
# We use the private method _set_tag_dict because normally bzr tries to
388
418
# avoid this scenario.
389
419
child.tags._set_tag_dict({'foo': 'rev-3'})
390
tag_conflicts = other.tags.merge_to(child.tags)
420
tag_updates, tag_conflicts = other.tags.merge_to(child.tags)
391
421
# Both master and child conflict, so both stay as they were.
392
self.assertEquals('rev-3', child.tags.lookup_tag('foo'))
393
self.assertEquals('rev-2', master.tags.lookup_tag('foo'))
422
self.assertEqual('rev-3', child.tags.lookup_tag('foo'))
423
self.assertEqual('rev-2', master.tags.lookup_tag('foo'))
394
424
# Both conflicts are reported.
425
self.assertEqual({}, tag_updates)
396
427
[(u'foo', 'rev-1', 'rev-2'), (u'foo', 'rev-1', 'rev-3')],
397
428
sorted(tag_conflicts))
447
478
def test_no_functions(self):
448
479
rev = self.branch.last_revision()
449
self.assertEquals(None, self.branch.automatic_tag_name(rev))
480
self.assertEqual(None, self.branch.automatic_tag_name(rev))
451
482
def test_returns_tag_name(self):
452
483
def get_tag_name(br, revid):
454
485
branch.Branch.hooks.install_named_hook('automatic_tag_name',
455
486
get_tag_name, 'get tag name foo')
456
self.assertEquals("foo", self.branch.automatic_tag_name(
487
self.assertEqual("foo", self.branch.automatic_tag_name(
457
488
self.branch.last_revision()))
459
490
def test_uses_first_return(self):
460
491
get_tag_name_1 = lambda br, revid: "foo1"
461
492
get_tag_name_2 = lambda br, revid: "foo2"