import logging

from itertools import filterfalse
from operator import itemgetter
from datetime import datetime, timezone

from maps_adv.billing_proxy.client import Client
from maps_adv.export.lib.pipeline.exceptions import StepException

logger = logging.getLogger(__name__)


class BillingStep:
    def __init__(self, config):
        self._client = Client(config.BILLING_URL)

    async def __call__(self, campaigns):
        auto_campaigns = list(filter(lambda c: c.get("order_id"), campaigns))
        manul_campaigns = list(filterfalse(lambda c: c.get("order_id"), campaigns))

        try:
            async with self._client as billing_client:
                active_orders = await billing_client.fetch_active_orders(
                    *set(map(itemgetter("order_id"), auto_campaigns))
                )
        except Exception:
            logger.exception("Failed to fetch active orders")
            raise StepException()

        active_orders = set(active_orders)
        now_utc = datetime.now(timezone.utc)
        return manul_campaigns + list(
            filter(
                lambda c: c["order_id"] in active_orders
                or (c.get("paid_till") is not None and c["paid_till"] >= now_utc),
                auto_campaigns,
            )
        )
