# -*- coding: utf-8 -*-
# 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.

"""Unittests for builder_status_lib."""

from __future__ import print_function

import mock

from chromite.cbuildbot import build_status_unittest
from chromite.lib import buildbucket_lib
from chromite.lib import builder_status_lib
from chromite.lib import cidb
from chromite.lib import config_lib
from chromite.lib import constants
from chromite.lib import cros_test_lib
from chromite.lib import fake_cidb
from chromite.lib import failure_message_lib
from chromite.lib import failure_message_lib_unittest
from chromite.lib import metadata_lib
from chromite.lib.buildstore import FakeBuildStore


bb_infos = build_status_unittest.BuildbucketInfos
cidb_infos = build_status_unittest.CIDBStatusInfos
failure_msg_helper = failure_message_lib_unittest.FailureMessageHelper
stage_failure_helper = failure_message_lib_unittest.StageFailureHelper


def ConstructFailureMessages(build_config):
  """Helper method to construct failure messages."""
  entry_1 = stage_failure_helper.GetStageFailure(
      build_config=build_config, failure_id=1)
  entry_2 = stage_failure_helper.GetStageFailure(
      build_config=build_config, failure_id=2, outer_failure_id=1)
  entry_3 = stage_failure_helper.GetStageFailure(
      build_config=build_config, failure_id=3, outer_failure_id=1)
  failure_entries = [entry_1, entry_2, entry_3]
  failure_messages = (
      failure_message_lib.FailureMessageManager.ConstructStageFailureMessages(
          failure_entries))

  return failure_messages


class BuilderStatusLibTests(cros_test_lib.MockTestCase):
  """Tests for builder_status_lib."""

  def testGetSlavesAbortedBySelfDestructedMaster(self):
    """Test GetSlavesAbortedBySelfDestructedMaster with aborted slaves."""
    db = fake_cidb.FakeCIDBConnection()
    buildstore = FakeBuildStore(db)
    cidb.CIDBConnectionFactory.SetupMockCidb(db)
    master_build_id = db.InsertBuild(
        'master', 1, 'master', 'bot_hostname',
        buildbucket_id='0')

    self.assertEqual(
        set(),
        builder_status_lib.GetSlavesAbortedBySelfDestructedMaster(
            master_build_id, buildstore))

    db.InsertBuild(
        'slave_1', 1, 'slave_1', 'bot_hostname',
        master_build_id=master_build_id, buildbucket_id=12)
    db.InsertBuild(
        'slave_2', 2, 'slave_2', 'bot_hostname',
        master_build_id=master_build_id, buildbucket_id=23)
    db.InsertBuild(
        'slave_3', 3, 'slave_3', 'bot_hostname',
        master_build_id=master_build_id, buildbucket_id=34)
    for slave_build_id in (12, 23):
      db.InsertBuildMessage(
          master_build_id,
          message_type=constants.MESSAGE_TYPE_IGNORED_REASON,
          message_subtype=constants.MESSAGE_SUBTYPE_SELF_DESTRUCTION,
          message_value=str(slave_build_id))
    self.assertEqual(
        {'slave_1', 'slave_2'},
        builder_status_lib.GetSlavesAbortedBySelfDestructedMaster(
            master_build_id, buildstore))


