import { Hono } from "hono";
import type { AppConfig } from "../config.js";
import { MiddlewareManager } from "../middlewares/middleware.js";
import { getClientAuthRouter } from "./clientAuth.js";
import type { BaseEnv } from "../types/app.types.js";
import { getAdminRouter } from "./admin.js";
import { getAuthenticatedRouter } from "./authRouter.js";
import { getPublicClientInvitesRouter } from "./clientInvites.js";
import { getClientPortalRouter } from "./clientPortal.js";
import { getMaybeAuthenticatedRouter } from "./maybeAuthRouter.js";
import { getPublicRouter } from "./public.js";
import { getRevenueCatWebhookRouter } from "./revenuecat.js";
import { getStripeWebhookRouter } from "./stripe.js";
import { getTaskRouter } from "./tasks.js";

export const getMainRouter = (config: AppConfig) => {
  const mainRouter = new Hono<BaseEnv>();

  const middlewareManager = MiddlewareManager.getInstance();

  // Apply supabase middleware globally (needed by all routes)
  mainRouter.use(middlewareManager.supabase);

  // Apply remaining middlewares after public routes
  mainRouter.use(middlewareManager.r2);
  mainRouter.use(middlewareManager.transporter);
  mainRouter.use(middlewareManager.stripe);
  mainRouter.use(middlewareManager.stripeSync);

  // public routes
  mainRouter.route("/public", getPublicRouter());

  // tasks routes
  mainRouter.route("/tasks", getTaskRouter());

  // webhooks
  mainRouter.route("/revenuecat-webhook", getRevenueCatWebhookRouter(config));
  mainRouter.route("/stripe-webhook", getStripeWebhookRouter());

  // admin routes
  mainRouter.route("/admin", getAdminRouter(config));

  // public client auth routes
  mainRouter.route(
    "/client-auth",
    getClientAuthRouter({
      apiBaseUrl: config.API_BASE_URL,
      clientsUrl: config.CLIENTS_URL,
      cookieDomain: config.CLIENT_AUTH_COOKIE_DOMAIN,
      cookieName: config.CLIENT_AUTH_COOKIE_NAME,
      jwtSecret: config.CLIENT_AUTH_JWT_SECRET,
      magicLinkTtlMinutes: config.CLIENT_MAGIC_LINK_TTL_MINUTES,
      sessionTtlDays: config.CLIENT_SESSION_TTL_DAYS,
    })
  );

  mainRouter.route("/client-portal", getClientPortalRouter());

  // public client onboarding routes
  mainRouter.route("/client-invites", getPublicClientInvitesRouter());

  // maybe authenticated routes (checked first to allow unauthenticated booking)
  mainRouter.route("/", getMaybeAuthenticatedRouter());

  // authenticated routes
  mainRouter.route("/", getAuthenticatedRouter(config));

  return mainRouter;
};

/**
 * Type-safe API routes for RPC usage
 * Use with hono/client: const client = hc<ApiRoutes>('http://localhost:8080')
 */
export type ApiRoutes = ReturnType<typeof getMainRouter>;
