~brz/brz-debian/byoci

« back to all changes in this revision

Viewing changes to tests/test_builder.py

  • Committer: James Westby
  • Date: 2007-02-27 20:14:25 UTC
  • mto: (104.1.5 unstable)
  • mto: This revision was merged to the branch mainline in revision 101.
  • Revision ID: jw+debian@jameswestby.net-20070227201425-vuyx5kr9j4mbe9qb
Add the start of a test suite.

  * Add the framework for a testsuite.
  * Add tests for the default builder.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
#    __init__.py -- Testsuite for builddeb builder.py
 
2
#    Copyright (C) 2007 James Westby <jw+debian@jameswestby.net>
 
3
#    
 
4
#    This file is part of bzr-builddeb.
 
5
#
 
6
#    bzr-builddeb is free software; you can redistribute it and/or modify
 
7
#    it under the terms of the GNU General Public License as published by
 
8
#    the Free Software Foundation; either version 2 of the License, or
 
9
#    (at your option) any later version.
 
10
#
 
11
#    bzr-builddeb is distributed in the hope that it will be useful,
 
12
#    but WITHOUT ANY WARRANTY; without even the implied warranty of
 
13
#    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
14
#    GNU General Public License for more details.
 
15
#
 
16
#    You should have received a copy of the GNU General Public License
 
17
#    along with bzr-builddeb; if not, write to the Free Software
 
18
#    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 
19
#
 
20
 
 
21
import commands
 
22
import os
 
23
from os.path import join
 
24
 
 
25
from debian_bundle.changelog import (Changelog, Version)
 
26
 
 
27
from bzrlib.tests import (TestCaseInTempDir,
 
28
                          TestCaseWithTransport,
 
29
                          )
 
30
 
 
31
from builder import (remove_dir,
 
32
                     remove_bzrbuilddeb_dir,
 
33
                     remove_debian_dir,
 
34
                     DebBuild,
 
35
                     )
 
36
import errors
 
37
from properties import BuildProperties
 
38
 
 
39
class TestUtil(TestCaseInTempDir):
 
40
  """Test the utility functions from builder.py."""
 
41
 
 
42
  def test_remove_dir(self):
 
43
    """Test that remove_dir correctly removes teh named directory/."""
 
44
    os.mkdir('dir1')
 
45
    os.mkdir('dir2')
 
46
    self.assert_(os.path.isdir('dir1'))
 
47
    self.assert_(os.path.isdir('dir2'))
 
48
    remove_dir('.', 'dir1')
 
49
    self.failIf(os.path.exists('dir1'))
 
50
    self.assert_(os.path.isdir('dir2'))
 
51
 
 
52
  def test_remove_dir_in_dir(self):
 
53
    """Test that remove_dir correctly removes a subdir."""
 
54
    os.mkdir('dir1')
 
55
    os.mkdir('dir2')
 
56
    self.assert_(os.path.isdir('dir1'))
 
57
    self.assert_(os.path.isdir('dir2'))
 
58
    os.mkdir(join('dir1', 'subdir1'))
 
59
    os.mkdir(join('dir1', 'subdir2'))
 
60
    os.mkdir(join('dir2', 'subdir1'))
 
61
 
 
62
    self.assert_(os.path.isdir(join('dir1', 'subdir1')))
 
63
    self.assert_(os.path.isdir(join('dir1', 'subdir2')))
 
64
    self.assert_(os.path.isdir(join('dir2', 'subdir1')))
 
65
    remove_dir('dir1', 'subdir1')
 
66
    self.failIf(os.path.exists(join('dir1', 'subdir1')))
 
67
    self.assert_(os.path.isdir(join('dir1', 'subdir2')))
 
68
    self.assert_(os.path.isdir(join('dir2', 'subdir1')))
 
69
 
 
70
  def test_remove_dir_works_on_non_empty_dirs(self):
 
71
    """Test that t can remove a non empty dir"""
 
72
    os.mkdir('dir1')
 
73
    os.mkdir(join('dir1', 'subdir1'))
 
74
    self.assert_(os.path.isdir(join('dir1', 'subdir1')))
 
75
    remove_dir('.', 'dir1')
 
76
    self.failIf(os.path.exists('dir1'))
 
77
 
 
78
  def test_remove_dir_copes_with_no_dir(self):
 
79
    """Test that it doesn't fail if the path doesn't exist."""
 
80
    self.failIf(os.path.exists('dir1'))
 
