// validations/customerValidation.js
const Joi = require('joi');

const customerValidationSchema = Joi.object({
  tenantId: Joi.string()
    .required()
    .regex(/^[0-9a-fA-F]{24}$/)
    .messages({
      'any.required': 'Tenant ID is required',
      'string.empty': 'Tenant ID cannot be empty',
      'string.pattern.base': 'Tenant ID must be a valid MongoDB ObjectId'
    }),
    
  caseNo: Joi.string()
    .required()
    .max(100)
    .trim()
    .messages({
      'any.required': 'Case number is required',
      'string.empty': 'Case number cannot be empty',
      'string.max': 'Case number cannot exceed 100 characters'
    }),
    
  name: Joi.string()
    .required()
    .max(100)
    .min(2)
    .trim()
    .messages({
      'any.required': 'Customer name is required',
      'string.empty': 'Customer name cannot be empty',
      'string.min': 'Customer name must be at least 2 characters long',
      'string.max': 'Customer name cannot exceed 100 characters'
    }),
    
  mobile: Joi.string()
    .required()
    .max(15)
    .min(10)
    .pattern(/^[0-9+\-\s()]+$/)
    .trim()
    .messages({
      'any.required': 'Mobile number is required',
      'string.empty': 'Mobile number cannot be empty',
      'string.min': 'Mobile number must be at least 10 characters long',
      'string.max': 'Mobile number cannot exceed 15 characters',
      'string.pattern.base': 'Mobile number can only contain digits, +, -, spaces, and parentheses'
    }),
    
  dob: Joi.date()
    .optional()
    .max('now')
    .messages({
      'date.base': 'Date of birth must be a valid date',
      'date.max': 'Date of birth cannot be in the future'
    }),
    
  gender: Joi.string()
    .optional()
    .valid('male', 'female', 'other')
    .messages({
      'any.only': 'Gender must be one of: male, female, or other'
    }),
    
  kycStatus: Joi.string()
    .optional()
    .valid('pending', 'approved', 'rejected')
    .default('pending')
    .messages({
      'any.only': 'KYC status must be one of: pending, approved, or rejected'
    })
});

const updateCustomerValidationSchema = Joi.object({
  tenantId: Joi.string()
    .optional()
    .regex(/^[0-9a-fA-F]{24}$/)
    .messages({
      'string.pattern.base': 'Tenant ID must be a valid MongoDB ObjectId'
    }),
    
  caseNo: Joi.string()
    .optional()
    .max(100)
    .min(1)
    .trim()
    .messages({
      'string.min': 'Case number cannot be empty',
      'string.max': 'Case number cannot exceed 100 characters'
    }),
    
  name: Joi.string()
    .optional()
    .max(100)
    .min(2)
    .trim()
    .messages({
      'string.min': 'Customer name must be at least 2 characters long',
      'string.max': 'Customer name cannot exceed 100 characters'
    }),
    
  mobile: Joi.string()
    .optional()
    .max(15)
    .min(10)
    .pattern(/^[0-9+\-\s()]+$/)
    .trim()
    .messages({
      'string.min': 'Mobile number must be at least 10 characters long',
      'string.max': 'Mobile number cannot exceed 15 characters',
      'string.pattern.base': 'Mobile number can only contain digits, +, -, spaces, and parentheses'
    }),
    
  dob: Joi.date()
    .optional()
    .max('now')
    .messages({
      'date.base': 'Date of birth must be a valid date',
      'date.max': 'Date of birth cannot be in the future'
    }),
    
  gender: Joi.string()
    .optional()
    .valid('male', 'female', 'other')
    .messages({
      'any.only': 'Gender must be one of: male, female, or other'
    }),
    
  kycStatus: Joi.string()
    .optional()
    .valid('pending', 'approved', 'rejected')
    .messages({
      'any.only': 'KYC status must be one of: pending, approved, or rejected'
    })
});

function validateCustomer(req, res, next) {
  const { error, value } = customerValidationSchema.validate(req.body, { 
    abortEarly: false,
    stripUnknown: true,
    convert: true
  });
  
  if (error) {
    return res.status(400).json({
      success: false,
      error: 'Customer validation failed',
      code: 'VALIDATION_ERROR',
      details: error.details.map(detail => ({
        field: detail.path.join('.'),
        message: detail.message,
        value: detail.context?.value
      }))
    });
  }
  
  req.body = value;
  next();
}

// Middleware to validate update customer payload
function updateValidateCustomer(req, res, next) {
  const { error, value } = updateCustomerValidationSchema.validate(req.body, { 
    abortEarly: false,
    stripUnknown: true,
    convert: true
  });
  
  if (error) {
    return res.status(400).json({
      success: false,
      error: 'Customer update validation failed',
      code: 'UPDATE_VALIDATION_ERROR',
      details: error.details.map(detail => ({
        field: detail.path.join('.'),
        message: detail.message,
        value: detail.context?.value
      }))
    });
  }
  
  // Replace req.body with validated and sanitized data
  req.body = value;
  next();
}

// Additional validation for checking if at least one field is provided for update
// function validateUpdateFields(req, res, next) {
//   const allowedFields = ['tenantId', 'caseNo', 'name', 'mobile', 'dob', 'gender', 'kycStatus'];
//   const providedFields = Object.keys(req.body);
  
//   if (providedFields.length === 0) {
//     return res.status(400).json({
//       success: false,
//       error: 'At least one field must be provided for update',
//       code: 'NO_UPDATE_FIELDS',
//       allowedFields
//     });
//   }
  
//   next();
// }

module.exports = {
  validateCustomer,
  updateValidateCustomer,
};