1#!/usr/bin/python
2#
3# Copyright (c) 2013 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
7import datetime, unittest
8
9import mox
10
11import common
12# This must come before the import of complete_failures in order to use the
13# in memory database.
14from autotest_lib.frontend import setup_django_readonly_environment
15from autotest_lib.frontend import setup_test_environment
16from autotest_lib.frontend.health import passing_experimental
17from autotest_lib.frontend.afe import models as afe_models
18from django import test
19
20
21# datetime.datetime is all C code and so cannot be mocked out in a normal
22# fashion.
23class MockDatetime(datetime.datetime):
24    """Used to mock out parts of datetime.datetime."""
25    pass
26
27
28class GetExperimentalTestsTests(test.TestCase):
29    """Tests the get_experimetnal_tests function."""
30
31    def setUp(self):
32        super(GetExperimentalTestsTests, self).setUp()
33        setup_test_environment.set_up()
34
35
36    def tearDown(self):
37        setup_test_environment.tear_down()
38        super(GetExperimentalTestsTests, self).tearDown()
39
40
41    def test_returns_tests_marked_experimental(self):
42        """Test that tests marked as experimental are returned."""
43        test = afe_models.Test(name='test', test_type=0,
44                               experimental=True)
45        test.save()
46
47        result = passing_experimental.get_experimental_tests()
48
49        self.assertEqual(result, set(['test']))
50
51
52    def test_does_not_return_tests_not_marked_experimental(self):
53        """Test that tests not marked as experimetnal are not returned."""
54        test = afe_models.Test(name='test', test_type=0,
55                               experimental=False)
56        test.save()
57
58        result = passing_experimental.get_experimental_tests()
59
60        self.assertEqual(result, set())
61
62
63class FindLongPassingTestsTests(mox.MoxTestBase, test.TestCase):
64    """Tests the find_long_passing_tests function."""
65    def setUp(self):
66        super(FindLongPassingTestsTests, self).setUp()
67        self.mox.StubOutWithMock(MockDatetime, 'today')
68        self._datetime = datetime.datetime
69        datetime.datetime = MockDatetime
70        self._orig_since_failure = passing_experimental._MIN_DAYS_SINCE_FAILURE
71        self._orig_since_pass = passing_experimental._MAX_DAYS_SINCE_LAST_PASS
72
73
74    def tearDown(self):
75        passing_experimental._MAX_DAYS_SINCE_LAST_PASS = self._orig_since_pass
76        passing_experimental._MIN_DAYS_SINCE_FAILURE = self._orig_since_failure
77        datetime.datetime = self._datetime
78        super(FindLongPassingTestsTests, self).tearDown()
79
80
81    def test_do_not_return_tests_that_have_failed_recently(self):
82        """Test that tests that have failed recently are not returned."""
83        passing_experimental._MIN_DAYS_SINCE_FAILURE = 10
84        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
85        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
86
87        pass_times = {'test': self._datetime(2013, 3, 12)}
88        fail_times = {'test': self._datetime(2013, 3, 13)}
89        valid_tests = {'test'}
90
91        self.mox.ReplayAll()
92        results = passing_experimental.find_long_passing_tests(pass_times,
93                                                               fail_times,
94                                                               valid_tests)
95
96        self.assertEqual(results, set([]))
97
98
99    def test_return_tests_that_have_recent_pass_but_not_recent_failure(self):
100        """Test returning tests that have recently passed but not failed."""
101        passing_experimental._MIN_DAYS_SINCE_FAILURE = 10
102        passing_experimental._MAX_DAYS_SINCE_LAST_PASS = 10
103        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
104        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
105
106        pass_times = {'test': self._datetime(2013, 3, 12)}
107        fail_times = {'test': self._datetime(2013, 3, 1)}
108        valid_tests = {'test'}
109
110        self.mox.ReplayAll()
111        results = passing_experimental.find_long_passing_tests(pass_times,
112                                                               fail_times,
113                                                               valid_tests)
114
115        self.assertEqual(results, set(['test']))
116
117
118    def test_filter_out_tests_that_have_not_passed_recently(self):
119        """Test that tests that have not recently passed are not returned."""
120        passing_experimental._MIN_DAYS_SINCE_FAILURE = 10
121        passing_experimental._MAX_DAYS_SINCE_LAST_PASS = 10
122        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
123        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
124
125        pass_times = {'test': self._datetime(2013, 3, 1)}
126        fail_times = {'test': self._datetime(2013, 3, 1)}
127        valid_tests = {'test'}
128
129        self.mox.ReplayAll()
130        results = passing_experimental.find_long_passing_tests(pass_times,
131                                                               fail_times,
132                                                               valid_tests)
133
134        self.assertEqual(results, set([]))
135
136
137    def test_filter_out_tests_that_are_not_valid(self):
138        """Test that tests that are not valid are not returned."""
139        passing_experimental._MIN_DAYS_SINCE_FAILURE = 10
140        passing_experimental._MAX_DAYS_SINCE_LAST_PASS = 10
141        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
142        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
143
144        pass_times = {'test2': self._datetime(2013, 3, 1)}
145        fail_times = {'test2': self._datetime(2013, 3, 1)}
146        valid_tests = {'test'}
147
148        self.mox.ReplayAll()
149        results = passing_experimental.find_long_passing_tests(pass_times,
150                                                               fail_times,
151                                                               valid_tests)
152
153        self.assertEqual(results, set([]))
154
155
156    def test_return_tests_that_have_recently_passed_and_never_failed(self):
157        """Test that we can handle tests that have never failed."""
158        passing_experimental._MIN_DAYS_SINCE_FAILURE = 10
159        passing_experimental._MAX_DAYS_SINCE_LAST_PASS = 10
160        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
161        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
162
163        pass_times = {'test': self._datetime(2013, 3, 11)}
164        fail_times = {}
165        valid_tests = {'test'}
166
167        self.mox.ReplayAll()
168        results = passing_experimental.find_long_passing_tests(pass_times,
169                                                               fail_times,
170                                                               valid_tests)
171
172        self.assertEqual(results, set(['test']))
173
174
175    def test_handle_tests_that_have_never_passed(self):
176        """Test that we can handle tests that have never passed."""
177        passing_experimental._MIN_DAYS_SINCE_FAILURE = 10
178        passing_experimental._MAX_DAYS_SINCE_LAST_PASS = 10
179        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
180        datetime.datetime.today().AndReturn(self._datetime(2013, 3, 20))
181
182        pass_times = {}
183        fail_times = {'test': self._datetime(2013, 3, 11)}
184        valid_tests = {'test'}
185
186        self.mox.ReplayAll()
187        results = passing_experimental.find_long_passing_tests(pass_times,
188                                                               fail_times,
189                                                               valid_tests)
190
191        self.assertEqual(results, set([]))
192
193
194if __name__ == '__main__':
195    unittest.main()
196