def test_get_exchange_rates_by_date__pick_average_rate_for_dates_missing_one_day(dao_exchange_rate, dao_provider, base_currency, logger):
    """
    :param dao_exchange_rate: Mock of gold_digger.database.DaoExchangeRate
    :param dao_provider: Mock of gold_digger.database.DaoProvider
    :type base_currency: str
    :type logger: logging.Logger
    """
    _start_date = date(2016, 2, 17)
    _end_date = date(2016, 2, 19)

    exchange_rate_manager = ExchangeRateManager(dao_exchange_rate, dao_provider, [], base_currency, set())

    def _get_rates_by_dates_for_currency_in_period(currency, start_date, end_date):
        """
        :type currency: str
        :type start_date: datetime.date
        :type end_date: datetime.date
        :rtype: dict[datetime.date, list[decimal.Decimal]]
        """
        return {
            "EUR": {
                start_date: [Decimal(0.88), Decimal(0.88), Decimal(0.89)],
                end_date: [Decimal(0.88), Decimal(0.89), Decimal(0.89)],
            },
            "CZK": {
                start_date: [Decimal(24.19), Decimal(24.19), Decimal(24.20)],
                end_date: [Decimal(24.19), Decimal(24.20), Decimal(24.20)],
            },
        }[currency]

    dao_exchange_rate.get_rates_by_dates_for_currency_in_period.side_effect = _get_rates_by_dates_for_currency_in_period

    exchange_rates_by_dates = exchange_rate_manager.get_exchange_rates_by_dates(_start_date, _end_date, "EUR", "CZK", logger)

    # we use average from best yesterday and best tomorrow rates
    best_to_currency_rate = (Decimal(24.19) + Decimal(24.20)) / 2
    best_from_currency_rate = (Decimal(0.88) + Decimal(0.89)) / 2
    assert exchange_rates_by_dates == {
        "2016-02-17": str(Decimal(24.19) / Decimal(0.88)),
        "2016-02-18": str(best_to_currency_rate / best_from_currency_rate),
        "2016-02-19": str(Decimal(24.20) / Decimal(0.89)),
    }
    dao_exchange_rate.get_rates_by_dates_for_currency_in_period.assert_has_calls([
        call("EUR", _start_date, _end_date),
        call("CZK", _start_date, _end_date),
    ])
def test_get_exchange_rates_by_date__same_currencies_returns_immediately(dao_exchange_rate, dao_provider, base_currency, logger):
    """
    :param dao_exchange_rate: Mock of gold_digger.database.DaoExchangeRate
    :param dao_provider: Mock of gold_digger.database.DaoProvider
    :type base_currency: str
    :type logger: logging.Logger
    """
    exchange_rate_manager = ExchangeRateManager(dao_exchange_rate, dao_provider, [], base_currency, set())

    exchange_rates_by_dates = exchange_rate_manager.get_exchange_rates_by_dates(date(2016, 2, 17), date(2016, 2, 19), "EUR", "EUR", logger)

    assert exchange_rates_by_dates == {
        "2016-02-17": "1.0",
        "2016-02-18": "1.0",
        "2016-02-19": "1.0",
    }
    dao_exchange_rate.get_rates_by_dates_for_currency_in_period.assert_not_called()
def test_get_exchange_rates_by_date__ignore_dates_missing_for_more_than_one_day(dao_exchange_rate, dao_provider, base_currency, logger):
    """
    :param dao_exchange_rate: Mock of gold_digger.database.DaoExchangeRate
    :param dao_provider: Mock of gold_digger.database.DaoProvider
    :type base_currency: str
    :type logger: logging.Logger
    """
    _start_date = date(2016, 2, 17)
    _end_date = date(2016, 2, 20)

    exchange_rate_manager = ExchangeRateManager(dao_exchange_rate, dao_provider, [], base_currency, set())

    def _get_rates_by_dates_for_currency_in_period(currency, start_date, end_date):
        """
        :type currency: str
        :type start_date: datetime.date
        :type end_date: datetime.date
        :rtype: dict[datetime.date, list[decimal.Decimal]]
        """
        return {
            "EUR": {
                start_date: [Decimal(0.88), Decimal(0.88), Decimal(0.89)],
                end_date: [Decimal(0.88), Decimal(0.89), Decimal(0.89)],
            },
            "CZK": {
                start_date: [Decimal(24.19), Decimal(24.19), Decimal(24.20)],
                end_date: [Decimal(24.19), Decimal(24.20), Decimal(24.20)],
            },
        }[currency]

    dao_exchange_rate.get_rates_by_dates_for_currency_in_period.side_effect = _get_rates_by_dates_for_currency_in_period

    exchange_rates_by_dates = exchange_rate_manager.get_exchange_rates_by_dates(_start_date, _end_date, "EUR", "CZK", logger)

    assert exchange_rates_by_dates == {
        "2016-02-17": str(Decimal(24.19) / Decimal(0.88)),
        "2016-02-20": str(Decimal(24.20) / Decimal(0.89)),
    }
    dao_exchange_rate.get_rates_by_dates_for_currency_in_period.assert_has_calls([
        call("EUR", _start_date, _end_date),
        call("CZK", _start_date, _end_date),
    ])