需要两次点击才能登录

huangapple go评论64阅读模式
英文:

Two clicks needed for log in

问题

我必须点击两次登录按钮才能检查数据。有人能解释为什么吗?

我正在创建一个论坛网站,在我的登录页面上,用户必须点击两次按钮,然后代码才会验证并响应提供的数据。

以下是在按钮点击时触发的 handle submit:

const [values, setValues] = useState({
    email: '',
    password: ''
})
const navigate = useNavigate();
const [errors, setErrors] = useState({})

const handleInput = (e) => {
    setValues(prev => ({ ...prev, [e.target.name]: [e.target.value] }))
}

const handleSubmit = (e) => {
    e.preventDefault()
    setErrors(Validation(values))
    if (errors.password === "" && errors.email === "") {
        axios.post('http://localhost:8081/login', values)
            .then(res => {
                if (res.data.errorMessage === 'Success') {
                    navigate('/dashboard');
                } else {
                    console.log(res.data.errorMessage);
                }
            })
            .catch(err => console.log(err));
    }
}

PS:当填写不正确时,验证返回错误消息。

我对Node.js和React都很新,如果有人能解释,将会帮助很大!

英文:

I have to click log in twice before it chacks the data. Can someone help why?

I'm creating a forum website and on my log-in page the user has to click the button twice before it the code validates and responds to the given data.

here is my handle submit which is triggered on button click.

const [values,setValues] =useState({
        email: '',
        password: ''
    })
    const navigate =useNavigate();
    const [errors, setErrors] = useState({})
    const handleInput = (e) => {
        setValues(prev => ({...prev, [e.target.name]: [e.target.value]}))
    }

const handleSubmit = (e) => {
        e.preventDefault()
        setErrors(Validation(values))
        if(errors.password === "" && errors.email === ""){
            axios.post('http://localhost:8081/login', values)
            .then(res => {
                    if(res.data.errorMessage ==='Success'){
                        navigate('/dashboard');
                    }
                    else{
                        console.log(res.data.errorMessage);
                    }
            })
            .catch(err => console.log(err));
            
        }
        
    };

PS validation returns error messages when spots are not filled properly

I'm new to nodejs and react so if anyone could explain it would be a huge help!

答案1

得分: 0

正如我在评论中提到的,我最好的猜测是这与useState设置方法不立即反映更改有关。在你的情况下,你试图在调用setErrors后立即访问errors上的属性。然而,setErrors不仅会异步执行,而且它的新值甚至不能从当前闭包中访问。具体来说,handleSubmit变成了所谓的“陈旧闭包”,因为errors仍然引用初始的空对象{}。只有在重新渲染后,handleSubmit才会以新的错误值重新定义;这就是为什么需要点击两次的原因。

要修复你的情况,你只需要通过将其存储在本地变量中来使自己同步访问新的错误,就像这样:

const handleSubmit = (e) => {
        e.preventDefault()
        const newErrors = Validation(values);
        setErrors(newErrors)
        if(newErrors.password === "" && newErrors.email === ""){
            axios.post('http://localhost:8081/login', values)
            .then(res => {
                    if(res.data.errorMessage === 'Success'){
                        navigate('/dashboard');
                    }
                    else{
                        console.log(res.data.errorMessage);
                    }
            })
            .catch(err => console.log(err)); 
        }  
    };
英文:

As I mentioned in my comment, my best guess is that this is related to The useState set method is not reflecting a change immediately. In your case, you are trying to access the properties on errors immediately after calling setErrors. However, not only will setErrors execute asynchronously, but its new value won't even be accessible from the current closure. Specifically, handleSubmit becomes what is known as a "stale closure" because errors still references the initial empty object {}. Only after rerendering does handleSubmit get redefined with the new error values; that's why it takes 2 clicks.

To fix your case, you just need to give yourself synchronous access to the new errors, which can be done simply by storing it in a local variable, like so:

const handleSubmit = (e) => {
        e.preventDefault()
        const newErrors = Validation(values);
        setErrors(newErrors)
        if(newErrors.password === "" && newErrors.email === ""){
            axios.post('http://localhost:8081/login', values)
            .then(res => {
                    if(res.data.errorMessage ==='Success'){
                        navigate('/dashboard');
                    }
                    else{
                        console.log(res.data.errorMessage);
                    }
            })
            .catch(err => console.log(err)); 
        }  
    };

huangapple
  • 本文由 发表于 2023年5月28日 22:34:53
  • 转载请务必保留本文链接:https://go.coder-hub.com/76352008.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定