binary_search_tool_tester.py revision 47de616141aac91d6d3e15e80591d1aca8dffc57
1#!/usr/bin/python2
2
3# Copyright 2012 Google Inc. All Rights Reserved.
4"""Tests for bisecting tool."""
5
6from __future__ import print_function
7
8__author__ = 'shenhan@google.com (Han Shen)'
9
10import os
11import random
12import sys
13import unittest
14
15from utils import command_executer
16from binary_search_tool import binary_search_state
17
18import common
19import gen_obj
20
21
22class BisectingUtilsTest(unittest.TestCase):
23  """Tests for bisecting tool."""
24
25  def setUp(self):
26    """Generate [100-1000] object files, and 1-5% of which are bad ones."""
27    obj_num = random.randint(100, 1000)
28    bad_obj_num = random.randint(obj_num / 100, obj_num / 20)
29    if bad_obj_num == 0:
30      bad_obj_num = 1
31    gen_obj.Main(['--obj_num', str(obj_num), '--bad_obj_num', str(bad_obj_num)])
32
33    with open('./installed', 'w'):
34      pass
35
36    try:
37      os.remove(binary_search_state.STATE_FILE)
38    except OSError:
39      pass
40
41  def tearDown(self):
42    """Cleanup temp files."""
43    os.remove(common.OBJECTS_FILE)
44    os.remove(common.WORKING_SET_FILE)
45    print('Deleted "{0}" and "{1}"'.format(common.OBJECTS_FILE,
46                                           common.WORKING_SET_FILE))
47    try:
48      os.remove('./installed')
49      os.remove(os.readlink(binary_search_state.STATE_FILE))
50      os.remove(binary_search_state.STATE_FILE)
51    except OSError:
52      pass
53
54  def runTest(self):
55    args = ['--get_initial_items', './gen_init_list.py', '--switch_to_good',
56            './switch_to_good.py', '--switch_to_bad', './switch_to_bad.py',
57            '--test_script', './is_good.py', '--prune', '--file_args']
58    binary_search_state.Main(args)
59    self.check_output()
60
61  def test_install_script(self):
62    args = ['--get_initial_items', './gen_init_list.py', '--switch_to_good',
63            './switch_to_good.py', '--switch_to_bad', './switch_to_bad.py',
64            '--test_script', './is_good.py', '--prune', '--file_args']
65
66    os.remove('./installed')
67    with self.assertRaises(AssertionError):
68      binary_search_state.Main(args)
69
70    args += ['--install_script', './install.py']
71    binary_search_state.Main(args)
72    self.check_output()
73
74  def test_bad_install_script(self):
75    args = ['--get_initial_items', './gen_init_list.py', '--switch_to_good',
76            './switch_to_good.py', '--switch_to_bad', './switch_to_bad.py',
77            '--test_script', './is_good.py', '--prune', '--file_args',
78            '--install_script', './install_bad.py']
79    with self.assertRaises(AssertionError):
80      binary_search_state.Main(args)
81
82  def test_bad_save_state(self):
83    state_file = binary_search_state.STATE_FILE
84    hidden_state_file = os.path.basename(binary_search_state.HIDDEN_STATE_FILE)
85
86    with open(state_file, 'w') as f:
87      f.write('test123')
88
89    bss = binary_search_state.MockBinarySearchState()
90    with self.assertRaises(binary_search_state.Error):
91      bss.SaveState()
92
93    with open(state_file, 'r') as f:
94      self.assertEquals(f.read(), 'test123')
95
96    os.remove(state_file)
97
98    # Cleanup generated save state that has no symlink
99    files = os.listdir(os.getcwd())
100    save_states = [x for x in files if x.startswith(hidden_state_file)]
101    _ = [os.remove(x) for x in save_states]
102
103  def test_save_state(self):
104    state_file = binary_search_state.STATE_FILE
105
106    bss = binary_search_state.MockBinarySearchState()
107    bss.SaveState()
108    self.assertTrue(os.path.exists(state_file))
109    first_state = os.readlink(state_file)
110
111    bss.SaveState()
112    second_state = os.readlink(state_file)
113    self.assertTrue(os.path.exists(state_file))
114    self.assertTrue(second_state != first_state)
115    self.assertFalse(os.path.exists(first_state))
116
117    bss.RemoveState()
118    self.assertFalse(os.path.islink(state_file))
119    self.assertFalse(os.path.exists(second_state))
120
121  def test_load_state(self):
122    test_items = [1, 2, 3, 4, 5]
123
124    bss = binary_search_state.MockBinarySearchState()
125    bss.all_items = test_items
126    bss.SaveState()
127
128    bss = None
129
130    bss2 = binary_search_state.MockBinarySearchState.LoadState()
131    self.assertEquals(bss2.all_items, test_items)
132
133  def test_tmp_cleanup(self):
134    bss = binary_search_state.MockBinarySearchState(
135        get_initial_items='echo "0\n1\n2\n3"', switch_to_good='./switch_tmp.py',
136        file_args=True)
137    bss.SwitchToGood(['0', '1', '2', '3'])
138
139    tmp_file = None
140    with open('tmp_file', 'r') as f:
141      tmp_file = f.read()
142    os.remove('tmp_file')
143
144    self.assertFalse(os.path.exists(tmp_file))
145    ws = common.ReadWorkingSet()
146    for i in range(3):
147      self.assertEquals(ws[i], 42)
148
149  def check_output(self):
150    _, out, _ = command_executer.GetCommandExecuter().RunCommandWOutput(
151        'tail -n 10 logs/binary_search_tool_tester.py.out')
152    ls = out.splitlines()
153    for l in ls:
154      t = l.find('Bad items are: ')
155      if t > 0:
156        bad_ones = l[(t + len('Bad items are: ')):].split()
157        objects_file = common.ReadObjectsFile()
158        for b in bad_ones:
159          self.assertEqual(objects_file[int(b)], 1)
160
161
162def Main(argv):
163  num_tests = 2
164  if len(argv) > 1:
165    num_tests = int(argv[1])
166
167  suite = unittest.TestSuite()
168  for _ in range(0, num_tests):
169    suite.addTest(BisectingUtilsTest())
170  suite.addTest(BisectingUtilsTest('test_install_script'))
171  suite.addTest(BisectingUtilsTest('test_bad_install_script'))
172  suite.addTest(BisectingUtilsTest('test_bad_save_state'))
173  suite.addTest(BisectingUtilsTest('test_save_state'))
174  suite.addTest(BisectingUtilsTest('test_load_state'))
175  suite.addTest(BisectingUtilsTest('test_tmp_cleanup'))
176  runner = unittest.TextTestRunner()
177  runner.run(suite)
178
179
180if __name__ == '__main__':
181  Main(sys.argv)
182