import {
  AddIntrest,
  GetUserInterests,
  HasUserInterest,
  RemoveInterest,
} from "~/server/services/interests.service";
import { createTRPCRouter, protectedProcedure } from "~/server/api/trpc";
import z from "zod";
import { zAnnuncioId, zUserId } from "~/server/utils/zod_types";
import { NewMail } from "~/server/services/mailer";
import { findUser_byId_MINI } from "~/server/services/user.service";
import { db } from "~/server/db";
import { env } from "~/env.mjs";
import { TRPCError } from "@trpc/server";

export const intrestsRouter = createTRPCRouter({
  addIntrest: protectedProcedure
    .input(
      z.object({
        annuncioId: zAnnuncioId,
        /**Optional */
        userId: zUserId.optional(),
      }),
    )
    .mutation(async ({ ctx, input }) => {
      const userId = input.userId || ctx.session.id;
      await AddIntrest({
        annuncioId: input.annuncioId,
        userId,
      });
      const annuncio = await db
        .selectFrom("annunci")
        .select(["id", "codice", "titolo_it"])
        .where("id", "=", input.annuncioId)
        .executeTakeFirst();
      if (!annuncio) {
        throw new TRPCError({
          code: "NOT_FOUND",
          message: "Annuncio not found",
        });
      }
      const user = await findUser_byId_MINI({
        userId,
      });
      if (!user) {
        throw new TRPCError({
          code: "NOT_FOUND",
          message: "User not found",
        });
      }
      await NewMail({
        userId,
        mailType: "generic",
        to: "web@infoalloggi.it",
        subject: "Utente interessato ad un annuncio",
        props: {
          title: "Nuovo interesse per un annuncio",
          testo: `L'utente ${user.username} (${user.email}) ha mostrato interesse per l'annuncio "${annuncio.titolo_it}" (Codice: ${annuncio.codice}).`,

          link: {
            href: `${env.NEXT_PUBLIC_BASE_URL}/area-riservata/admin/user-view/ricerca/${userId}`,
            label: "Visualizza utente",
          },
        },
      });
      return { success: true };
    }),
  removeIntrest: protectedProcedure
    .input(
      z.object({
        annuncioId: zAnnuncioId,
        userId: zUserId.optional(),
      }),
    )
    .mutation(async ({ ctx, input }) => {
      return await RemoveInterest({
        annuncioId: input.annuncioId,
        userId: input.userId || ctx.session.id,
      });
    }),
  hasUserInterest: protectedProcedure
    .input(
      z.object({
        annuncioId: zAnnuncioId,
        userId: zUserId.optional(),
      }),
    )
    .query(async ({ ctx, input }) => {
      return await HasUserInterest({
        annuncioId: input.annuncioId,
        userId: input.userId || ctx.session.id,
      });
    }),
  getUserInterests: protectedProcedure
    .input(
      z.object({
        userId: zUserId.optional(),
      }),
    )
    .query(async ({ input, ctx }) => {
      return await GetUserInterests(input.userId || ctx.session.id);
    }),
  getUserInterestsAnnunci: protectedProcedure
    .input(
      z.object({
        userId: zUserId.optional(),
      }),
    )
    .query(async ({ input, ctx }) => {
      const interests = await GetUserInterests(input.userId || ctx.session.id);

      return await db
        .selectFrom("annunci")
        .select([
          "annunci.id",
          "annunci.codice",
          "annunci.prezzo",
          "annunci.desc_en",
          "annunci.desc_it",
          "annunci.url_immagini",
          "annunci.titolo_en",
          "annunci.titolo_it",
          "annunci.tipo",
          "annunci.consegna",
          "annunci.stato",
          "annunci.web",
        ])
        .where("web", "=", true)
        .where("stato", "!=", "Sospeso")
        .where("annunci.id", "in", interests)
        .execute();
    }),
});
