HEX
Server: nginx/1.24.0
System: Linux DGT-WORDPRESS-VM-SERVER 6.14.0-1014-azure #14~24.04.1-Ubuntu SMP Fri Oct 3 20:52:11 UTC 2025 x86_64
User: ubuntu (1000)
PHP: 8.4.12
Disabled: NONE
Upload Files
File: /mnt/data/dreamssalon-wp-market/wp-content/themes/dreamsalon/assets/js/dreamsalon-registration.js
/**
 * Dream Salon Registration OTP System
 * This file handles OTP verification for user registration
 */

(function($) {
    'use strict';

    /**
     * Registration OTP Manager
     * @param {Object} config - Configuration object
     */
    class RegistrationOTPManager {
        constructor(config) {
            this.config = config;
            this.otpTimer = null;
            this.resendTimer = null;
            this.otpTimeLeft = config.otpExpirySeconds || 300;
            this.resendTimeLeft = config.otpResendSeconds || 60;
            this.isOtpVerified = !config.otpEnabled;
            this.canResend = false;
            this.form = $('#dreamsalon-register-form');
            this.init();
        }

        /**
         * Initialize all event handlers
         */
        init() {
            // Email availability check
            this.bindEmailCheck();
            
            // Clear errors on input
            this.bindInputEvents();
            
            // OTP related functionality (only if enabled)
            if (this.config.otpEnabled) {
                this.bindOTPEvents();
            }
            
            // Form submission
            this.bindFormSubmission();
        }

        /**
         * Show error message
         * @param {string} fieldId - Field ID
         * @param {string} message - Error message
         */
        showError(fieldId, message) {
            $('#' + fieldId).html(message).show();
            $('#' + fieldId.replace('-error', '')).addClass('field-error');
        }

        /**
         * Clear error message
         * @param {string} fieldId - Field ID
         */
        clearError(fieldId) {
            $('#' + fieldId).html('').hide();
            $('#' + fieldId.replace('-error', '')).removeClass('field-error');
        }

        /**
         * Bind input events to clear errors
         */
        bindInputEvents() {
            $('input').on('input', (e) => {
                const fieldName = $(e.target).attr('id');
                if (fieldName) {
                    this.clearError(fieldName + '-error');
                }
            });
        }

        /**
         * Bind email availability check
         */
        bindEmailCheck() {
            $('#email').on('blur', (e) => {
                const email = $(e.target).val().trim();
                const emailCheckMessage = $('#email-check-message');

                // Clear previous messages
                emailCheckMessage.html('').removeClass('email-available email-taken email-checking');
                this.clearError('email-error');

                if (!email) return;

                // Basic email validation
                const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
                if (!emailRegex.test(email)) return;

                // Show checking message
                emailCheckMessage.html('Checking email availability...').addClass('email-checking');

                $.ajax({
                    url: this.config.ajaxUrl,
                    type: 'POST',
                    data: {
                        action: 'check_email_availability',
                        email: email,
                        security: this.config.emailCheckNonce
                    },
                    success: (response) => {
                        if (response.success) {
                            if (response.data.available) {
                                emailCheckMessage.html('✓ Email is available').addClass('email-available').removeClass('email-taken email-checking');
                            } else {
                                emailCheckMessage.html('').addClass('email-taken').removeClass('email-available email-checking');
                                this.showError('email-error', 'This email is already registered. Please login instead.');
                            }
                        } else {
                            emailCheckMessage.html('Error checking email').addClass('email-taken').removeClass('email-checking');
                        }
                    },
                    error: () => {
                        emailCheckMessage.html('Error checking email availability').addClass('email-taken').removeClass('email-checking');
                    }
                });
            });

            // Clear email error specifically
            $('#email').on('input', (e) => {
                this.clearError('email-error');
                this.clearError('otp-status');
                $('#email-check-message').html('').removeClass('email-available email-taken email-checking');
            });

            // Firefox-specific email validation fixes
            this.fixFirefoxEmailValidation();
        }

        /**
         * Fix Firefox email validation issues
         */
        fixFirefoxEmailValidation() {
            // Detect Firefox
            const isFirefox = typeof InstallTrigger !== 'undefined' || 
                            navigator.userAgent.toLowerCase().indexOf('firefox') > -1;

            if (isFirefox) {
                // Fix all form fields for Firefox
                this.fixFirefoxFormFields();
            }
        }

        /**
         * Fix Firefox validation for all form fields
         */
        fixFirefoxFormFields() {
            // Firefox-specific styling fixes for all form controls
            $('.form-control').css({
                '-moz-appearance': 'none',
                'appearance': 'none'
            });

            $('.form-check-input').css({
                '-moz-appearance': 'none',
                'appearance': 'none'
            });

            $('.btn').css({
                '-moz-appearance': 'none',
                'appearance': 'none'
            });

            // NAME FIELD VALIDATION
            $('#name').on('blur', (e) => {
                const name = $(e.target).val().trim();
                
                if (!name) {
                    this.showError('name-error', 'Name is required.');
                    $(e.target).addClass('field-error');
                } else if (name.length < 0) {
                    this.showError('name-error', 'Fill This Field.');
                    $(e.target).addClass('field-error');
                } else {
                    this.clearError('name-error');
                    $(e.target).removeClass('field-error');
                }
            });

            $('#name').on('input', (e) => {
                const name = $(e.target).val().trim();
                
                if (name && name.length >= 2) {
                    this.clearError('name-error');
                    $(e.target).removeClass('field-error');
                }
            });

            // EMAIL FIELD VALIDATION
            $('#email').on('blur', (e) => {
                const email = $(e.target).val().trim();
                const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
                
                if (email && !emailRegex.test(email)) {
                    this.showError('email-error', 'Please enter a valid email address.');
                    $(e.target).addClass('field-error');
                } else {
                    this.clearError('email-error');
                    $(e.target).removeClass('field-error');
                }
            });

            $('#email').on('input', (e) => {
                const email = $(e.target).val().trim();
                const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
                
                if (email && emailRegex.test(email)) {
                    this.clearError('email-error');
                    $(e.target).removeClass('field-error');
                }
            });

            // PASSWORD FIELD VALIDATION
            $('#password').on('blur', (e) => {
                const password = $(e.target).val();
                
                if (!password) {
                    this.showError('password-error', 'Password is required.');
                    $(e.target).addClass('field-error');
                } else if (password.length < 6) {
                    this.showError('password-error', 'Password must be at least 6 characters long.');
                    $(e.target).addClass('field-error');
                } else {
                    this.clearError('password-error');
                    $(e.target).removeClass('field-error');
                }
            });

            $('#password').on('input', (e) => {
                const password = $(e.target).val();
                
                if (password && password.length >= 6) {
                    this.clearError('password-error');
                    $(e.target).removeClass('field-error');
                }
            });

            // CHECKBOX VALIDATION
            $('#agree_terms').on('change', (e) => {
                const isChecked = $(e.target).is(':checked');
                
                if (!isChecked) {
                    this.showError('terms-error', 'You must agree to Terms & Service.');
                    $(e.target).addClass('field-error');
                } else {
                    this.clearError('terms-error');
                    $(e.target).removeClass('field-error');
                }
            });

            // FOCUS/BLUR STYLING FOR ALL FIELDS
            $('.form-control').on('focus', (e) => {
                if (!$(e.target).hasClass('field-error')) {
                    $(e.target).css({
                        'border-color': '#86b7fe',
                        'box-shadow': '0 0 0 0.25rem rgba(13, 110, 253, 0.25)',
                        'outline': 'none'
                    });
                }
            });

            $('.form-control').on('blur', (e) => {
                if (!$(e.target).hasClass('field-error')) {
                    $(e.target).css({
                        'border-color': '#ced4da',
                        'box-shadow': 'none'
                    });
                }
            });

            // ENSURE VALIDATION MESSAGES ARE VISIBLE IN FIREFOX
            const ensureVisibility = () => {
                $('.error-message').each((index, element) => {
                    const $element = $(element);
                    if ($element.html()) {
                        $element.css({
                            'display': 'block',
                            'visibility': 'visible',
                            'opacity': '1'
                        });
                    }
                });

                $('.email-check-message').each((index, element) => {
                    const $element = $(element);
                    if ($element.html()) {
                        $element.css({
                            'display': 'block',
                            'visibility': 'visible',
                            'opacity': '1'
                        });
                    }
                });
            };

            // Force visibility check every 100ms
            setInterval(ensureVisibility, 100);

            // ENHANCED ERROR STATE HANDLING
            const originalShowError = this.showError;
            this.showError = (fieldId, message) => {
                originalShowError.call(this, fieldId, message);
                
                const $field = $('#' + fieldId.replace('-error', ''));
                
                if ($field.length) {
                    $field.css({
                        'border-color': '#dc3545',
                        'box-shadow': '0 0 0 0.25rem rgba(220, 53, 69, 0.25)'
                    }).addClass('field-error');
                }
            };

            const originalClearError = this.clearError;
            this.clearError = (fieldId) => {
                originalClearError.call(this, fieldId);
                
                const $field = $('#' + fieldId.replace('-error', ''));
                
                if ($field.length) {
                    $field.css({
                        'border-color': '#ced4da',
                        'box-shadow': 'none'
                    }).removeClass('field-error');
                }
            };
        }

        /**
         * Bind OTP related events
         */
        bindOTPEvents() {
            // Send OTP
            $('#send_otp').on('click', (e) => {
                this.handleSendOTP(e);
            });

            // Resend OTP
            $('#resend_otp_link').on('click', (e) => {
                this.handleResendOTP(e);
            });

            // Verify OTP
            $('#verify-otp').on('click', (e) => {
                this.handleVerifyOTP(e);
            });

            // Auto-verify when 6 digits entered
            $('#otp').on('input', (e) => {
                const otp = $(e.target).val().trim();
                if (otp.length === 6 && /^\d+$/.test(otp) && !this.isOtpVerified) {
                    $('#verify-otp').click();
                }
            });

            // Email change handler
            $('#email').on('change', (e) => {
                this.handleEmailChange(e);
            });
        }

        /**
         * Handle send OTP button click
         */
       

        /**
         * Handle resend OTP
         */

        /**
         * Handle OTP verification
         */
        /**
         * Handle email change
         */
        handleEmailChange(e) {
            // Reset OTP verification if email changes
            if (this.isOtpVerified) {
                this.isOtpVerified = false;
                $('#register-btn').prop('disabled', true);
                $('#verify-status').html('');
                $('#otp').val('').prop('readonly', false);
                $('#verify-otp').text('Verify').prop('disabled', false);
                $('#send_otp').prop('disabled', false);
                $('#resend_otp_link').show().prop('disabled', false).css('pointer-events', 'auto');
                $('#otp-section').slideUp(300, () => {
                    $('#registration-fields').slideDown(300);
                });
                $('#auto-submit-message').hide();
                $('#submit-section').show();
                $('#resend-timer').hide();
                clearInterval(this.otpTimer);
                clearInterval(this.resendTimer);
            }
        }

        /**
         * Validate registration fields
         */
        validateRegistrationFields(name, email, password, agreeTerms) {
            let hasErrors = false;

            // Validate name
            if (!name) {
                this.showError('name-error', 'Name is required.');
                hasErrors = true;
            }

            // Validate email
            const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
            if (!email) {
                this.showError('email-error', 'Email is required.');
                hasErrors = true;
            } else if (!emailRegex.test(email)) {
                this.showError('email-error', 'Please enter a valid email address.');
                hasErrors = true;
            }

            // Check if email is already registered
            const emailCheckMessage = $('#email-check-message');
            if (emailCheckMessage.hasClass('email-taken')) {
                this.showError('email-error', 'This email is already registered. Please login instead.');
                hasErrors = true;
            }

            // Validate password
            if (!password) {
                this.showError('password-error', 'Password is required.');
                hasErrors = true;
            } else if (password.length < 6) {
                this.showError('password-error', 'Password must be at least 6 characters long.');
                hasErrors = true;
            }

            // Validate terms
            if (!agreeTerms) {
                this.showError('terms-error', 'You must agree to the Terms & Service.');
                hasErrors = true;
            }

            if (hasErrors) {
                // Scroll to first error
                $('html, body').animate({
                    scrollTop: $('.error-message:visible').first().offset().top - 100
                }, 500);
                return false;
            }

            return true;
        }

        /**
         * Start OTP expiration timer
         */

        /**
         * Start resend timer
         */

        /**
         * Update resend timer display
         */

        /**
         * Bind form submission
         */

        /**
         * Validate form before submission
         */
        validateFormSubmission(e) {
            let hasErrors = false;

            // Clear all errors first
            this.clearError('name-error');
            this.clearError('email-error');
            this.clearError('password-error');
            this.clearError('terms-error');
            if (this.config.otpEnabled) {
                this.clearError('otp-error');
            }

            // Get field values
            const name = $('#name').val().trim();
            const email = $('#email').val().trim();
            const password = $('#password').val();
            const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
            const emailCheckMessage = $('#email-check-message');

            // Validate name
            if (!name) {
                this.showError('name-error', 'Name is required.');
                hasErrors = true;
            }

            // Validate email
            if (!email) {
                this.showError('email-error', 'Email is required.');
                hasErrors = true;
            } else if (!emailRegex.test(email)) {
                this.showError('email-error', 'Please enter a valid email address.');
                hasErrors = true;
            }

            // Check if email is already registered
            if (emailCheckMessage.hasClass('email-taken')) {
                this.showError('email-error', 'This email is already registered. Please login instead.');
                hasErrors = true;
            }

            // Validate password
            if (!password) {
                this.showError('password-error', 'Password is required.');
                hasErrors = true;
            } else if (password.length < 6) {
                this.showError('password-error', 'Password must be at least 6 characters long.');
                hasErrors = true;
            }

            // Validate terms
            if (!$('#agree_terms').is(':checked')) {
                this.showError('terms-error', 'You must agree to the Terms & Service.');
                hasErrors = true;
            }

            // Validate OTP only if enabled
            if (this.config.otpEnabled && !this.isOtpVerified) {
                this.showError('otp-error', 'Please verify your OTP before submitting.');
                hasErrors = true;
            }

            if (hasErrors) {
                e.preventDefault();
                // Scroll to first error
                $('html, body').animate({
                    scrollTop: $('.error-message:visible').first().offset().top - 100
                }, 500);
                return false;
            }

            // Show loading state
            const submitBtn = $('#register-btn');
            const originalText = submitBtn.text();
            submitBtn.prop('disabled', true).text('Creating Account...');

            // Re-enable after 3 seconds if still on page (fallback)
            setTimeout(() => {
                if ($('#register-btn').text() === 'Creating Account...') {
                    submitBtn.prop('disabled', false).text(originalText);
                }
            }, 3000);

            return true;
        }

        /**
         * Show success message
         */
        showSuccessMessage(message) {
            // Remove any existing success messages
            $('.success-alert').remove();

            // Create success alert
            const successAlert = $('<div class="alert alert-success success-alert text-center mb-4">' + message + '</div>');
            successAlert.hide().insertBefore('#dreamsalon-register-form').fadeIn(300);

            // Auto-hide after 5 seconds
            setTimeout(() => {
                successAlert.fadeOut(300, () => {
                    $(this).remove();
                });
            }, 5000);
        }
    }

    /**
     * Initialize Registration OTP Manager when DOM is ready
     */
    $(document).ready(() => {
        // Check if registration form exists on the page
        if ($('#dreamsalon-register-form').length) {
            // Get configuration from PHP variables (these should be set in your PHP template)
            const config = {
                ajaxUrl: dreamsalonRegistration.ajaxUrl || '/wp-admin/admin-ajax.php',
                otpEnabled: dreamsalonRegistration.otpEnabled || false,
                otpExpirySeconds: parseInt(dreamsalonRegistration.otpExpirySeconds) || 300,
                otpResendSeconds: parseInt(dreamsalonRegistration.otpResendSeconds) || 60,
                otpNonce: dreamsalonRegistration.otpNonce || '',
                emailCheckNonce: dreamsalonRegistration.emailCheckNonce || ''
            };

            // Initialize the OTP manager
            new RegistrationOTPManager(config);
        }
    });

})(jQuery);