81
    remove_dir('.', 'dir1')
 
82
 
 
83
  def test_remove_dir_no_remove_file(self):
 
84
    """Test that it doesn't remove files"""
 
85
    file = open('file', 'w')
 
86
    file.write('test\n')
 
87
    file.close()
 
88
    self.assert_(os.path.exists('file'))
 
89
    remove_dir('.', 'file')
 
90
    self.assert_(os.path.exists('file'))
 
91
 
 
92
  def test_remove_dir_no_remove_symlink(self):
 
93
    """Test that it neither removes the symlink or the target."""
 
94
    os.mkdir('dir1')
 
95
    os.symlink('dir1', 'link1')
 
96
    self.assert_(os.path.exists('dir1'))
 
97
    self.assert_(os.path.exists('link1'))
 
98
    remove_dir(',', 'link1')
 
99
    self.assert_(os.path.exists('dir1'))
 
100
    self.assert_(os.path.exists('link1'))
 
101
 
 
102
  def test_remove_bzr_builddeb_dir(self):
 
103
    """Tests that a dir named .bzr-buiddeb is removed"""
 
104
    os.mkdir('.bzr-builddeb')
 
105
    self.assert_(os.path.exists('.bzr-builddeb'))
 
106
    remove_bzrbuilddeb_dir('.')
 
107
    self.failIf(os.path.exists('.bzr-builddeb'))
 
108
 
 
109
  def test_remove_debian_dir(self):
 
110
    """Tests that a dir named debian/ is removed"""
 
111
    os.mkdir('debian')
 
112
    self.assert_(os.path.exists('debian'))
 
113
    remove_debian_dir('.')
 
114
    self.failIf(os.path.exists('debian'))
 
115
 
 
116
class BuilderTestCase(TestCaseWithTransport):
 
117
  """A class that helps with the testing of builders."""
 
118
 
 
119
  package_name = 'test'
 
120
  package_version = '0.1'
 
121
 
 
122
  def __init__(self, *args, **kwargs):
 
123
    self.basedir = 'base'
 
124
    self.build_dir = join(self.basedir, 'build')
 
125
    self.orig_dir = join(self.basedir, 'orig')
 
126
    self.result_dir = join(self.basedir, 'result')
 
127
    self.branch_dir = join(self.basedir, 'branch')
 
128
    self.source_dir = join(self.build_dir,
 
129
                           self.package_name + '-' + self.package_version)
 
130
    self.tarball_name = self.package_name + '_' + self.package_version + \
 
131
                        '.orig.tar.gz'
 
132
    super(BuilderTestCase, self).__init__(*args, **kwargs)
 
133
 
 
134
  def make_properties(self, changelog, larstiq):
 
135
    return BuildProperties(changelog, self.build_dir, self.orig_dir, larstiq)
 
136
 
 
137
  def change_to_branch_dir(self):
 
138
    os.chdir(self.branch_dir)
 
139
 
 
140
  def _make_branch(self):
 
141
    os.mkdir(self.basedir)
 
142
    tree = self.make_branch_and_tree(self.branch_dir)
 
143
    branch = tree.branch
 
144
    return (tree, branch)
 
145
 
 
146
  def build_tree(self, files, *args, **kwargs):
 
147
    #divert in to base
 
148
    newfiles = []
 
149
    for filename in files:
 
150
      newfiles.append(join('base', filename))
 
151
    super(BuilderTestCase, self).build_tree(newfiles, *args, **kwargs)
 
152
 
 
153
  def make_orig_tarball(self):
 
154
    os.mkdir(self.orig_dir)
 
155
    tarball = join(self.orig_dir, self.tarball_name)
 
156
    f = open(tarball, 'wb')
 
157
    f.close()
 
158
 
 
159
  def make_changelog(self, version=None):
 
160
    if version is None:
 
161
      version = self.package_version
 
162
    c = Changelog()
 
163
    c.new_block()
 
164
    c.version = Version(version)
 
165
    c.package = self.package_name
 
166
    c.distributions = 'unstable'
 
167
    c.urgency = 'low'
 
168
    c.author = 'James Westby <jw+debian@jameswestby.net>'
 
169
    c.date = 'The,  3 Aug 2006 19:16:22 +0100'
 
170
    c.add_change('')
 
171
    c.add_change('  *  test build')
 
172
    c.add_change('')
 
173
    return c
 
174
 
 
175
  def write_changelog(self, changelog, filename):
 
