~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/tests/test_merge_directive.py

  • Committer: John Arbash Meinel
  • Date: 2007-03-15 22:35:35 UTC
  • mto: This revision was merged to the branch mainline in revision 2363.
  • Revision ID: john@arbash-meinel.com-20070315223535-d3d4964oe1hc8zhg
Add an overzealous test, for Unicode support of _iter_changes.
For both knowns and unknowns.
And include a basic, if suboptimal, fix.
I would rather defer the decoding until we've determined that we are going to return the tuple.
There is still something broken with added files, but I'll get to that.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
# Copyright (C) 2007 Canonical Ltd
 
2
#
 
3
# This program is free software; you can redistribute it and/or modify
 
4
# it under the terms of the GNU General Public License as published by
 
5
# the Free Software Foundation; either version 2 of the License, or
 
6
# (at your option) any later version.
 
7
#
 
8
# This program is distributed in the hope that it will be useful,
 
9
# but WITHOUT ANY WARRANTY; without even the implied warranty of
 
10
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
11
# GNU General Public License for more details.
 
12
#
 
13
# You should have received a copy of the GNU General Public License
 
14
# along with this program; if not, write to the Free Software
 
15
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 
16
 
 
17
 
 
18
from bzrlib import (
 
19
    errors,
 
20
    gpg,
 
21
    merge_directive,
 
22
    tests,
 
23
    )
 
24
 
 
25
 
 
26
OUTPUT1 = """# Bazaar merge directive format 1
 
27
# revision_id: example:
 
28
# target_branch: http://example.com
 
29
# testament_sha1: sha
 
30
# timestamp: 1970-01-01 00:09:33 +0002
 
31
#\x20
 
32
booga"""
 
33
 
 
34
 
 
35
OUTPUT2 = """# Bazaar merge directive format 1
 
36
# revision_id: example:
 
37
# target_branch: http://example.com
 
38
# testament_sha1: sha
 
39
# timestamp: 1970-01-01 00:09:33 +0002
 
40
# source_branch: http://example.org
 
41
# message: Hi mom!
 
42
#\x20
 
43
booga"""
 
44
 
 
45
 
 
46
INPUT1 = """
 
47
I was thinking today about creating a merge directive.
 
48
 
 
49
So I did.
 
50
 
 
51
Here it is.
 
52
 
 
53
(I've pasted it in the body of this message)
 
54
 
 
55
Aaron
 
56
 
 
57
# Bazaar merge directive format 1\r
 
58
# revision_id: example:
 
59
# target_branch: http://example.com
 
60
# testament_sha1: sha
 
61
# timestamp: 1970-01-01 00:09:33 +0002
 
62
# source_branch: http://example.org
 
63
# message: Hi mom!
 
64
#\x20
 
65
booga""".splitlines(True)
 
66
 
 
67
 
 
68
class TestMergeDirective(tests.TestCase):
 
69
 
 
70
    def test_merge_source(self):
 
71
        time = 500.0
 
72
        timezone = 5
 
73
        self.assertRaises(errors.NoMergeSource, merge_directive.MergeDirective,
 
74
            'example:', 'sha', time, timezone, 'http://example.com')
 
75
        self.assertRaises(errors.NoMergeSource, merge_directive.MergeDirective,
 
76
            'example:', 'sha', time, timezone, 'http://example.com',
 
77
            patch_type='diff')
 
78
        merge_directive.MergeDirective('example:', 'sha', time, timezone,
 
79
            'http://example.com', source_branch='http://example.org')
 
80
        md = merge_directive.MergeDirective('null:', 'sha', time, timezone,
 
81
            'http://example.com', patch='blah', patch_type='bundle')
 
82
        self.assertIs(None, md.source_branch)
 
83
        md2 = merge_directive.MergeDirective('null:', 'sha', time, timezone,
 
84
            'http://example.com', patch='blah', patch_type='bundle',
 
85
            source_branch='bar')
 
86
        self.assertEqual('bar', md2.source_branch)
 
