import { MailOutlined, LockOutlined } from '@ant-design/icons';
import { Button, Form, Input, message, Row, Col, Modal } from 'antd';
import { NavLink, useNavigate } from 'react-router';
import { useState, useEffect } from 'react';
import { useForm } from 'antd/es/form/Form';
import authApi from '../../api/Auth/AuthApi';

// 定义表单值的类型
interface FormValues {
    email: string;
    code: string;
    password: string;
    confirmPassword: string;
}


function Forget() {
    const [countdown, setCountdown] = useState(0);
    const [emailSent, setEmailSent] = useState(false); // 是否已发送验证码
    const [form] = useForm<FormValues>();
    const emailValue = Form.useWatch('email', form);
    const [messageApi, contextHolder] = message.useMessage();
    const nav = useNavigate(); // 页面跳转

    // 校验邮箱格式
    function isValidEmail(email: string): boolean {
        const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
        console.log(emailRegex.test(email))
        console.log(email)
        return emailRegex.test(email);
    }

    // 发送验证码
    const sendResetCode = async () => {
        if (!isValidEmail(emailValue)) {
            form.validateFields(['email']);
            return;
        }

        await authApi.sendResetCode(emailValue).then(() => {
            setEmailSent(true);
            setCountdown(60);
        }).catch((error) => {
            messageApi.error(error?.message || '验证码发送失败');
        });
    };

    const [modal, modalContext] = Modal.useModal();

    const countDownNav = (onOk: () => void) => {
        let secondsToGo = 5;
        const instance = modal.success({
            title: '重置成功',
            content: `系统将在 ${secondsToGo} 后跳转到登陆页面.`,
            okText: "立即跳转",
            onOk
        });

        const timer = setInterval(() => {
            secondsToGo -= 1;
            instance.update({
                content: `将在 ${secondsToGo} 后回到登陆页面.`,
            });
        }, 1000);

        setTimeout(() => {
            clearInterval(timer);
            instance.destroy();
        }, secondsToGo * 1000);
    };
    // 倒计时发送
    useEffect(() => {
        let countdownTimer = null;

        if (countdown > 0) {
            countdownTimer = setTimeout(() => {
                setCountdown(prev => prev - 1);
            }, 1000);
        }

        return () => {
            if (countdownTimer) {
                clearTimeout(countdownTimer);
            }
        };
    }, [countdown]);

    // 重新发送验证码
    const resendCode = () => {
        if (countdown > 0) return;
        setCountdown(60);
        sendResetCode();  // 重新发送验证码
    };

    // 表单提交处理
    const onFinish = (values: FormValues) => {
        if (!emailSent) {
            sendResetCode();
        } else {
            console.log(values);
            authApi.resetPassword({
                email: values.email,
                code: values.code,
                newPassword: values.password,
            }).then((response) => {
                if (response.data.code == 0) {
                    countDownNav(() => nav('/login'))
                } else {
                    messageApi.error(response.data.message);
                }
            })
        }
    };

    return (
        <>
            <Form
                form={form}
                name="forget"
                initialValues={{ remember: false }}
                onFinish={onFinish}
            >
                {contextHolder}
                <h2>重置密码</h2>
                <p>请输入您注册时使用的邮箱地址</p>

                <Form.Item
                    name="email"
                    rules={[
                        { required: true, message: '请输入您的邮箱！' },
                        { type: 'email', message: '请输入正确的邮箱格式' }
                    ]}
                >
                    <Input prefix={<MailOutlined />} placeholder="注册邮箱" />
                </Form.Item>

                {emailSent && (
                    <>
                        <Form.Item
                            name="code"
                            rules={[{ required: true, message: '请输入验证码！' }]}
                        >
                            <Row gutter={8}>
                                <Col span={16}>
                                    <Input placeholder="验证码" />
                                </Col>
                                <Col span={8}>
                                    <Button
                                        disabled={countdown > 0}
                                        onClick={resendCode}
                                        style={{ width: '100%' }}
                                    >
                                        {countdown > 0 ? `${countdown}s后重试` : '重新发送'}
                                    </Button>
                                </Col>
                            </Row>
                        </Form.Item>

                        <Form.Item
                            name="password"
                            rules={[
                                { required: true, message: '请设置新密码！' },
                                { min: 6, message: '密码长度至少为6位' }
                            ]}
                        >
                            <Input.Password prefix={<LockOutlined />} placeholder="新密码" />
                        </Form.Item>

                        <Form.Item
                            name="confirmPassword"
                            dependencies={['password']}
                            rules={[
                                { required: true, message: '请确认新密码！' },
                                ({ getFieldValue }) => ({
                                    validator(_, value) {
                                        if (!value || getFieldValue('password') === value) {
                                            return Promise.resolve();
                                        }
                                        return Promise.reject(new Error('两次输入的密码不一致！'));
                                    },
                                }),
                            ]}
                        >
                            <Input.Password prefix={<LockOutlined />} placeholder="确认新密码" />
                        </Form.Item>
                    </>
                )}

                <Form.Item>
                    <Button block type="primary" htmlType="submit">
                        {emailSent ? '确认重置' : '获取验证码'}
                    </Button>
                    或 <NavLink to='/login'>返回登录</NavLink>
                </Form.Item>
            </Form>
            {modalContext}
        </>
    );
}

export default Forget;