176
    f = open(filename, 'w')
 
177
    c.write_to_open_file(f)
 
178
    f.close()
 
179
 
 
180
  def get_arch(self):
 
181
    status, arch = commands.getstatusoutput(
 
182
        'dpkg-architecture -qDEB_BUILD_ARCH')
 
183
    if status > 0:
 
184
      self.fail("Couldn't discover arch")
 
185
    return arch
 
186
 
 
187
  def changes_filename(self):
 
188
    arch = self.get_arch()
 
189
    changesfilename = "%s_%s_%s.changes" % (self.package_name,
 
190
                                            self.package_version, arch)
 
191
    return changesfilename
 
192
 
 
193
  def make_changes_file(self):
 
194
    os.mkdir(self.build_dir)
 
195
    arch = self.get_arch()
 
196
    changesfilename = self.changes_filename()
 
197
    changesfile = open(join(self.build_dir, changesfilename), 'wb')
 
198
    changesfile.write("""Format: 1.7
 
199
Date: Wed, 31 Jan 2007 20:15:42 +0000
 
200
Source: """)
 
201
    changesfile.write(self.package_name)
 
202
    changesfile.write("\nBinary: %s" % self.package_name)
 
203
    changesfile.write("\nArchitecture: source %s" % arch)
 
204
    changesfile.write("\nVersion: %s" % self.package_version)
 
205
    changesfile.write("""
 
206
Distribution: experimental
 
207
Urgency: low
 
208
Maintainer: Noone <noone@nowhere.con>
 
209
Changed-By: Noone <noone@nowhere.com>
 
210
Description:
 
211
 test - A test package
 
212
Changes:""")
 
213
    changesfile.write("\n %s (%s) experimental; urgency=low" % (
 
214
                                self.package_name, self.package_version))
 
215
    changesfile.write("""
 
216
 .
 
217
   * A change.
 
218
Files:
 
219
 7fee96643187b7d498ca2ef32aea1b3c 441 devel optional """)
 
220
    changesfile.write("%s_%s.dsc\n" % (self.package_name, self.package_version))
 
221
    changesfile.write(" 3808bdf49220a86f097316207f8a7fce 24786 devel optional ")
 
222
    changesfile.write("%s_%s.tar.gz\n" % (self.package_name,
 
223
                                        self.package_version))
 
224
    changesfile.write(" 645fb698444a226c55e9af861604d643 29574 devel optional ")
 
225
    changesfile.write("%s_%s_%s.deb\n" % (self.package_name,
 
226
                                        self.package_version, arch))
 
227
    changesfile.close()
 
228
 
 
229
  def get_result_filenames(self):
 
230
    """Return a list of the filenames that a build might produce."""
 
231
    arch = self.get_arch()
 
232
    dsc = "%s_%s.dsc" % (self.package_name, self.package_version)
 
233
    tar = "%s_%s.tar.gz" % (self.package_name, self.package_version)
 
234
    deb = "%s_%s_%s.deb" % (self.package_name, self.package_version, arch)
 
235
    return [dsc, tar, deb]
 
236
 
 
237
  def make_result_files(self):
 
238
    """Make the files to go along with the .changes file."""
 
239
    for filename in self.get_result_filenames():
 
240
      f = open(join(self.build_dir, filename), 'wb')
 
241
      f.close()
 
242
 
 
243
class TestDefaultBuilder(BuilderTestCase):
 
244
  """Test the default builder (full source, non-native)"""
 
245
 
 
246
  def get_builder(self, version=None, wt=None):
 
247
    """Returns a builder set up for this type."""
 
248
    if wt is None:
 
249
      (wt, branch) = self._make_branch()
 
250
    changelog = self.make_changelog(version=version)
 
251
    properties = self.make_properties(changelog, False)
 
252
    return DebBuild(properties, wt)
 
253
 
 
254
  def test_prepare_creates_build_dir(self):
 
255
    """Test that the build dir is created correctly."""
 
256
    builder = self.get_builder()
 
257
    self.failIfExists(self.build_dir)
 
258
    builder.prepare(False)
 
259
    self.failUnlessExists(self.build_dir)
 
260
 
 
261
  def test_prepare_allows_build_dir_to_exist(self):
 
262
    """Test that prepare doen't fall over if the build dir exists."""
 
263
    builder = self.get_builder()
 
264
    os.mkdir(self.build_dir)
 
265
    self.failUnlessExists(self.build_dir)
 