87
 
 
88
    def test_require_patch(self):
 
89
        time = 500.0
 
90
        timezone = 5
 
91
        self.assertRaises(errors.PatchMissing, merge_directive.MergeDirective,
 
92
            'example:', 'sha', time, timezone, 'http://example.com',
 
93
            patch_type='bundle')
 
94
        md = merge_directive.MergeDirective('example:', 'sha1', time, timezone,
 
95
            'http://example.com', source_branch="http://example.org",
 
96
            patch='', patch_type='diff')
 
97
        self.assertEqual(md.patch, '')
 
98
 
 
99
    def test_serialization(self):
 
100
        time = 501
 
101
        timezone = 72
 
102
        md = merge_directive.MergeDirective('example:', 'sha', time, timezone,
 
103
            'http://example.com', patch='booga', patch_type='bundle')
 
104
        self.assertEqualDiff(OUTPUT1, ''.join(md.to_lines()))
 
105
        md = merge_directive.MergeDirective('example:', 'sha', time, timezone,
 
106
            'http://example.com', source_branch="http://example.org",
 
107
            patch='booga', patch_type='diff', message="Hi mom!")
 
108
        self.assertEqualDiff(OUTPUT2, ''.join(md.to_lines()))
 
109
 
 
110
    def test_deserialize_junk(self):
 
111
        self.assertRaises(errors.NotAMergeDirective,
 
112
                          merge_directive.MergeDirective.from_lines, 'lala')
 
113
 
 
114
    def test_deserialize_leading_junk(self):
 
115
        md = merge_directive.MergeDirective.from_lines(INPUT1)
 
116
        self.assertEqual('example:', md.revision_id)
 
117
        self.assertEqual('sha', md.testament_sha1)
 
118
        self.assertEqual('http://example.com', md.target_branch)
 
119
        self.assertEqual('http://example.org', md.source_branch)
 
120
        self.assertEqual(501, md.time)
 
121
        self.assertEqual(72, md.timezone)
 
122
        self.assertEqual('booga', md.patch)
 
123
        self.assertEqual('diff', md.patch_type)
 
124
        self.assertEqual('Hi mom!', md.message)
 
125
 
 
126
    def test_roundtrip(self):
 
127
        time = 501
 
128
        timezone = 72
 
129
        md = merge_directive.MergeDirective('example:', 'sha', time, timezone,
 
130
            'http://example.com', source_branch="http://example.org",
 
131
            patch='booga', patch_type='diff')
 
132
        md2 = merge_directive.MergeDirective.from_lines(md.to_lines())
 
133
        self.assertEqual('example:', md2.revision_id)
 
134
        self.assertIsInstance(md2.revision_id, str)
 
135
        self.assertEqual('sha', md2.testament_sha1)
 
136
        self.assertEqual('http://example.com', md2.target_branch)
 
137
        self.assertEqual('http://example.org', md2.source_branch)
 
138
        self.assertEqual(time, md2.time)
 
139
        self.assertEqual(timezone, md2.timezone)
 
140
        self.assertEqual('diff', md2.patch_type)
 
141
        self.assertEqual('booga', md2.patch)
 
142
        self.assertEqual(None, md2.message)
 
143
        md.patch = "# Bazaar revision bundle v0.9\n#\n"
 
144
        md.message = "Hi mom!"
 
145
        md3 = merge_directive.MergeDirective.from_lines(md.to_lines())
 
146
        self.assertEqual("# Bazaar revision bundle v0.9\n#\n", md3.patch)
 
147
        self.assertEqual("bundle", md3.patch_type)
 
148
        self.assertContainsRe(md3.to_lines()[0],
 
149
            '^# Bazaar merge directive format ')
 
150
        self.assertEqual("Hi mom!", md3.message)
 
151
        md3.patch_type = None
 
152
        md3.patch = None
 
153
        md4 = merge_directive.MergeDirective.from_lines(md3.to_lines())
 
154
        self.assertIs(None, md4.patch_type)
 
