from aiohttp import web

from maps_adv.manul.lib.api_providers import ClientsApiProvider, OrdersApiProvider
from maps_adv.manul.lib.db import DB

from . import middlewares
from .resources import clients, orders, ping


def create(
    db: DB, clients_provider: ClientsApiProvider, orders_provider: OrdersApiProvider
) -> web.Application:
    api = web.Application(
        middlewares=[
            middlewares.handle_validation_exception,
            middlewares.handle_client_exists_exception,
            middlewares.handle_client_not_found_exception,
            middlewares.handle_order_not_found_exception,
        ]
    )

    ping_resources = ping.Resources(db)
    clients_resources = clients.Resources(clients_provider)
    orders_resources = orders.Resources(orders_provider)

    api.add_routes(
        [
            # ping
            web.get("/ping", ping_resources.ping),
            # clients
            web.post("/clients/", clients_resources.create_client),
            web.get(r"/clients/{client_id:\d+}/", clients_resources.retrieve_client),
            web.put(r"/clients/{client_id:\d+}/", clients_resources.update_client),
            web.post(
                r"/clients/set-account-manager/",
                clients_resources.set_account_manager_for_client,
            ),
            web.get("/clients/", clients_resources.list_clients),
            # orders
            web.post("/orders/", orders_resources.create_order),
            web.get(r"/orders/{order_id:\d+}/", orders_resources.retrieve_order),
            web.post("/orders/list/", orders_resources.list_orders),
            web.post(
                "/orders/by-account-manager/",
                orders_resources.retrieve_order_ids_for_account,
            ),
        ]
    )

    return api