266
    builder.prepare(False)
 
267
    self.failUnlessExists(self.build_dir)
 
268
 
 
269
  def test_prepare_purges_the_source_dir(self):
 
270
    """Test that the source dir is purged if not keep_source_dir."""
 
271
    builder = self.get_builder()
 
272
    os.mkdir(self.build_dir)
 
273
    os.mkdir(self.source_dir)
 
274
    self.failUnlessExists(self.source_dir)
 
275
    builder.prepare(False)
 
276
    self.failIfExists(self.source_dir)
 
277
 
 
278
  def test_prepare_keeps_the_source_dir(self):
 
279
    """Test that the source dir is kept if keep_source_dir."""
 
280
    builder = self.get_builder()
 
281
    os.mkdir(self.build_dir)
 
282
    os.mkdir(self.source_dir)
 
283
    self.failUnlessExists(self.source_dir)
 
284
    builder.prepare(True)
 
285
    self.failUnlessExists(self.source_dir)
 
286
 
 
287
  def test_prepare_errors_on_keep_source_dir_and_it_doesnt_exist(self):
 
288
    """Test that there is an exception if keep_source_dir and there is none."""
 
289
    builder = self.get_builder()
 
290
    self.failIfExists(self.source_dir)
 
291
    self.assertRaises(errors.NoSourceDirError, builder.prepare, True)
 
292
    self.failIfExists(self.source_dir)
 
293
 
 
294
  def test__tarball_name_native(self):
 
295
    """Test the correct upstream tarball name for native package."""
 
296
    builder = self.get_builder()
 
297
    self.assertEqual(builder._tarball_name(),
 
298
                     self.package_name+'_'+self.package_version+'.orig.tar.gz')
 
299
 
 
300
  def test__tarball_name_non_native(self):
 
301
    """Test the correct upstream tarball name for non-native package."""
 
302
    version = '0.1-1'
 
303
    builder = self.get_builder(version)
 
304
    self.assertEqual(builder._tarball_name(),
 
305
                     self.package_name+'_0.1.orig.tar.gz')
 
306
 
 
307
  def test__find_tarball_present(self):
 
308
    """Test that _find_tarball returns the correct path if present."""
 
309
    builder = self.get_builder()
 
310
    tarball = join(self.orig_dir, builder._tarball_name())
 
311
    self.make_orig_tarball()
 
312
    self.failUnlessExists(tarball)
 
313
    self.assertEqual(builder._find_tarball(), tarball)
 
314
 
 
315
  def test__find_tarball_no_orig_dir(self):
 
316
    """Test that an exception is raised it the orig dir is not present."""
 
317
    builder = self.get_builder()
 
318
    self.failIfExists(self.orig_dir)
 
319
    self.assertRaises(errors.DebianError, builder._find_tarball)
 
320
 
 
321
  def test__find_tarball_not_exists(self):
 
322
    """Test that an exception is raised if the tarball is not found."""
 
323
    builder = self.get_builder()
 
324
    os.mkdir(self.orig_dir)
 
325
    tarball = join(self.orig_dir, builder._tarball_name())
 
326
    self.failIfExists(tarball)
 
327
    self.assertRaises(errors.DebianError, builder._find_tarball)
 
328
 
 
329
  def test_export_copies_tarball(self):
 
330
    """Test that the tarball is copied in to the build dir."""
 
331
    builder = self.get_builder()
 
332
    self.make_orig_tarball()
 
333
    builder.prepare()
 
334
    builder.export()
 
335
    self.failUnlessExists(join(self.build_dir, self.tarball_name))
 
336
 
 
337
  def test_export_creates_source_dir(self):
 
338
    """Test that the source dir is created on export."""
 
339
    builder = self.get_builder()
 
340
    self.make_orig_tarball()
 
341
    builder.prepare()
 
342
    builder.export()
 
343
    self.failUnlessExists(self.source_dir)
 
344
 
 
345
  def test_export_has_correct_contents_in_source_dir(self):
 
346
    """Test that the exported source dir has the correct contents."""
 
347
    wt = self.make_branch_and_tree(self.basedir)
 
348
    self.build_tree(['a', 'b'])
 
349
    wt.add(['a', 'b'])
 
350
    wt.commit('commit one')
 
351
    self.build_tree(['c', 'd'])
 
352
    wt.add(['c'])
 
353
    wt.remove(['b'])
 
354
    builder = self.get_builder(wt=wt)
 
