Home | History | Annotate | Download | only in suite_scheduler
      1 #!/usr/bin/python
      2 #
      3 # Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
      4 # Use of this source code is governed by a BSD-style license that can be
      5 # found in the LICENSE file.
      6 
      7 """Unit tests for site_utils/build_event.py."""
      8 
      9 import datetime, logging, mox, unittest
     10 # driver must be imported first due to circular imports in base_event and task
     11 import driver  # pylint: disable-msg=W0611
     12 import base_event, build_event, forgiving_config_parser, manifest_versions, task
     13 
     14 
     15 class BuildEventTestBase(mox.MoxTestBase):
     16     """Base class for BuildEvent unit test classes.
     17 
     18     @var BOARD: faux board.
     19     """
     20 
     21 
     22     BOARD = 'faux_board'
     23 
     24 
     25     def setUp(self):
     26         super(BuildEventTestBase, self).setUp()
     27         self.mv = self.mox.CreateMock(manifest_versions.ManifestVersions)
     28 
     29 
     30     def CreateEvent(self):
     31         """Return an instance of the BuildEvent subclass being tested."""
     32         raise NotImplementedError()
     33 
     34 
     35     def VetBranchBuilds(self, board, branch_manifests, branch_builds):
     36         """Assert that branch_builds is derived from branch_manifests.
     37 
     38         @param board: the board to get builds for.
     39         @param branch_manifests: {(type, milestone): [manifests]}
     40         @param branch_builds: {type-or-milestone: [build-names]}
     41         """
     42         for (type, milestone), manifests in branch_manifests.iteritems():
     43             builds = []
     44             if type in task.BARE_BRANCHES:
     45                 builds = branch_builds[type]
     46                 for build in builds:
     47                     self.assertTrue(build.startswith('%s-%s' % (board, type)))
     48             else:
     49                 builds = branch_builds[milestone]
     50                 for build in builds:
     51                     self.assertTrue(build.startswith('%s-release' % board))
     52             for build, manifest in zip(builds, manifests):
     53                 self.assertTrue('R%s-%s' % (milestone, manifest) in build)
     54 
     55 
     56     def doTestGetBranchBuilds(self, board, branch_manifests):
     57         """Set expectations for and run BuildEvent.GetBranchBuildsForBoard().
     58 
     59         @param board: the board to get builds for.
     60         @param branch_manifests: {(type, milestone): [manifests]}
     61         @return per-branch builds; {type-or-milestone: [build-names]}
     62         """
     63         head = '1cedcafe'
     64         self.mv.GetCheckpoint().AndReturn(head)
     65         self.mv.ManifestsSinceRev(head, board).AndReturn(branch_manifests)
     66         self.mox.ReplayAll()
     67 
     68         event = self.CreateEvent()
     69         event.Prepare()
     70         return event.GetBranchBuildsForBoard(board)
     71 
     72 
     73 class NewBuildTest(BuildEventTestBase):
     74     """Unit tests for build_event.NewBuild."""
     75 
     76 
     77     def CreateEvent(self):
     78         return build_event.NewBuild(self.mv, False)
     79 
     80 
     81     def testMerge(self):
     82         initial_hash = '1cedcafe'
     83         self.mv.GetCheckpoint().AndReturn(initial_hash)
     84         self.mox.ReplayAll()
     85 
     86         event1 = self.CreateEvent()
     87         event1.Prepare()
     88         event1.Merge(self.CreateEvent())
     89         self.assertEquals(event1._revision, initial_hash)
     90 
     91 
     92     def testCreateFromAlwaysHandleConfig(self):
     93         """Test that creating with always_handle works as intended."""
     94         config = forgiving_config_parser.ForgivingConfigParser()
     95         section = base_event.SectionName(build_event.NewBuild.KEYWORD)
     96         config.add_section(section)
     97         config.set(section, 'always_handle', 'True')
     98         self.mox.ReplayAll()
     99 
    100         event = build_event.NewBuild.CreateFromConfig(config, self.mv)
    101         self.assertTrue(event.ShouldHandle())
    102 
    103 
    104     def testGetBranchBuilds(self):
    105         """Ensure that we handle the appearance of new branch builds."""
    106         branch_manifests = {('factory','16'): ['last16'],
    107                             ('release','17'): ['first17', 'last17']}
    108         branch_builds = self.doTestGetBranchBuilds(self.BOARD, branch_manifests)
    109         self.VetBranchBuilds(self.BOARD, branch_manifests, branch_builds)
    110 
    111 
    112 
    113     def testGetNoBranchBuilds(self):
    114         """Ensure that we tolerate the appearance of no new branch builds."""
    115         branch_builds = self.doTestGetBranchBuilds(self.BOARD, {})
    116         self.assertEquals(branch_builds, {})
    117 
    118 
    119     def testShouldHandle(self):
    120         """Ensure that we suggest Handle() iff new successful builds exist."""
    121         initial_hash = '1cedcafe'
    122         expected_hash = 'deadbeef'
    123         self.mv.GetCheckpoint().AndReturn(initial_hash)
    124         self.mv.AnyManifestsSinceRev(initial_hash).AndReturn(False)
    125         self.mv.GetCheckpoint().AndReturn(expected_hash)
    126         self.mv.AnyManifestsSinceRev(expected_hash).AndReturn(True)
    127         self.mox.ReplayAll()
    128         new_build = self.CreateEvent()
    129         new_build.Prepare()
    130         self.assertFalse(new_build.ShouldHandle())
    131         new_build.UpdateCriteria()
    132         self.assertTrue(new_build.ShouldHandle())
    133 
    134 
    135     def testRunThrough(self):
    136         """Ensure we can run through a couple passes of expected workflow."""
    137         initial_hash = '1cedcafe'
    138         expected_hash = 'deadbeef'
    139         branch_manifests = {('factory','16'): ['last16'],
    140                             ('release','17'): ['first17', 'last17']}
    141 
    142         # Expect Prepare()
    143         self.mv.GetCheckpoint().AndReturn(initial_hash)
    144 
    145         # Expect one run through.
    146         self.mv.AnyManifestsSinceRev(initial_hash).AndReturn(True)
    147         self.mv.ManifestsSinceRev(initial_hash,
    148                                   self.BOARD).AndReturn(branch_manifests)
    149         self.mv.GetCheckpoint().AndReturn(expected_hash)
    150 
    151         # Expect a second run through.
    152         self.mv.AnyManifestsSinceRev(expected_hash).AndReturn(True)
    153         self.mv.ManifestsSinceRev(expected_hash,
    154                                   self.BOARD).AndReturn(branch_manifests)
    155         self.mox.ReplayAll()
    156 
    157         new_build = self.CreateEvent()
    158 
    159         new_build.Prepare()
    160 
    161         self.assertTrue(new_build.ShouldHandle())
    162         self.assertTrue(new_build.GetBranchBuildsForBoard(self.BOARD))
    163         new_build.Handle(None, {}, self.BOARD)
    164         new_build.UpdateCriteria()
    165 
    166         self.assertTrue(new_build.ShouldHandle())
    167         self.assertTrue(new_build.GetBranchBuildsForBoard(self.BOARD))
    168         new_build.Handle(None, {}, self.BOARD)
    169 
    170 
    171 if __name__ == '__main__':
    172   unittest.main()
    173