155
 
 
156
 
 
157
EMAIL1 = """To: pqm@example.com
 
158
From: J. Random Hacker <jrandom@example.com>
 
159
Subject: Commit of rev2a
 
160
 
 
161
# Bazaar merge directive format 1
 
162
# revision_id: rev2a
 
163
# target_branch: (.|\n)*
 
164
# testament_sha1: .*
 
165
# timestamp: 1970-01-01 00:08:56 \\+0001
 
166
# source_branch: (.|\n)*
 
167
"""
 
168
 
 
169
 
 
170
EMAIL2 = """To: pqm@example.com
 
171
From: J. Random Hacker <jrandom@example.com>
 
172
Subject: Commit of rev2a with special message
 
173
 
 
174
# Bazaar merge directive format 1
 
175
# revision_id: rev2a
 
176
# target_branch: (.|\n)*
 
177
# testament_sha1: .*
 
178
# timestamp: 1970-01-01 00:08:56 \\+0001
 
179
# source_branch: (.|\n)*
 
180
# message: Commit of rev2a with special message
 
181
"""
 
182
 
 
183
 
 
184
class TestMergeDirectiveBranch(tests.TestCaseWithTransport):
 
185
 
 
186
    def make_trees(self):
 
187
        tree_a = self.make_branch_and_tree('tree_a')
 
188
        tree_a.branch.get_config().set_user_option('email',
 
189
            'J. Random Hacker <jrandom@example.com>')
 
190
        self.build_tree_contents([('tree_a/file', 'content_a\ncontent_b\n')])
 
191
        tree_a.add('file')
 
192
        tree_a.commit('message', rev_id='rev1')
 
193
        tree_b = tree_a.bzrdir.sprout('tree_b').open_workingtree()
 
194
        branch_c = tree_a.bzrdir.sprout('branch_c').open_branch()
 
195
        tree_b.commit('message', rev_id='rev2b')
 
196
        self.build_tree_contents([('tree_a/file', 'content_a\ncontent_c\n')])
 
197
        tree_a.commit('Commit of rev2a', rev_id='rev2a')
 
198
        return tree_a, tree_b, branch_c
 
199
 
 
200
    def test_generate_patch(self):
 
201
        tree_a, tree_b, branch_c = self.make_trees()
 
202
        md2 = merge_directive.MergeDirective.from_objects(
 
203
            tree_a.branch.repository, 'rev2a', 500, 144, tree_b.branch.base,
 
204
            patch_type='diff', public_branch=tree_a.branch.base)
 
205
        self.assertNotContainsRe(md2.patch, 'Bazaar revision bundle')
 
206
        self.assertContainsRe(md2.patch, '\\+content_c')
 
207
        self.assertNotContainsRe(md2.patch, '\\+\\+\\+ b/')
 
208
        self.assertContainsRe(md2.patch, '\\+\\+\\+ file')
 
209
 
 
210
    def test_public_branch(self):
 
211
        tree_a, tree_b, branch_c = self.make_trees()
 
212
        self.assertRaises(errors.PublicBranchOutOfDate,
 
213
            merge_directive.MergeDirective.from_objects,
 
214
            tree_a.branch.repository, 'rev2a', 500, 144, tree_b.branch.base,
 
215
            public_branch=branch_c.base, patch_type='diff')
 
216
        # public branch is not checked if patch format is bundle.
 
217
        md1 = merge_directive.MergeDirective.from_objects(
 
218
            tree_a.branch.repository, 'rev2a', 500, 144, tree_b.branch.base,
 
219
            public_branch=branch_c.base)
 
220
        # public branch is provided with a bundle, despite possibly being out
 
221
        # of date, because it's not required if a bundle is present.
 
222
        self.assertEqual(md1.source_branch, branch_c.base)
 
223
        # Once we update the public branch, we can generate a diff.
 
224
        branch_c.pull(tree_a.branch)
 
225
        md3 = merge_directive.MergeDirective.from_objects(
 
226
            tree_a.branch.repository, 'rev2a', 500, 144, tree_b.branch.base,
 
227
            patch_type=None, public_branch=branch_c.base)
 
