from typing import Optional

from boss.interactor.get_info.dto import GetInfoRequest
from boss.model import User
from boss.util import convert_user_dto_into_user_response
from boss_api.shared.exception import (
    NoData,
    NoUser,
    NoUtf8Data,
)
from messagebus import (
    AckMessage,
    Event,
    Message,
    MessageBus,
)
from ._BaseProcessor import BaseProcessor


class GetInfoProcessor(BaseProcessor):

    def parse_data(
        self,
        data: bytes,
    ) -> GetInfoRequest:

        if not data:
            raise NoData()

        try:
            data.decode()
        except UnicodeDecodeError:
            raise NoUtf8Data()

        try:
            user_id = int(data.decode())
        except ValueError:
            raise NoUser()

        if not user_id:
            raise NoUser()

        return GetInfoRequest(user_id=user_id)

    def format_response(
        self,
        message_bus: MessageBus,
        message: Message,
        event: Event,
        request: GetInfoRequest,
        result: Optional[User],
    ) -> None:

        if result is None:
            reply_message = AckMessage(data=b"<UserInfo/>")
        else:
            user = convert_user_dto_into_user_response(user=result)
            reply_data = f"<UserInfo>{user.get_info_response()}</UserInfo>"
            reply_message = AckMessage(data=reply_data.encode())

        message_bus.reply_message(
            message=message,
            reply_message=reply_message,
        )