# pylint: disable=protected-access
class BuilderStatusManagerTest(cros_test_lib.MockTestCase):
  """Tests for BuilderStatusManager."""

  def setUp(self):
    self.db = fake_cidb.FakeCIDBConnection()

  def testCreateBuildFailureMessageWithMessages(self):
    """Test CreateBuildFailureMessage with stage failure messages."""
    overlays = constants.PRIVATE_OVERLAYS
    dashboard_url = 'http://fake_dashboard_url'
    slave = 'cyan-paladin'
    failure_messages = ConstructFailureMessages(slave)

    build_msg = (
        builder_status_lib.BuilderStatusManager.CreateBuildFailureMessage(
            slave, overlays, dashboard_url, failure_messages))

    self.assertTrue('stage failed' in build_msg.message_summary)
    self.assertTrue(build_msg.internal)
    self.assertEqual(build_msg.builder, slave)

  def testCreateBuildFailureMessageWithoutMessages(self):
    """Test CreateBuildFailureMessage without stage failure messages."""
    overlays = constants.PUBLIC_OVERLAYS
    dashboard_url = 'http://fake_dashboard_url'
    slave = 'cyan-paladin'

    build_msg = (
        builder_status_lib.BuilderStatusManager.CreateBuildFailureMessage(
            slave, overlays, dashboard_url, None))

    self.assertTrue('cbuildbot failed' in build_msg.message_summary)
    self.assertFalse(build_msg.internal)
    self.assertEqual(build_msg.builder, slave)

  def testCreateBuildFailureMessageWhenCanceled(self):
    """Test CreateBuildFailureMessage with no stage failure and canceled"""
    overlays = constants.PRIVATE_OVERLAYS
    dashboard_url = 'http://fake_dashboard_url'
    slave = 'cyan-paladin'

    build_msg = (
        builder_status_lib.BuilderStatusManager.CreateBuildFailureMessage(
            slave, overlays, dashboard_url, None,
            aborted_by_self_destruction=True))

    self.assertTrue('aborted by self-destruction' in build_msg.message_summary)
    self.assertFalse('cbuildbot failed' in build_msg.message_summary)
    self.assertEqual(build_msg.builder, slave)

  def testCreateBuildFailureMessageSupersedesCancellation(self):
    """Test CreateBuildFailureMessage with a stage failure when canceled"""
    overlays = constants.PRIVATE_OVERLAYS
    dashboard_url = 'http://fake_dashboard_url'
    slave = 'cyan-paladin'
    failure_messages = ConstructFailureMessages(slave)

    build_msg = (
        builder_status_lib.BuilderStatusManager.CreateBuildFailureMessage(
            slave, overlays, dashboard_url, failure_messages,
            aborted_by_self_destruction=True))

    self.assertFalse('canceled by master' in build_msg.message_summary)
    self.assertFalse('cbuildbot failed' in build_msg.message_summary)
    self.assertEqual(build_msg.builder, slave)


