import json
import logging

from .dto import LockBenefitRequest
from application.model import ApplierSubTypes
from application.repository.api import APIRepository
from order_api import OrderService
from order_api.dto import CustomProperty

logger = logging.getLogger(__name__)


class LockBenefitInteractor(object):
    def __init__(
        self,            # type: LockBenefitInteractor
        api_repository,  # type: APIRepository
    ):
        # type: (...) -> None

        self.api_repository = api_repository

    def lock_benefit(
        self,       # type: LockBenefitInteractor
        request,    # type: LockBenefitRequest
    ):
        # type: (...) -> str

        if request.benefit.get("applierSubType") == ApplierSubTypes.LOYALTY:
            self._update_applied_loyalty_on_total(
                pos_id=request.pos_id,
                benefit_id=request.benefit["id"],
            )

        logger.info("Locking benefit: {}; PosId: {}".format(request.benefit.get("id"), request.pos_id))
        lock_id = self.api_repository.lock_benefit(
            benefit=request.benefit,
            pos_id=request.pos_id,
            payment_info=request.payment_info,
        )
        message = "Benefit {}; PosId: {} locked with lock id: {}"
        logger.info(message.format(request.benefit.get("id"), request.pos_id, lock_id))
        return lock_id

    def _update_applied_loyalty_on_total(
        self,           # type: LockBenefitInteractor
        pos_id,         # type: int
        benefit_id,     # type: str
    ):
        # type: (...) -> None

        order_service = OrderService(
            pos_id=pos_id,
            message_bus=self.api_repository.message_bus,
        )
        order_picture = order_service.get_order_picture()
        prop = order_picture.find(".//OrderProperty[@key='LOYALTY_COUPONS_TO_APPLY_ON_TOTAL']")
        loyalty_on_total = json.loads(prop.get("value") or "[]") if prop is not None else []

        if benefit_id not in loyalty_on_total:
            loyalty_on_total.append(benefit_id)

        order_service.set_order_custom_property(custom_property=CustomProperty(
            key="LOYALTY_COUPONS_TO_APPLY_ON_TOTAL",
            value=json.dumps(loyalty_on_total),
        ))
