Chromium Code Reviews| Index: scripts/master/unittests/master_utils_test.py |
| diff --git a/scripts/master/unittests/master_utils_test.py b/scripts/master/unittests/master_utils_test.py |
| index 6ac5a3031ddb8662898c31bd9b4c43ade68a27df..b02149e6420c25247a26fd338ab98ec9d5346841 100755 |
| --- a/scripts/master/unittests/master_utils_test.py |
| +++ b/scripts/master/unittests/master_utils_test.py |
| @@ -14,6 +14,12 @@ from buildbot.process.properties import Properties |
| from master import master_utils |
| +# Use this instead of random.choice on function return for determinism |
| +# and to check the full choice range. |
| +def mock_random_choice(iterable): |
| + return list(iterable) |
| + |
| + |
| class MasterUtilsTest(unittest.TestCase): |
| def testPartition(self): |
| @@ -46,28 +52,56 @@ class PreferredBuilderNextSlaveFuncTest(unittest.TestCase): |
| builder3 = MockBuilder('builder3') |
| slaves = [ |
| - MockSlaveBuilder('slave1', {'preferred_builder': 'builder1'}), |
| - MockSlaveBuilder('slave2', {'preferred_builder': 'builder2'}), |
| - MockSlaveBuilder('slave3', {'preferred_builder': 'builder3'}), |
| + MockSlaveBuilder('s1', {'preferred_builder': 'builder1'}), |
| + MockSlaveBuilder('s2', {'preferred_builder': 'builder2'}), |
| + MockSlaveBuilder('s3', {'preferred_builder': 'builder3'}), |
| + MockSlaveBuilder('s4', {'preferred_builder': 'builder1'}), |
| + MockSlaveBuilder('s5', {'preferred_builder': 'builder2'}), |
| + MockSlaveBuilder('s6', {'preferred_builder': 'builder3'}), |
| + # Fall-over pool with no preference. |
| + MockSlaveBuilder('s7', {'preferred_builder': None}), |
| + MockSlaveBuilder('s8', {'preferred_builder': None}), |
| ] |
| - f = master_utils.PreferredBuilderNextSlaveFunc() |
| - self.assertEqual('slave1', f(builder1, slaves).name) |
| - self.assertEqual('slave2', f(builder2, slaves).name) |
| - self.assertEqual('slave3', f(builder3, slaves).name) |
| + f = lambda builder, slaves: ( |
| + set([s.name for s in master_utils.PreferredBuilderNextSlaveFunc( |
| + mock_random_choice)(builder, slaves)])) |
| + self.assertEqual(set(['s1', 's4']), f(builder1, slaves)) |
| + self.assertEqual(set(['s2', 's5']), f(builder2, slaves)) |
| + self.assertEqual(set(['s3', 's6']), f(builder3, slaves)) |
| # Remove slave 3. |
| del slaves[2] |
| - # When there is no slave that matches preferred_builder, |
| - # any slave builder might be chosen. |
| - self.assertTrue(f(builder3, slaves).name in ['slave1', 'slave2']) |
| + # There's still a preferred slave left. |
| + self.assertEqual(set(['s6']), f(builder3, slaves)) |
| + |
| + # Remove slave 6. |
| + del slaves[4] |
|
tandrii(chromium)
2016/10/21 10:39:17
def remove(slaves):
iterate and find and remove
Michael Achenbach
2016/10/21 13:17:43
Done.
|
| + |
| + # No preferred slave. Slave will be choosen from fall-over pool (i.e. |
| + # slaves with no preference). |
| + self.assertEqual(set(['s7', 's8']), f(builder3, slaves)) |
| + |
| + # Remove slaves 7 and 8. |
| + del slaves[4] |
| + del slaves[4] |
| + |
| + # When the fall-over pool is depleted, slaves will be chosen from slave |
| + # groups with most capacity (here: all the remaining ones are equal). |
| + self.assertEqual(set(['s1', 's2', 's4', 's5']), f(builder3, slaves)) |
| + |
| + # Remove slave 1: |
| + del slaves[0] |
| + |
| + # Now only slaves preferring builder2 have most capacity. |
| + self.assertEqual(set(['s2', 's5']), f(builder3, slaves)) |
| def testNextSlaveEmpty(self): |
| builder = MockBuilder('builder') |
| slaves = [] |
| - f = master_utils.PreferredBuilderNextSlaveFunc() |
| + f = master_utils.PreferredBuilderNextSlaveFunc(mock_random_choice) |
| self.assertIsNone(f(builder, slaves)) |