import { Body, Controller, Delete, Get, Param, Patch, Post, UseGuards } from "@nestjs/common";
import { Tenant } from "../../common/decorators/tenant.decorator";
import { JwtAuthGuard } from "../../common/guards/jwt-auth.guard";
import { TenantBodyGuard } from "../../common/guards/tenant-body.guard";
import { PrismaService } from "../../infra/prisma/prisma.service";
import { CreateUserDto } from "./dto/create-user.dto";
import { UpdateCompanyDto } from "../dashboard/dto/update-company.dto";
import { AuthService } from "./auth.service";

@UseGuards(JwtAuthGuard, TenantBodyGuard)
@Controller()
export class UsersController {
  constructor(private readonly prisma: PrismaService) {}

  @Get("users")
  async findAllUsers(@Tenant() companyId: string) {
    const users = await this.prisma.user.findMany({
      where: { companyId },
      select: {
        id: true,
        name: true,
        email: true,
        role: true,
        active: true,
        avatarUrl: true,
        createdAt: true,
      },
      orderBy: { name: "asc" },
    });

    return users.map((u) => ({
      ...u,
      createdAt: u.createdAt.toISOString(),
    }));
  }

  @Post("users")
  async createUser(@Tenant() companyId: string, @Body() dto: CreateUserDto) {
    // Use 12 bcrypt rounds for stronger security
    const passwordHash = await AuthService.hashPassword(dto.password);
    const user = await this.prisma.user.create({
      data: {
        companyId,
        name: dto.name,
        email: dto.email,
        passwordHash,
        role: dto.role,
        active: dto.active ?? true,
      },
      select: {
        id: true,
        name: true,
        email: true,
        role: true,
        active: true,
        createdAt: true,
      },
    });

    return {
      ...user,
      createdAt: user.createdAt.toISOString(),
    };
  }

  @Patch("users/:id")
  async updateUser(
    @Tenant() companyId: string,
    @Param("id") id: string,
    @Body() dto: Partial<CreateUserDto>
  ) {
    const updated = await this.prisma.user.update({
      where: { id },
      data: {
        ...(dto.name ? { name: dto.name } : {}),
        ...(dto.email ? { email: dto.email } : {}),
        ...(dto.role ? { role: dto.role } : {}),
        ...(dto.active !== undefined ? { active: dto.active } : {}),
      },
      select: {
        id: true,
        name: true,
        email: true,
        role: true,
        active: true,
        createdAt: true,
      },
    });

    return {
      ...updated,
      createdAt: updated.createdAt.toISOString(),
    };
  }

  @Delete("users/:id")
  async deleteUser(@Tenant() companyId: string, @Param("id") id: string) {
    await this.prisma.user.delete({
      where: { id },
    });
    return { success: true };
  }

  @Get("company")
  async getCompany(@Tenant() companyId: string) {
    // Busca pela empresa correta do tenant
    const company = await this.prisma.company.findUnique({
      where: { id: companyId },
    });

    if (!company) {
      // fallback: tenta encontrar qualquer empresa
      const fallback = await this.prisma.company.findFirst();
      if (fallback) return fallback;
      return {
        id: companyId,
        legalName: "",
        tradeName: "",
        document: "",
        email: "",
        phone: "",
        logoUrl: null,
      };
    }

    return company;
  }

  @Patch("company")
  async updateCompany(@Tenant() companyId: string, @Body() dto: UpdateCompanyDto) {
    const existing = await this.prisma.company.findUnique({
      where: { id: companyId },
    });

    if (!existing) {
      return this.prisma.company.create({
        data: {
          id: companyId,
          legalName: dto.legalName || "",
          tradeName: dto.tradeName || "",
          document: dto.document || "",
          email: dto.email || "",
          phone: dto.phone || "",
        },
      });
    }

    const updated = await this.prisma.company.update({
      where: { id: existing.id },
      data: {
        ...(dto.legalName !== undefined ? { legalName: dto.legalName } : {}),
        ...(dto.tradeName !== undefined ? { tradeName: dto.tradeName } : {}),
        ...(dto.document !== undefined ? { document: dto.document } : {}),
        ...(dto.email !== undefined ? { email: dto.email } : {}),
        ...(dto.phone !== undefined ? { phone: dto.phone } : {}),
        ...(dto.logoUrl !== undefined ? { logoUrl: dto.logoUrl } : {}),
      },
    });

    return updated;
  }
}
