from .thread import Thread
from .components import MessageSelectMenu, MessageButton
from .interactions import MessageInteraction
from .partials import PartialMember
from .role import Role
from .mentions import (
    MentionedUser,
    MentionedChannel
)    
from .application import Application
from .webhook import WebhookUser
from .user import User
from .reaction import Reaction
from typing import (
    Optional,
    List,
    Union
)
from .embed import Embed

class Message:
    def __init__(self, data: dict):
        self.id: str = data["id"]
        self.channel_id: str = data["channel_id"]
        self.guild_id: Optional[str] = data["guild_id"] or None
        self.webhook_id: Optional[str] = data["webhook_id"] or None
        self.author: Optional[User] if not self.webhook_id else WebhookUser = WebhookUser(data["author"]) if self.webhook_id else User(data["author"])
        self.member: Optional[PartialMember] = PartialMember(data["member"]) if data["member"] else None
        self.content: str = data["content"]
        self.timestamp: str = data["timestamp"]
        self.edited_timestamp: Optional[str] = data["edited_timestamp"] or None
        self.tts: bool = data["tts"]
        self.mention_everyone: bool = data["mention_everyone"]
        self.mentions: List[MentionedUser] = [MentionedUser(mention) for mention in data["mentions"]]
        self.mention_roles: List[Role] = [Role(role) for role in data["mention_roles"]]
        self.mention_channels: List[MentionedChannel] = [MentionedChannel(channel) for channel in data["mention_channels"]]
        self.embeds: List[Embed] = [Embed(embed) for embed in data["embeds"]]
        self.reactions: Optional[List[Reaction]] = [Reaction(reaction) for reaction in data["reactions"]]
        self.nonce: Optional[str] = data["nonce"] or None
        self.pinned: bool = data["pinned"]
        self.type: int = data["type"]
        self.activity: int = data["activity"]
        self.application: Application = Application(data["application"]) # Despite there being a PartialApplication, Discord don't specify what attributes it has
        self.flags: int = data["flags"]
        self.referenced_message: Optional[Message] = Message(data["referenced_message"]) if data["referenced_message"] else None
        self.interaction: Optional[MessageInteraction] = MessageInteraction(data["interaction"]) if data["interaction"] else None
        self.thread: Thread = Thread(data["thread"]) if data["thread"] else None
        self.components: List[Union[MessageSelectMenu, MessageButton]]