from __future__ import annotations

from adapter.matrix.handlers.chat import (
    handle_list_chats,
    make_handle_archive,
    make_handle_new_chat,
    make_handle_rename,
)
from adapter.matrix.handlers.confirm import make_handle_cancel, make_handle_confirm
from adapter.matrix.handlers.context_commands import (
    make_handle_context,
    make_handle_load,
    make_handle_reset,
    make_handle_save,
)
from adapter.matrix.handlers.settings import (
    handle_help,
    handle_settings,
    handle_settings_connectors,
    handle_settings_plan,
    handle_settings_safety,
    handle_settings_skills,
    handle_settings_soul,
    handle_settings_status,
    handle_settings_whoami,
    handle_toggle_skill,
    handle_unknown_command,
)
from core.handler import EventDispatcher
from core.protocol import IncomingCallback, IncomingCommand


def register_matrix_handlers(
    dispatcher: EventDispatcher,
    client=None,
    store=None,
    registry=None,
    prototype_state=None,
    agent_base_url: str = "http://127.0.0.1:8000",
) -> None:
    dispatcher.register(IncomingCommand, "new", make_handle_new_chat(client, store, registry))
    dispatcher.register(IncomingCommand, "chats", handle_list_chats)
    dispatcher.register(IncomingCommand, "rename", make_handle_rename(client, store))
    dispatcher.register(IncomingCommand, "archive", make_handle_archive(client, store))
    dispatcher.register(IncomingCommand, "help", handle_help)
    dispatcher.register(IncomingCommand, "settings", handle_settings)
    if prototype_state is not None:
        clear_handler = make_handle_reset(store, prototype_state)
        dispatcher.register(IncomingCommand, "clear", clear_handler)
        dispatcher.register(IncomingCommand, "reset", clear_handler)
    else:
        dispatcher.register(IncomingCommand, "reset", handle_settings)
    dispatcher.register(IncomingCommand, "settings_skills", handle_settings_skills)
    dispatcher.register(IncomingCommand, "settings_connectors", handle_settings_connectors)
    dispatcher.register(IncomingCommand, "settings_soul", handle_settings_soul)
    dispatcher.register(IncomingCommand, "settings_safety", handle_settings_safety)
    dispatcher.register(IncomingCommand, "settings_plan", handle_settings_plan)
    dispatcher.register(IncomingCommand, "settings_status", handle_settings_status)
    dispatcher.register(IncomingCommand, "settings_whoami", handle_settings_whoami)

    dispatcher.register(IncomingCallback, "confirm", make_handle_confirm(store))
    dispatcher.register(IncomingCallback, "cancel", make_handle_cancel(store))
    dispatcher.register(IncomingCallback, "toggle_skill", handle_toggle_skill)
    dispatcher.register(IncomingCommand, "*", handle_unknown_command)

    if prototype_state is not None:
        dispatcher.register(
            IncomingCommand,
            "save",
            make_handle_save(None, store, prototype_state),
        )
        dispatcher.register(IncomingCommand, "load", make_handle_load(store, prototype_state))
        dispatcher.register(IncomingCommand, "context", make_handle_context(store, prototype_state))
