import 'package:krow/core/application/common/validators/email_validator.dart';
import 'package:krow/core/application/common/validators/phone_validator.dart';
import 'package:krow/core/application/common/validators/social_number_validator.dart';
import 'package:krow/features/profile/wages_forms/domain/bloc/wages_form_bloc.dart';
import 'package:krow/features/profile/wages_forms/domain/entities/edd_form_entity.dart';
import 'package:krow/features/profile/wages_forms/domain/entities/i_nine_entity.dart';
import 'package:krow/features/profile/wages_forms/domain/entities/offer_letter_entity.dart';
import 'package:krow/features/profile/wages_forms/domain/entities/w_four_entity.dart';
import 'package:krow/features/profile/wages_forms/domain/utils/wage_form_visitor.dart';

/// Returns a Map of keys that represent the form fields and values that
/// represent corresponding error
class ValidatorWageFromVisitor implements WageFormVisitor<Map<String, String>> {
  const ValidatorWageFromVisitor();

  @override
  Map<String, String> visitEddForm(EddFormEntity entity) {
    final ssnError = SocialNumberValidator.validate(
      entity.socialNumber,
      isRequired: true,
    );

    return <String, String>{
      if (entity.firstName.isEmpty)
        WagesFormFields.firstName: 'Required to fill',
      if (entity.lastName.isEmpty) WagesFormFields.lastName: 'Required to fill',
      if (entity.address.isEmpty) WagesFormFields.address: 'Required to fill',
      if (entity.city.isEmpty) WagesFormFields.city: 'Required to fill',
      if (entity.state.isEmpty) WagesFormFields.state: 'Required to fill',
      if (entity.zipCode.isEmpty) WagesFormFields.zipCode: 'Required to fill',
      if (ssnError != null) WagesFormFields.socialNumber: ssnError,
    };
  }

  @override
  Map<String, String> visitINineForm(INineEntity entity) {
    final emailError = EmailValidator.validate(entity.email, isRequired: true);
    final phoneError = PhoneValidator.validate(
      entity.phoneNumber,
      isRequired: true,
    );
    final ssnError = SocialNumberValidator.validate(
      entity.socialNumber,
      isRequired: true,
    );

    final birthdate = entity.dateOfBirth;
    String? birthDateError;
    if (birthdate == null) {
      birthDateError = 'This field is required';
    } else {
      final now = DateTime.now();
      if (birthdate.isAfter(now)) {
        birthDateError = 'Future date selected';
      } else if (birthdate.difference(now).inDays.abs() < 5840) {
        birthDateError = 'Invalid date selected';
      }
    }

    return <String, String>{
      if (entity.firstName.isEmpty)
        WagesFormFields.firstName: 'Required to fill',
      if (entity.lastName.isEmpty) WagesFormFields.lastName: 'Required to fill',
      if (entity.address.isEmpty) WagesFormFields.address: 'Required to fill',
      if (entity.city.isEmpty) WagesFormFields.city: 'Required to fill',
      if (entity.state.isEmpty) WagesFormFields.state: 'Required to fill',
      if (entity.zipCode.isEmpty) WagesFormFields.zipCode: 'Required to fill',
      if (birthDateError != null) WagesFormFields.birthdate: birthDateError,
      if (ssnError != null) WagesFormFields.socialNumber: ssnError,
      if (emailError != null) WagesFormFields.email: emailError,
      if (phoneError != null) WagesFormFields.phone: phoneError,
    };
  }

  @override
  Map<String, String> visitOfferLetterFrom(OfferLetterEntity entity) {
    return <String, String>{
      if (entity.fullName.isEmpty) WagesFormFields.fullName: 'Required to fill',
      if (entity.city.isEmpty) WagesFormFields.city: 'Required to fill'
    };
  }

  @override
  Map<String, String> visitWFourForm(WFourEntity entity) {
    final ssnError = SocialNumberValidator.validate(
      entity.socialNumber,
      isRequired: true,
    );

    return <String, String>{
      if (entity.firstName.isEmpty)
        WagesFormFields.firstName: 'Required to fill',
      if (entity.lastName.isEmpty) WagesFormFields.lastName: 'Required to fill',
      if (entity.address.isEmpty) WagesFormFields.address: 'Required to fill',
      if (entity.city.isEmpty) WagesFormFields.city: 'Required to fill',
      if (entity.state.isEmpty) WagesFormFields.state: 'Required to fill',
      if (entity.zipCode.isEmpty) WagesFormFields.zipCode: 'Required to fill',
      if (ssnError != null) WagesFormFields.socialNumber: ssnError,
    };
  }
}
