import { Injectable, OnModuleInit, ConflictException, BadRequestException, Logger } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import { Model } from 'mongoose';
import { DropdownOption, DropdownOptionDocument } from './dropdown-option.schema';

const VALID_CATEGORIES = [
    'religion',
    'caste',
    'medium',
    'nationality',
    'guardianRelation',
    'bloodGroup',
] as const;

const DEFAULTS: Record<string, string[]> = {
    religion: ['Hindu', 'Muslim', 'Christian', 'Sikh', 'Buddhist', 'Jain', 'Parsi', 'Jewish', 'Other'],
    caste: ['SC', 'ST', 'OBC', 'General'],
    medium: ['English', 'Bengali', 'Hindi', 'Other'],
    nationality: ['Indian', 'Bangladeshi', 'Nepali', 'Sri Lankan', 'Other'],
    guardianRelation: ['Father', 'Mother', 'Uncle', 'Aunt', 'Grandparent', 'Other'],
    bloodGroup: ['A+', 'A-', 'B+', 'B-', 'AB+', 'AB-', 'O+', 'O-'],
};

@Injectable()
export class DropdownOptionsService implements OnModuleInit {
    private readonly logger = new Logger(DropdownOptionsService.name);

    constructor(
        @InjectModel(DropdownOption.name)
        private readonly model: Model<DropdownOptionDocument>,
    ) {}

    async onModuleInit() {
        await this.seedDefaults();
    }

    private async seedDefaults() {
        for (const [category, values] of Object.entries(DEFAULTS)) {
            for (const value of values) {
                const exists = await this.model
                    .findOne({ category, value })
                    .collation({ locale: 'en', strength: 2 })
                    .lean();
                if (!exists) {
                    await this.model.create({ category, value, isDefault: true });
                }
            }
        }
        this.logger.log('Dropdown option defaults seeded');
    }

    async findByCategory(category: string): Promise<DropdownOption[]> {
        return this.model
            .find({ category })
            .sort({ isDefault: -1, value: 1 })
            .lean();
    }

    async create(category: string, value: string): Promise<DropdownOption> {
        if (!VALID_CATEGORIES.includes(category as any)) {
            throw new BadRequestException(`Invalid category: ${category}`);
        }

        const trimmed = value.trim();
        if (!trimmed) {
            throw new BadRequestException('Value is required');
        }

        const existing = await this.model
            .findOne({ category, value: trimmed })
            .collation({ locale: 'en', strength: 2 })
            .lean();
        if (existing) {
            throw new ConflictException(`"${trimmed}" already exists in ${category}`);
        }

        const doc = await this.model.create({ category, value: trimmed, isDefault: false });
        return doc.toObject();
    }
}