class SlaveBuilderStatusTest(cros_test_lib.MockTestCase):
  """Tests for SlaveBuilderStatus."""

  def setUp(self):
    self.db = fake_cidb.FakeCIDBConnection()
    self.master_build_id = 0
    self.site_config = config_lib.GetConfig()
    self.config = self.site_config['master-paladin']
    self.metadata = metadata_lib.CBuildbotMetadata()
    self.db = fake_cidb.FakeCIDBConnection()
    self.buildbucket_client = mock.Mock()
    self.slave_1 = 'cyan-paladin'
    self.slave_2 = 'auron-paladin'
    self.builders_array = [self.slave_1, self.slave_2]

  def testGetAllSlaveBuildbucketInfo(self):
    """Test GetAllSlaveBuildbucketInfo."""

    # Test completed builds.
    buildbucket_info_dict = {
        'build1': buildbucket_lib.BuildbucketInfo(
            'id_1', 1, 0, None, None, None),
        'build2': buildbucket_lib.BuildbucketInfo(
            'id_2', 1, 0, None, None, None)
    }
    self.PatchObject(buildbucket_lib, 'GetScheduledBuildDict',
                     return_value=buildbucket_info_dict)

    expected_status = 'COMPLETED'
    expected_result = 'SUCCESS'
    expected_url = 'fake_url'
    content = {
        'build': {
            'status': expected_status,
            'result': expected_result,
            'url': expected_url
        }
    }

    self.buildbucket_client.GetBuildRequest.return_value = content
    updated_buildbucket_info_dict = (
        builder_status_lib.SlaveBuilderStatus.GetAllSlaveBuildbucketInfo(
            self.buildbucket_client, buildbucket_info_dict))

    self.assertEqual(updated_buildbucket_info_dict['build1'].status,
                     expected_status)
    self.assertEqual(updated_buildbucket_info_dict['build1'].result,
                     expected_result)
    self.assertEqual(updated_buildbucket_info_dict['build1'].url,
                     expected_url)
    self.assertEqual(updated_buildbucket_info_dict['build2'].status,
                     expected_status)
    self.assertEqual(updated_buildbucket_info_dict['build2'].result,
                     expected_result)
    self.assertEqual(updated_buildbucket_info_dict['build1'].url,
                     expected_url)

    # Test started builds.
    expected_status = 'STARTED'
    expected_result = None
    content = {
        'build': {
            'status': 'STARTED'
        }
    }
    self.buildbucket_client.GetBuildRequest.return_value = content
    updated_buildbucket_info_dict = (
        builder_status_lib.SlaveBuilderStatus.GetAllSlaveBuildbucketInfo(
            self.buildbucket_client, buildbucket_info_dict))

    self.assertEqual(updated_buildbucket_info_dict['build1'].status,
                     expected_status)
    self.assertEqual(updated_buildbucket_info_dict['build1'].result,
                     expected_result)
    self.assertEqual(updated_buildbucket_info_dict['build2'].status,
                     expected_status)
    self.assertEqual(updated_buildbucket_info_dict['build2'].result,
                     expected_result)

    # Test BuildbucketResponseException failures.
    self.buildbucket_client.GetBuildRequest.side_effect = (
        buildbucket_lib.BuildbucketResponseException)
    updated_buildbucket_info_dict = (
        builder_status_lib.SlaveBuilderStatus.GetAllSlaveBuildbucketInfo(
            self.buildbucket_client, buildbucket_info_dict))
    self.assertIsNone(updated_buildbucket_info_dict['build1'].status)
    self.assertIsNone(updated_buildbucket_info_dict['build2'].status)

  def _InsertMasterSlaveBuildsToCIDB(self):
    """Insert master and slave builds into fake_cidb."""
    master = self.db.InsertBuild('master', 1,
                                 'master', 'host1')
    slave1 = self.db.InsertBuild('slave1', 2,
                                 'slave1', 'host1', master_build_id=0,
                                 buildbucket_id='id_1', status='fail')
    slave2 = self.db.InsertBuild('slave2', 3,
                                 'slave2', 'host1', master_build_id=0,
                                 buildbucket_id='id_2', status='fail')
    return master, slave1, slave2

  def testGetAllSlaveCIDBStatusInfo(self):
    """GetAllSlaveCIDBStatusInfo without Buildbucket info."""
    _, slave1_id, slave2_id = self._InsertMasterSlaveBuildsToCIDB()

    expected_status = {
        'slave1': builder_status_lib.CIDBStatusInfo(slave1_id, 'fail', 'id_1'),
        'slave2': builder_status_lib.CIDBStatusInfo(slave2_id, 'fail', 'id_2')
    }

    cidb_status = (
        builder_status_lib.SlaveBuilderStatus.GetAllSlaveCIDBStatusInfo(
            self.db, self.master_build_id, None))
    self.assertDictEqual(cidb_status, expected_status)

    cidb_status = (
        builder_status_lib.SlaveBuilderStatus.GetAllSlaveCIDBStatusInfo(
            self.db, self.master_build_id, None))
    self.assertDictEqual(cidb_status, expected_status)

  def testGetAllSlaveCIDBStatusInfoWithBuildbucket(self):
    """GetAllSlaveCIDBStatusInfo with Buildbucket info."""
    _, slave1_id, slave2_id = self._InsertMasterSlaveBuildsToCIDB()

    buildbucket_info_dict = {
        'slave1': build_status_unittest.BuildbucketInfos.GetStartedBuild(
            bb_id='id_1'),
        'slave2': build_status_unittest.BuildbucketInfos.GetStartedBuild(
            bb_id='id_2')
    }

    expected_status = {
        'slave1': builder_status_lib.CIDBStatusInfo(slave1_id, 'fail', 'id_1'),
        'slave2': builder_status_lib.CIDBStatusInfo(slave2_id, 'fail', 'id_2')
    }

    cidb_status = (
        builder_status_lib.SlaveBuilderStatus.GetAllSlaveCIDBStatusInfo(
            self.db, self.master_build_id, buildbucket_info_dict))
    self.assertDictEqual(cidb_status, expected_status)

    cidb_status = (
        builder_status_lib.SlaveBuilderStatus.GetAllSlaveCIDBStatusInfo(
            self.db, self.master_build_id, buildbucket_info_dict))
    self.assertDictEqual(cidb_status, expected_status)

  def testGetAllSlaveCIDBStatusInfoWithRetriedBuilds(self):
    """GetAllSlaveCIDBStatusInfo doesn't return retried builds."""
    self._InsertMasterSlaveBuildsToCIDB()
    self.db.InsertBuild('slave1', 3,
                        'slave1', 'host1', master_build_id=0,
                        buildbucket_id='id_3', status='inflight')

    buildbucket_info_dict = {
        'slave1': build_status_unittest.BuildbucketInfos.GetStartedBuild(
            bb_id='id_3'),
        'slave2': build_status_unittest.BuildbucketInfos.GetStartedBuild(
            bb_id='id_4')
    }

    cidb_status = (
        builder_status_lib.SlaveBuilderStatus.GetAllSlaveCIDBStatusInfo(
            self.db, self.master_build_id, buildbucket_info_dict))
    self.assertEqual(set(cidb_status.keys()), set(['slave1']))
    self.assertEqual(cidb_status['slave1'].status, 'inflight')


  def ConstructBuilderStatusManager(self,
                                    master_build_id=None,
                                    db=None,
                                    config=None,
                                    metadata=None,
                                    buildbucket_client=None,
                                    builders_array=None,
                                    dry_run=True):
    if master_build_id is None:
      master_build_id = self.master_build_id
    if db is None:
      db = self.db
    if config is None:
      config = self.config
    if metadata is None:
      metadata = self.metadata
    if buildbucket_client is None:
      buildbucket_client = self.buildbucket_client
    if builders_array is None:
      builders_array = self.builders_array
    buildstore = FakeBuildStore(db)

    return builder_status_lib.SlaveBuilderStatus(
        master_build_id, buildstore, config, metadata, buildbucket_client,
        builders_array, dry_run)

  def testGetSlaveFailures(self):
    """Test _GetSlaveFailures."""
    # pylint: disable=attribute-defined-outside-init
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_InitSlaveInfo')
    entry_1 = stage_failure_helper.GetStageFailure(
        build_config=self.slave_1, failure_id=1)
    entry_2 = stage_failure_helper.GetStageFailure(
        build_config=self.slave_1, failure_id=2, outer_failure_id=1)
    entry_3 = stage_failure_helper.GetStageFailure(
        build_config=self.slave_2, failure_id=3)
    failure_entries = [entry_1, entry_2, entry_3]
    mock_db = mock.Mock()
    mock_db.GetBuildStatusesWithBuildbucketIds.return_value = []
    self.buildstore = FakeBuildStore(mock_db)
    mock_db.GetBuildsFailures.return_value = failure_entries
    fake_bb_info = mock.Mock()
    fake_bb_info.buildbucket_id = 1234
    fake_buildbucket_info_dict = {1: fake_bb_info}
    manager = self.ConstructBuilderStatusManager(db=mock_db)
    slave_failures_dict = manager._GetSlaveFailures(fake_buildbucket_info_dict)

    self.assertItemsEqual(slave_failures_dict.keys(),
                          [self.slave_1, self.slave_2])
    self.assertEqual(len(slave_failures_dict[self.slave_1]), 1)
    self.assertEqual(len(slave_failures_dict[self.slave_2]), 1)
    self.assertTrue(isinstance(slave_failures_dict[self.slave_1][0],
                               failure_message_lib.CompoundFailureMessage))
    self.assertTrue(isinstance(slave_failures_dict[self.slave_2][0],
                               failure_message_lib.StageFailureMessage))

  def testGetSlavesAbortedBySelfDestructionReturnsEmptySet(self):
    """Test GetSlavesAbortedBySelfDestruction returns an empty set."""
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_InitSlaveInfo')
    cidb_info_dict = cidb_infos.GetFullCIDBStatusInfo()
    manager = self.ConstructBuilderStatusManager()

    aborted_slaves = manager._GetSlavesAbortedBySelfDestruction(cidb_info_dict)
    self.assertEqual(aborted_slaves, set())

  def testGetSlavesAbortedBySelfDestructionWithAbortedBuilds(self):
    """Test GetSlavesAbortedBySelfDestruction with aborted builds."""
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_InitSlaveInfo')
    cidb_info_dict = cidb_infos.GetFullCIDBStatusInfo()
    self.db.InsertBuildMessage(
        self.master_build_id,
        message_type=constants.MESSAGE_TYPE_IGNORED_REASON,
        message_subtype=constants.MESSAGE_SUBTYPE_SELF_DESTRUCTION,
        message_value=str(3))
    manager = self.ConstructBuilderStatusManager()

    aborted_slaves = manager._GetSlavesAbortedBySelfDestruction(cidb_info_dict)
    self.assertEqual(aborted_slaves, {'completed_failure'})

  def testInitSlaveInfo(self):
    """Test _InitSlaveInfo with Buildbucket info."""
    self.PatchObject(builder_status_lib.SlaveBuilderStatus,
                     '_GetSlaveFailures')
    self.PatchObject(builder_status_lib.SlaveBuilderStatus,
                     'GetAllSlaveBuildbucketInfo',
                     return_value={self.slave_1: bb_infos.GetSuccessBuild()})
    manager = self.ConstructBuilderStatusManager()

    self.assertItemsEqual(manager.builders_array, [self.slave_1])
    self.assertIsNotNone(manager.buildbucket_info_dict)

  def testGetStatusWithBuildbucket(self):
    """Test _GetStatus with Buildbucket info."""
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_InitSlaveInfo')
    cidb_info_dict = cidb_infos.GetFullCIDBStatusInfo()
    buildbucket_info_dict = bb_infos.GetFullBuildbucketInfoDict()
    manager = self.ConstructBuilderStatusManager()

    status_1 = manager._GetStatus(
        'scheduled', cidb_info_dict, buildbucket_info_dict)
    self.assertEqual(status_1, constants.BUILDER_STATUS_MISSING)
    status_2 = manager._GetStatus(
        'started', cidb_info_dict, buildbucket_info_dict)
    self.assertEqual(status_2, constants.BUILDER_STATUS_INFLIGHT)
    status_3 = manager._GetStatus(
        'completed_success', cidb_info_dict, buildbucket_info_dict)
    self.assertEqual(status_3, constants.BUILDER_STATUS_PASSED)
    status_4 = manager._GetStatus(
        'completed_failure', cidb_info_dict, buildbucket_info_dict)
    self.assertEqual(status_4, constants.BUILDER_STATUS_FAILED)
    status_5 = manager._GetStatus(
        'completed_canceled', cidb_info_dict, buildbucket_info_dict)
    self.assertEqual(status_5, constants.BUILDER_STATUS_FAILED)

  def test_GetDashboardUrlWithBuildbucket(self):
    """Test _GetDashboardUrl with Buildbucket info."""
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_InitSlaveInfo')
    manager = self.ConstructBuilderStatusManager()
    cidb_info_dict = {
        self.slave_1: cidb_infos.GetPassedBuild(build_id=1, buildbucket_id=100)}
    buildbucket_info_dict = {
        self.slave_1: bb_infos.GetSuccessBuild(url='http://buildbucket_url'),
        self.slave_2:  bb_infos.GetSuccessBuild(url='http://buildbucket_url'),
    }

    dashboard_url = manager._GetDashboardUrl(
        self.slave_1, cidb_info_dict, buildbucket_info_dict)
    self.assertEqual(
        dashboard_url,
        'http://buildbucket_url')

    dashboard_url = manager._GetDashboardUrl(
        self.slave_2, cidb_info_dict, buildbucket_info_dict)
    self.assertEqual(dashboard_url, 'http://buildbucket_url')

  def testGetDashboardUrlWithoutBuildbucket(self):
    """Test _GetDashboardUrl without Buildbucket info."""
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_InitSlaveInfo')
    manager = self.ConstructBuilderStatusManager()

    dashboard_url = manager._GetDashboardUrl(self.slave_1, {}, None)
    self.assertIsNone(dashboard_url)

  def testGetMessageOnFailedBuilds(self):
    """Test _GetMessage on failed builds."""
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_InitSlaveInfo')
    mock_create_msg = self.PatchObject(builder_status_lib.BuilderStatusManager,
                                       'CreateBuildFailureMessage')
    manager = self.ConstructBuilderStatusManager()
    failure_messages = ConstructFailureMessages(self.slave_1)
    slave_failures_dict = {self.slave_1: failure_messages}
    aborted_slaves = {self.slave_1, self.slave_2}
    manager._GetMessage(
        self.slave_1, constants.BUILDER_STATUS_FAILED, 'dashboard_url',
        slave_failures_dict, aborted_slaves)

    mock_create_msg.assert_called_with(
        self.slave_1, mock.ANY, 'dashboard_url',
        slave_failures_dict.get(self.slave_1), aborted_by_self_destruction=True)

  def testGetMessageOnNotFailedBuilds(self):
    """Test _GetMessage on not failed builds."""
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_InitSlaveInfo')
    mock_create_msg = self.PatchObject(builder_status_lib.BuilderStatusManager,
                                       'CreateBuildFailureMessage')
    manager = self.ConstructBuilderStatusManager()
    manager._GetMessage(
        self.slave_1, constants.BUILDER_STATUS_PASSED, 'dashboard_url', {},
        set())

    mock_create_msg.assert_not_called()

  def testGetBuilderStatusForBuild(self):
    """Test GetBuilderStatusForBuild."""
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_InitSlaveInfo')
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_GetStatus')
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_GetDashboardUrl')
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '_GetMessage')
    manager = self.ConstructBuilderStatusManager()
    self.assertIsNotNone(manager.GetBuilderStatusForBuild(self.slave_1))

  def testCancelBuilds(self):
    """Test CancelBuilds."""
    buildbucket_id_1 = '100'
    buildbucket_id_2 = '200'
    buildbucket_ids = [buildbucket_id_1, buildbucket_id_2]

    cancel_mock = self.buildbucket_client.CancelBatchBuildsRequest

    cancel_mock.return_value = dict()
    builder_status_lib.CancelBuilds(buildbucket_ids, self.buildbucket_client)

    self.assertEqual(cancel_mock.call_count, 1)

  def testCancelNoBuilds(self):
    """Test CancelBuilds with no builds to cancel."""
    cancel_mock = self.buildbucket_client.CancelBatchBuildsRequest

    builder_status_lib.CancelBuilds([], self.buildbucket_client)
    self.assertEqual(cancel_mock.call_count, 0)

  def testCancelWithBuildbucketClient(self):
    """Test Buildbucket client cancels successfully during CancelBuilds."""
    buildbucket_id_1 = '100'
    buildbucket_id_2 = '200'
    buildbucket_ids = [buildbucket_id_1, buildbucket_id_2]

    self.PatchObject(buildbucket_lib, 'GetServiceAccount',
                     return_value=True)
    send_request_mock = self.PatchObject(buildbucket_lib.BuildbucketClient,
                                         'SendBuildbucketRequest',
                                         return_value=dict())
    buildbucket_client = buildbucket_lib.BuildbucketClient(
        mock.Mock(), mock.Mock())

    builder_status_lib.CancelBuilds(buildbucket_ids, buildbucket_client)

    self.assertEqual(send_request_mock.call_count, 1)

  def testAbortedBySelfDestruction(self):
    """Test that self-destructive aborts in CIDB are recognized."""
    slave = 'cyan-paladin'
    builder_number = 37

    slave_id = self.db.InsertBuild(slave,
                                   builder_number, slave, 'bot_hostname',
                                   master_build_id=self.master_build_id)
    self.db.InsertBuildMessage(
        self.master_build_id,
        message_type=constants.MESSAGE_TYPE_IGNORED_REASON,
        message_subtype=constants.MESSAGE_SUBTYPE_SELF_DESTRUCTION,
        message_value=str(slave_id))

    self.assertTrue(
        builder_status_lib.BuilderStatusManager.AbortedBySelfDestruction(
            self.db, slave_id, self.master_build_id))

  def testNotAbortedBySelfDestruction(self):
    """Test that aborts in CIDB are only flagged if they happened."""
    slave = 'cyan-paladin'
    builder_number = 37

    slave_id = self.db.InsertBuild(slave,
                                   builder_number, slave, 'bot_hostname',
                                   master_build_id=self.master_build_id)
    self.db.InsertBuildMessage(self.master_build_id,
                               message_value=slave_id)
    builder_number = 1

    self.db.InsertBuild(slave,
                        builder_number, slave, 'bot_hostname')
    self.db.InsertBuildMessage(slave)

    self.assertFalse(
        builder_status_lib.BuilderStatusManager.AbortedBySelfDestruction(
            self.db, slave_id, self.master_build_id))

  def testAbortedBySelfDestructionOnBuildWithoutMaster(self):
    """AbortedBySelfDestruction returns False on builds without master."""
    self.assertFalse(
        builder_status_lib.BuilderStatusManager.AbortedBySelfDestruction(
            self.db, 1, None))