355
    self.make_orig_tarball()
 
356
    builder.prepare()
 
357
    builder.export()
 
358
    self.failUnlessExists(join(self.source_dir, 'a'))
 
359
    self.failIfExists(join(self.source_dir, 'b'))
 
360
    self.failUnlessExists(join(self.source_dir, 'c'))
 
361
    self.failIfExists(join(self.source_dir, 'd'))
 
362
 
 
363
  def test_export_removes_builddeb_dir(self):
 
364
    """Test that the builddeb dir is removed from the export."""
 
365
    wt = self.make_branch_and_tree(self.basedir)
 
366
    files = ['a', '.bzr-builddeb/', '.bzr-builddeb/default.conf']
 
367
    self.build_tree(files)
 
368
    wt.add(files)
 
369
    wt.commit('commit one')
 
370
    builder = self.get_builder(wt=wt)
 
371
    self.make_orig_tarball()
 
372
    builder.prepare()
 
373
    builder.export()
 
374
    self.failUnlessExists(join(self.source_dir, 'a'))
 
375
    self.failIfExists(join(self.source_dir, '.bzr-builddeb'))
 
376
 
 
377
  def test_build(self):
 
378
    """Test that the build command is run correctly."""
 
379
    builder = self.get_builder()
 
380
    self.make_orig_tarball()
 
381
    builder.prepare()
 
382
    builder.export()
 
383
    self.failIfExists(join(self.source_dir, 'built'))
 
384
    builder.build('touch built')
 
385
    self.failUnlessExists(join(self.source_dir, 'built'))
 
386
 
 
387
  def test_build_fails(self):
 
388
    """Test that a failing build raises an error."""
 
389
    builder = self.get_builder()
 
390
    self.make_orig_tarball()
 
391
    builder.prepare()
 
392
    builder.export()
 
393
    self.assertRaises(errors.BuildFailedError, builder.build, 'false')
 
394
 
 
395
  def test_clean(self):
 
396
    """Test that clean removes the source dir."""
 
397
    builder = self.get_builder()
 
398
    os.mkdir(self.build_dir)
 
399
    os.mkdir(self.source_dir)
 
400
    # make it non-empty for good measure
 
401
    f = open(join(self.source_dir, 'file'), 'wb')
 
402
    f.close()
 
403
    self.failUnlessExists(self.source_dir)
 
404
    builder.clean()
 
405
    self.failIfExists(self.source_dir)
 
406
 
 
407
  def test_move_result_creates_result_dir(self):
 
408
    """Test that move_result creates the result directory."""
 
409
    builder = self.get_builder()
 
410
    self.make_changes_file()
 
411
    self.make_result_files()
 
412
    self.failIfExists(self.result_dir)
 
413
    builder.move_result(self.result_dir)
 
414
    self.failUnlessExists(self.result_dir)
 
415
 
 
416
  def test_move_result_allows_existing_result_dir(self):
 
417
    """Test that move_result doesn't choke if the result directory exists."""
 
418
    builder = self.get_builder()
 
419
    self.make_changes_file()
 
420
    self.make_result_files()
 
421
    os.mkdir(self.result_dir)
 
422
    self.failUnlessExists(self.result_dir)
 
423
    builder.move_result(self.result_dir)
 
424
    self.failUnlessExists(self.result_dir)
 
425
 
 
426
  def test_move_result_moves_files(self):
 
427
    """Test that the move_result places the expected files in the result dir"""
 
428
    builder = self.get_builder()
 
429
    self.make_changes_file()
 
430
    self.make_result_files()
 
431
    builder.move_result(self.result_dir)
 
432
    self.failUnlessExists(join(self.result_dir, self.changes_filename()))
 
433
    for filename in self.get_result_filenames():
 
434
      self.failUnlessExists(join(self.result_dir, filename))
 
435
 
 
436
  def test_move_result_errors_on_missing_changes_file(self):
 
437
    """Test that the move_result errors if the changes file is missing."""
 
438
    builder = self.get_builder()
 
439
    self.assertRaises(errors.DebianError, builder.move_result, self.result_dir)
 
440
 
 
441
  def test_move_result_errors_on_missing_result_file(self):
 
442
    """Test that the move_result errors if one of the files is missing."""
 
443
    builder = self.get_builder()
 
444
    self.make_changes_file()
 
445
    self.assertRaises(errors.DebianError, builder.move_result, self.result_dir)
 
446