
import { Prop, Schema, SchemaFactory } from '@nestjs/mongoose';
import { Document, HydratedDocument, Schema as MongooseSchema } from 'mongoose';
export type UsersDocument = HydratedDocument<Users>;

export enum UserType {
    SUPER_ADMIN = 'SUPER_ADMIN',
    POLICY_STAFF = 'POLICY_STAFF',
    ADMIN_STAFF = 'ADMIN_STAFF',
    AGENT = 'AGENT'
}

// Roles that log in through the admin panel. AGENT has a separate login.
export const STAFF_ROLES = [UserType.POLICY_STAFF, UserType.ADMIN_STAFF];
export const PANEL_ROLES = [UserType.SUPER_ADMIN, ...STAFF_ROLES];

export enum AgentStatus {
    INVITED = 'INVITED',     // invite sent, not opened yet
    ACCEPTED = 'ACCEPTED',   // agent accepted, filling KYC
    SUBMITTED = 'SUBMITTED', // KYC submitted, waiting for admin review
    APPROVED = 'APPROVED',
    REJECTED = 'REJECTED'    // agent must resubmit (or admin reopens)
}

export enum AgentDocumentType {
    PAN = 'PAN',
    AADHAAR = 'AADHAAR',
    ADDRESS_PROOF = 'ADDRESS_PROOF',
    LICENSE_CERTIFICATE = 'LICENSE_CERTIFICATE'
}

export enum AgentDocumentStatus {
    PENDING = 'PENDING',
    APPROVED = 'APPROVED',
    REJECTED = 'REJECTED'
}

export enum Language {
    EN = 'en',
    HI = 'hi'
}

const AgentDocumentSchema = new MongooseSchema({
    type: { type: String, enum: Object.values(AgentDocumentType), required: true },
    number: { type: String, default: null },
    file: { type: MongooseSchema.Types.Mixed, required: true }, // as returned by POST /uploads/file
    status: { type: String, enum: Object.values(AgentDocumentStatus), default: AgentDocumentStatus.PENDING },
    uploaded_at: { type: Number, default: () => +new Date() }
}, { _id: false });

@Schema()
export class Users extends Document {
    @Prop({ type: String, default: null })
    phone_no: string;

    @Prop({ type: String, default: null })
    country_code: string;

    @Prop({ type: Boolean, default: false })
    is_phone_verified: boolean;

    @Prop({ type: String, default: null })
    email: string; // unique when set (see partial index below); agents may have none

    @Prop({ type: String, default: null })
    username: string;

    @Prop({ type: String, default: null , select: false })
    password: string;

    @Prop({ type: Boolean, default: false })
    is_email_verified: boolean;

    @Prop({ type: Boolean, default: true })
    is_active: boolean; // false = deactivated, cannot log in

    // ----- Agent fields: only set when user_type is AGENT -----

    @Prop({ type: Number })
    agent_no: number;

    @Prop({ type: String })
    agent_code: string; // e.g. AG-8041

    @Prop({ type: String, enum: AgentStatus })
    agent_status: AgentStatus;

    @Prop({ type: MongooseSchema.Types.ObjectId, ref: 'regions', default: null })
    region_id: any;

    @Prop({ type: [{ type: MongooseSchema.Types.ObjectId, ref: 'categories' }], default: undefined })
    category_ids: any[]; // categories the agent may sell

    @Prop({ type: MongooseSchema.Types.ObjectId, default: null })
    invited_by: any;

    @Prop({ type: Number, default: null })
    invited_at: number;

    @Prop({ type: Number, default: null })
    accepted_at: number;

    @Prop({ type: String, default: null })
    irdai_number: string;

    @Prop({ type: Number, default: null })
    training_hours: number;

    @Prop({ type: [AgentDocumentSchema], default: undefined })
    kyc_documents: any[];

    @Prop({ type: Number, default: null })
    kyc_submitted_at: number;

    @Prop({ type: MongooseSchema.Types.ObjectId, default: null })
    kyc_reviewed_by: any;

    @Prop({ type: Number, default: null })
    kyc_reviewed_at: number;

    @Prop({ type: String, default: null })
    kyc_reject_reason: string;

    @Prop({ type: String, default: null, select: false })
    password_reset_token: string; // sha256 hash of the emailed reset token

    @Prop({ type: Number, default: null, select: false })
    password_reset_expires_at: number;

    @Prop({ type: String, default: null })
    profile_pic: string;

    @Prop({ type: String, default: null })
    name: string;

    @Prop({ type: String, default: null })
    socket_id: string;

    @Prop({ type: Boolean, default: false })
    is_online: boolean;

    @Prop({ type: String, enum: UserType, default: UserType.AGENT })
    user_type: UserType;

    @Prop({ type: Number, default: +new Date() })
    created_at: number;

    @Prop({ type: Number, default: +new Date() })
    updated_at: number;

    @Prop({ type: String, enum: Language, default: Language.EN })
    language: Language;

    @Prop({ type: Boolean, default: false })
    is_profile_complete: boolean;

    @Prop({ type: Boolean, default: false })
    is_deleted: boolean;
}

export const UserSchema = SchemaFactory.createForClass(Users);
UserSchema.index({ email: 1 }, { unique: true, partialFilterExpression: { email: { $type: 'string' } } });
UserSchema.index({ agent_no: 1 }, { unique: true, partialFilterExpression: { agent_no: { $type: 'number' } } });