class BuilderStatusesFetcherTests(cros_test_lib.MockTestCase):
  """Tests for BuilderStatusesFetcher."""

  def setUp(self):
    self.build_id = 0
    self.db = fake_cidb.FakeCIDBConnection()
    self.buildstore = FakeBuildStore(self.db)
    self.site_config = config_lib.GetConfig()
    self.config = self.site_config['master-paladin']
    self.slave_config = self.site_config['eve-paladin']
    self.message = 'build message'
    self.metadata = metadata_lib.CBuildbotMetadata()
    self.buildbucket_client = mock.Mock()
    self.slave_1 = 'cyan-paladin'
    self.slave_2 = 'auron-paladin'
    self.builders_array = [self.slave_1, self.slave_2]

  def CreateBuilderStatusesFetcher(
      self, build_id=None, success=True, message=None, config=None,
      metadata=None, buildbucket_client=None, builders_array=None,
      dry_run=True):
    build_id = build_id or self.build_id
    message = message or self.message
    config = config or self.config
    metadata = metadata or self.metadata
    buildbucket_client = buildbucket_client or self.buildbucket_client
    builders_array = (builders_array if builders_array is not None
                      else self.builders_array)
    self.PatchObject(buildbucket_lib, 'FetchCurrentSlaveBuilders',
                     return_value=builders_array)
    builder_statuses_fetcher = builder_status_lib.BuilderStatusesFetcher(
        build_id, self.buildstore, success, message, config, metadata,
        buildbucket_client, builders_array=builders_array, dry_run=dry_run)

    return builder_statuses_fetcher

  def _PatchesForGetSlaveBuilderStatus(self, status_dict):
    self.PatchObject(builder_status_lib.SlaveBuilderStatus, '__init__',
                     return_value=None)
    message_mock = mock.Mock()
    message_mock.BuildFailureMessageToStr.return_value = 'failure_message_str'
    build_statuses = {
        x: builder_status_lib.BuilderStatus(
            status_dict[x].status, message_mock) for x in status_dict
    }
    self.PatchObject(builder_status_lib.SlaveBuilderStatus,
                     'GetBuilderStatusForBuild',
                     side_effect=lambda config: build_statuses[config])

  def testFetchLocalBuilderStatus(self):
    """Test _FetchLocalBuilderStatus."""
    fetcher = self.CreateBuilderStatusesFetcher()

    local_builder_status = fetcher._FetchLocalBuilderStatus()
    self.assertTrue('master-paladin' in local_builder_status.keys())

  def testFetchSlaveBuilderStatusesWithEmptySlaveList(self):
    """Test _FetchSlaveBuilderStatuses with an empty slave list."""
    self._PatchesForGetSlaveBuilderStatus({})
    fetcher = self.CreateBuilderStatusesFetcher(builders_array=[])
    statuses = fetcher._FetchSlaveBuilderStatuses()
    self.assertEqual(statuses, {})

  def testFetchSlaveBuildersStatusesWithSlaveList(self):
    """Test _FetchSlaveBuilderStatuses with a slave list."""
    status_dict = {
        'build1': build_status_unittest.CIDBStatusInfos.GetFailedBuild(
            build_id=1),
        'build2': build_status_unittest.CIDBStatusInfos.GetPassedBuild(
            build_id=2),
        'build3': build_status_unittest.CIDBStatusInfos.GetInflightBuild(
            build_id=3)
    }
    self._PatchesForGetSlaveBuilderStatus(status_dict)
    fetcher = self.CreateBuilderStatusesFetcher(
        builders_array=['build1', 'build2', 'build3'])
    statuses = fetcher._FetchSlaveBuilderStatuses()
    self.assertTrue(statuses['build1'].Failed())
    self.assertTrue(statuses['build2'].Passed())
    self.assertTrue(statuses['build3'].Inflight())

  def testGetBuilderStatusesOnSlaves(self):
    """Test GetBuilderStatuses on slaves."""
    fetcher = self.CreateBuilderStatusesFetcher(
        config=self.slave_config, builders_array=[])

    important_statuses, experimental_statuses = fetcher.GetBuilderStatuses()
    self.assertEqual(len(important_statuses), 1)
    self.assertEqual(len(experimental_statuses), 0)
    self.assertTrue(important_statuses['eve-paladin'].Passed())

  def testGetBuilderStatusesOnMasters(self):
    """Test GetBuilderStatuses on masters."""
    status_dict = {
        'build1': build_status_unittest.CIDBStatusInfos.GetFailedBuild(
            build_id=1),
        'build2': build_status_unittest.CIDBStatusInfos.GetPassedBuild(
            build_id=2),
        'build3': build_status_unittest.CIDBStatusInfos.GetInflightBuild(
            build_id=3)
    }
    self._PatchesForGetSlaveBuilderStatus(status_dict)
    fetcher = self.CreateBuilderStatusesFetcher(
        builders_array=status_dict.keys())

    important, experimental = fetcher.GetBuilderStatuses()
    self.assertItemsEqual(['build1', 'build2', 'build3', 'master-paladin'],
                          important.keys())
    self.assertItemsEqual([], experimental.keys())

    # Update the experimental_builders in metadata
    self.metadata.UpdateWithDict({
        constants.METADATA_EXPERIMENTAL_BUILDERS: ['build1']
    })
    important, experimental = fetcher.GetBuilderStatuses()
    self.assertItemsEqual(['build2', 'build3', 'master-paladin'],
                          important.keys())
    self.assertItemsEqual(['build1'], experimental.keys())

  def _CreateBuilderStatusDict(self):
    passed = builder_status_lib.BuilderStatus(
        constants.BUILDER_STATUS_PASSED, None)
    failed = builder_status_lib.BuilderStatus(
        constants.BUILDER_STATUS_FAILED, mock.Mock())
    inflight = builder_status_lib.BuilderStatus(
        constants.BUILDER_STATUS_INFLIGHT, mock.Mock())
    missing = builder_status_lib.BuilderStatus(
        constants.BUILDER_STATUS_MISSING, None)
    return {'passed': passed,
            'failed': failed,
            'inflight': inflight,
            'missing': missing}

  def testGetFailingBuilds(self):
    """Test GetFailingBuilds."""
    statuses = self._CreateBuilderStatusDict()
    self.assertEqual(
        builder_status_lib.BuilderStatusesFetcher.GetFailingBuilds(statuses),
        {'failed'})

  def testGetInflightBuilds(self):
    """Test GetInflightBuilds."""
    statuses = self._CreateBuilderStatusDict()
    self.assertEqual(
        builder_status_lib.BuilderStatusesFetcher.GetInflightBuilds(statuses),
        {'inflight'})

  def testGetNostatBuilds(self):
    """Test GetNostatBuilds."""
    statuses = self._CreateBuilderStatusDict()
    self.assertEqual(
        builder_status_lib.BuilderStatusesFetcher.GetNostatBuilds(statuses),
        {'missing'})
