# -*- coding: utf-8 -*-

import os

from typing import Optional

import cfgtools

from posot import OrderTaker
from sysactions import (
    show_messagebox,
    show_keyboard,
    StopAction,
    get_current_order,
    get_model
)

from utilfunctions import (
    validate_document,
    update_custom_properties,
    get_custom_property_value,
    input_document_pinpad_dialog
)
from model.customexception import RequiredDocumentException

document_required_value = None


def validate_required_document(
    pos_id,                     # type: str
    pos_ot,                     # type: OrderTaker
    total_gross,                # type: float
    amount,                     # type: str
    due_amount,                 # type: float
    ask_document_pinpad=False   # type: Optional[bool]
):
    # type: (...) -> None

    model = get_model(pos_id)
    required_value = _get_document_required_value()
    ask_for_doc = document_required_value != 0.0 and (float(total_gross) >= required_value)
    last_payment = amount == "" or (float(amount) >= float(due_amount))
    document = get_custom_property_value(pos_id, 'CUSTOMER_DOC')

    if ask_for_doc and last_payment and document is None:
        message = "$DOC_REQUIRED|%s" % "{0:.2f}".format(required_value)
        show_messagebox(pos_id, message, "$INFORMATION")

        document = get_customer_doc(
            pos_id,
            pos_ot,
            required=True,
            ask_document_pinpad=ask_document_pinpad
        )
        order_properties_dict = update_custom_properties(customer_doc=document)
        if len(order_properties_dict) > 0:
            order = get_current_order(model)
            pos_ot.setOrderCustomProperties(order_properties_dict, orderid=order.get("orderId"))


def get_customer_doc(
    pos_id,                      # type: str
    pos_ot,                      # type: OrderTaker
    default_doc="",              # type: Optional[str]
    required=False,              # type: bool
    ask_document_pinpad=False,   # type: Optional[bool]
    stop_action=True             # type: Optional[bool]
):
    # type: (...) -> str

    valid = False
    customer_doc = None
    while not valid:
        if ask_document_pinpad:
            customer_doc = input_document_pinpad_dialog(pos_id)

        if customer_doc is None:
            message = "$ONLY_NUMBERS"
            title = "$ENTER_CPF_CNPJ"
            customer_doc = show_keyboard(pos_id, message, title=title, mask="CPF_CNPJ", numpad=True, defvalue=default_doc)

        if customer_doc is None:
            if required:
                raise RequiredDocumentException()
            if stop_action:
                raise StopAction()
            return ""

        if customer_doc == "" and not required:
            customer_doc = ""
            break

        valid = validate_document(customer_doc)
        if not valid:
            customer_doc = None
            show_messagebox(pos_id, "$INVALID_CPF_CNPJ")

    fill_additional_info(pos_ot, "CPF", customer_doc)

    return customer_doc


def fill_additional_info(
        pos_ot,         # type: OrderTaker
        properties,     # type: str
        value           # type: str
):
    # type: (...) -> None

    if pos_ot.additionalInfo:
        pos_ot.additionalInfo += "|"
    else:
        pos_ot.additionalInfo = ""

    pos_ot.additionalInfo += "{0}={1}".format(properties, value)


def _get_document_required_value():
    # type: (...) -> float

    global document_required_value

    if document_required_value is None:
        config = cfgtools.read(os.environ["LOADERCFG"])
        document_required_value = float(config.find_value("Customizations.DocumentRequiredValue") or 0)

    return document_required_value