228
 
 
229
    def test_use_public_submit_branch(self):
 
230
        tree_a, tree_b, branch_c = self.make_trees()
 
231
        branch_c.pull(tree_a.branch)
 
232
        md = merge_directive.MergeDirective.from_objects(
 
233
             tree_a.branch.repository, 'rev2a', 500, 144, tree_b.branch.base,
 
234
             patch_type=None, public_branch=branch_c.base)
 
235
        self.assertEqual(md.target_branch, tree_b.branch.base)
 
236
        tree_b.branch.set_public_branch('http://example.com')
 
237
        md2 = merge_directive.MergeDirective.from_objects(
 
238
              tree_a.branch.repository, 'rev2a', 500, 144, tree_b.branch.base,
 
239
              patch_type=None, public_branch=branch_c.base)
 
240
        self.assertEqual(md2.target_branch, 'http://example.com')
 
241
 
 
242
    def test_message(self):
 
243
        tree_a, tree_b, branch_c = self.make_trees()
 
244
        md3 = merge_directive.MergeDirective.from_objects(
 
245
            tree_a.branch.repository, 'rev2a', 500, 144, tree_b.branch.base,
 
246
            patch_type=None, public_branch=branch_c.base,
 
247
            message='Merge message')
 
248
        md3.to_lines()
 
249
        self.assertIs(None, md3.patch)
 
250
        self.assertEqual('Merge message', md3.message)
 
251
 
 
252
    def test_generate_bundle(self):
 
253
        tree_a, tree_b, branch_c = self.make_trees()
 
254
        md1 = merge_directive.MergeDirective.from_objects(
 
255
            tree_a.branch.repository, 'rev2a', 500, 144, tree_b.branch.base,
 
256
            public_branch=branch_c.base)
 
257
        self.assertContainsRe(md1.patch, 'Bazaar revision bundle')
 
258
        self.assertContainsRe(md1.patch, '\\+content_c')
 
259
        self.assertNotContainsRe(md1.patch, '\\+content_a')
 
260
        self.assertContainsRe(md1.patch, '\\+content_c')
 
261
        self.assertNotContainsRe(md1.patch, '\\+content_a')
 
262
 
 
263
    def test_signing(self):
 
264
        time = 501
 
265
        timezone = 72
 
266
        class FakeBranch(object):
 
267
            def get_config(self):
 
268
                return self
 
269
            def gpg_signing_command(self):
 
270
                return 'loopback'
 
271
        md = merge_directive.MergeDirective('example:', 'sha', time, timezone,
 
272
            'http://example.com', source_branch="http://example.org",
 
273
            patch='booga', patch_type='diff')
 
274
        old_strategy = gpg.GPGStrategy
 
275
        gpg.GPGStrategy = gpg.LoopbackGPGStrategy
 
276
        try:
 
277
            signed = md.to_signed(FakeBranch())
 
278
        finally:
 
279
            gpg.GPGStrategy = old_strategy
 
280
        self.assertContainsRe(signed, '^-----BEGIN PSEUDO-SIGNED CONTENT')
 
281
        self.assertContainsRe(signed, 'example.org')
 
282
        self.assertContainsRe(signed, 'booga')
 
283
 
 
284
    def test_email(self):
 
285
        tree_a, tree_b, branch_c = self.make_trees()
 
286
        md = merge_directive.MergeDirective.from_objects(
 
287
            tree_a.branch.repository, 'rev2a', 500, 36, tree_b.branch.base,
 
288
            patch_type=None, public_branch=tree_a.branch.base)
 
289
        message = md.to_email('pqm@example.com', tree_a.branch)
 
290
        self.assertContainsRe(message.as_string(), EMAIL1)
 
291
        md.message = 'Commit of rev2a with special message'
 
292
        message = md.to_email('pqm@example.com', tree_a.branch)
 
293
        self.assertContainsRe(message.as_string(), EMAIL2)