import bcrypt from "bcrypt";
import jwt from "jsonwebtoken";
import { ENV } from "@/config/env.js";
import { SessionService } from "@/modules/auth/service/session.service.js";
import AdminModel from "../model/admin.model.js";
import { Types } from "mongoose";
export default class AdminAuthService {
  private sessionService: SessionService;
  constructor() {
    this.sessionService = new SessionService();
  }
  async registerInitialAdmin(): Promise<{ success: boolean; message: string }> {
    const existing = await AdminModel.find();
    if (existing.length > 0) {
      return {
        success: true,
        message:
          "Admin is already registered, Please login using the credentials as provided by the developer team.",
      };
    }
    const password = "Admin@123";
    const name = "Admin";
    const email = "admin@backend.com";
    const hash = await bcrypt.hash(password, 10);
    await AdminModel.create({
      name,
      email,
      password: hash,
    });
    return {
      success: true,
      message:
        "Admin registered successfully, you can login using the credentials email",
    };
  }
  async login(
    body: any,
    opts: {
      userAgent?: string;
      deviceName?: string;
    },
  ): Promise<{
    admin: any;
    accessToken: string;
    refreshToken: string;
  }> {
    const { email, password } = body;
    const admin = await AdminModel.findOne({
      email: email.toLowerCase().trim(),
    });
    if (!admin) {
      throw new Error("Invalid credentials");
    }
    const isMatch = await bcrypt.compare(password, admin.password);
    if (!isMatch) {
      throw new Error("Invalid credentials");
    }
    const payload = {
      _id: admin._id.toString(),
      name: admin.name,
      email: admin.email,
      user_type: admin.user_type,
    };
    const token = jwt.sign(payload, ENV.JWT_SECRET);
    const { accessToken, refreshToken } =
      await this.sessionService.createSession(
        admin._id.toString(),
        token,
        { ...opts, userType: "admin" },
      );
    const adminResponse = {
      _id: admin._id,
      name: admin.name,
      email: admin.email,
      user_type: admin.user_type,
      avatar: admin.avatar,
      createdAt: (admin as any).createdAt,
    };
    return { admin: adminResponse, accessToken, refreshToken };
  }
  async logout(sessionId: string | Types.ObjectId): Promise<void> {
    await this.sessionService.revokeSession(sessionId.toString());
  }
}
