| # Copyright 2017 The Chromium OS Authors. All rights reserved. |
| # Use of this source code is governed by a BSD-style license that can be |
| # found in the LICENSE file. |
| |
| """Tests for innocent_cls.py""" |
| |
| from __future__ import absolute_import |
| from __future__ import division |
| from __future__ import print_function |
| |
| import datetime |
| |
| from chromite.lib import constants |
| from chromite.lib import cidb_integration_test |
| from chromite.lib import clactions |
| from chromite.lib import metadata_lib |
| from google.appengine.ext import testbed |
| |
| from exonerator import innocent_cls |
| |
| |
| class TestInnocentCLs(cidb_integration_test.CIDBIntegrationTest): |
| """Tests the innocent_cls module with a local MySQL server. |
| |
| Must be run in the chroot. |
| """ |
| |
| def setUp(self): |
| """Sets up a fake datastore and some fake cidb data.""" |
| self.tb = testbed.Testbed() |
| self.tb.activate() |
| self.tb.init_datastore_v3_stub() |
| self.tb.init_memcache_stub() |
| self._SetupAnnotationsAndFinalizeMessage() |
| |
| def tearDown(self): |
| self.tb.deactivate() |
| |
| def _SetupAnnotationsAndFinalizeMessage(self): |
| """Creates rows in cidb for a finalized BAD_CL annotation.""" |
| self.db = self._PrepareDatabase() |
| |
| default_build_values = { |
| 'builder_name': 'my builder', |
| 'buildbot_generation': constants.BUILDBOT_GENERATION, |
| 'waterfall': 'chromiumos', |
| 'build_config': 'a build config', |
| 'bot_hostname': 'bot hostname', |
| } |
| # pylint: disable=protected-access |
| build_id_1 = self.db._Insert('buildTable', dict( |
| default_build_values, |
| start_time=datetime.datetime(2017, 1, 1), |
| build_number=1)) |
| build_id_2 = self.db._Insert('buildTable', dict( |
| default_build_values, |
| start_time=datetime.datetime(2017, 2, 2), |
| build_number=2)) |
| |
| action_1234 = clactions.CLAction.FromGerritPatchAndAction( |
| metadata_lib.GerritPatchTuple(1234, 1, True), |
| constants.CL_ACTION_KICKED_OUT) |
| |
| action_4242 = clactions.CLAction.FromGerritPatchAndAction( |
| metadata_lib.GerritPatchTuple(4242, 1, False), |
| constants.CL_ACTION_KICKED_OUT) |
| |
| action_4321 = clactions.CLAction.FromGerritPatchAndAction( |
| metadata_lib.GerritPatchTuple(4321, 1, False), |
| constants.CL_ACTION_KICKED_OUT) |
| |
| action_9999 = clactions.CLAction.FromGerritPatchAndAction( |
| metadata_lib.GerritPatchTuple(9999, 1, True), |
| constants.CL_ACTION_KICKED_OUT) |
| |
| self.db.InsertCLActions(build_id_1, [action_1234, action_4242]) |
| self.db.InsertCLActions(build_id_2, [action_4321, action_9999]) |
| |
| self.db._Insert('annotationsTable', { |
| 'build_id': build_id_1, |
| 'failure_category': constants.FAILURE_CATEGORY_BAD_CL, |
| 'last_annotator': 'bert', |
| 'failure_message': 'whoops!', |
| 'blame_url': 'crrev.com/c/4242', |
| }) |
| self.db._Insert('annotationsTable', { |
| 'build_id': build_id_2, |
| 'failure_category': constants.FAILURE_CATEGORY_BAD_CL, |
| 'last_annotator': 'ernie', |
| 'failure_message': 'yikes!', |
| 'blame_url': 'crrev.com/i/9999', |
| }) |
| |
| self.db._Insert('buildMessageTable', { |
| 'build_id': build_id_1, |
| 'message_type': constants.MESSAGE_TYPE_ANNOTATIONS_FINALIZED, |
| 'timestamp': '2017-01-01 00:00:00' |
| }) |
| self.db._Insert('buildMessageTable', { |
| 'build_id': build_id_2, |
| 'message_type': constants.MESSAGE_TYPE_ANNOTATIONS_FINALIZED, |
| 'timestamp': '2017-02-02 00:00:00' |
| }) |
| |
| def test_NewInnocentCLsWithOldLastBuild(self): |
| last_run = innocent_cls.LastBuild(timestamp=datetime.datetime(1999, 1, 1)) |
| last_run.put() |
| |
| new_cls = list(innocent_cls.NewInnocentCLs(self.db)) |
| assert new_cls == [(clactions.GerritPatchTuple(1234, 1, internal=True), 1), |
| (clactions.GerritPatchTuple(4321, 1, internal=False), 2)] |
| |
| def test_NewInnocentCLsWithNoLastBuild(self): |
| new_cls = list(innocent_cls.NewInnocentCLs(self.db)) |
| assert new_cls == [(clactions.GerritPatchTuple(1234, 1, internal=True), 1), |
| (clactions.GerritPatchTuple(4321, 1, internal=False), 2)] |
| |
| def test_NewInnocentCLsWithIntermediateLastBuild(self): |
| last_run = innocent_cls.LastBuild(timestamp=datetime.datetime(2017, 1, 23)) |
| last_run.put() |
| |
| new_cls = list(innocent_cls.NewInnocentCLs(self.db)) |
| assert new_cls == [(clactions.GerritPatchTuple(4321, 1, internal=False), 2)] |
| |
| def test_NewInnocentCLsWithNewLastBuild(self): |
| last_run = innocent_cls.LastBuild(timestamp=datetime.datetime.max) |
| last_run.put() |
| |
| new_cls = list(innocent_cls.NewInnocentCLs(self.db)) |
| assert new_cls == [] |