from logging import Logger

from interactor.route.order.remove_coupon.dto import RemoveCouponRequest
from model.config import Config
from model.error_type import PosValidationErrorsType
from model.exception import ValidationError
from model.repository import PosRepositoryModel
from model.services import OrderServiceModel
from validation_util import (
    validate_api_key,
    check_if_business_day_is_opened,
    check_if_operator_is_logged
)


class RemoveCouponInteractor(object):

    def __init__(
            self,
            logger,             # type: Logger
            config,             # type: Config
            pos_repository,     # type: PosRepositoryModel
            order_service       # type: OrderServiceModel
    ):
        # type: (...) -> None

        self.logger = logger
        self.config = config
        self.pos_repository = pos_repository
        self.order_service = order_service

    def execute(
            self,
            request  # type: RemoveCouponRequest
    ):
        # type: (...) -> None

        pos_id = validate_api_key(
                request=request,
                secure_api_key_list=self.config.api_key_mapping
        )
        if not pos_id:
            raise ValidationError(PosValidationErrorsType.PosIdNotFound)

        model = self.pos_repository.get_model(pos_id)
        pos_ot = self.pos_repository.get_pos_ot(model)

        check_if_business_day_is_opened(
                repository=self.pos_repository,
                model=model
        )
        check_if_operator_is_logged(
                repository=self.pos_repository,
                model=model
        )

        coupon_data, coupon_removed = self.pos_repository.remove_coupon(
                pos_id=pos_id,
                coupon_applied_id=request.coupon_applied_id
        )

        if coupon_removed:
            self.logger.info("Coupon successfully removed. CouponData: {}".format(coupon_data))
            order = self.pos_repository.get_current_order(model)
            order_id = order.get('orderId')
            order = self.pos_repository.get_order_details(
                    pos_id=pos_id,
                    order_id=order_id,
                    pos_ot=pos_ot
            )

            if not order:
                raise ValidationError(PosValidationErrorsType.OrderNotFound)

            order = self.order_service.convert_mw_order_to_order_detail(order)

            return order
        else:
            self.logger.info("Error removing coupon. CouponData: {}".format(coupon_data))
            raise ValidationError(PosValidationErrorsType.CannotApplyCoupon, coupon_data)
