如何将 .then .catch 转换为 async/await [英] How to convert .then .catch to async/await
问题描述
使用 React/Redux 前端和我自己的 nodejs/express api 处理登录表单/注销按钮.登录表单有问题.大多数时候它工作得很好,但我经常遇到错误.第一个错误是 forbidden
,它告诉我用户在发送 userDetails
请求之前没有完全通过身份验证.
然后还有一个 bug,Redux 没有改变用户的角色,我需要动态渲染导航.我认为将 handleLogin 转换为 async/await 将是解决方案,但我相信我做得不对.
从'react'导入React;从'../axios/homeApi'导入{登录,用户详细信息};导入 { useForm } from 'react-hook-form';从'react-redux'导入{useDispatch};import { setLogin, setRole } from '../redux/actions';const LoginForm = () =>{const { handleSubmit, register, errors } = useForm();const dispatch = useDispatch();const handleLogin = 值 =>{登录(值.电子邮件,值.密码).then(res => {const token = res.data.token;window.localStorage.setItem('auth', token);调度(setLogin({登录:真}));用户详细信息().then(res => {const 角色 = res.data.data.role;调度(setRole({角色}));})})}返回 (<div><form action=""onSubmit={handleSubmit(handleLogin)} className=footer-form"><输入类型=电子邮件"placeholder =在此处输入电子邮件"名称=电子邮件"ref={register({ 必填:必填字段"})}/><输入类型=密码"placeholder="在此处输入密码";名称=密码"ref={注册({必填:必填字段",minLength: { value: 6, message: "Minimum Length: 6 Characters";}})}/>{errors.password &&错误.密码.消息}{errors.email &&错误.email.message}<输入类型=提交"值=登录"/></表单>
)}导出默认登录表单;
这是我将 handleLogin 转换为 async/await 的最佳尝试.我试图了解我应该如何从这些调用中提取数据.
const handleLogin = 异步值 =>{尝试 {const {data: {token}} = await login(values.email, values.password)window.localStorage.setItem('auth', token);控制台日志(令牌);const user = await userDetails();等待调度(setLogin({登录:真}))等待调度(setRole(user.data.data.role))} 抓住(错误){控制台日志(错误)}}
对此的任何帮助/指导将不胜感激.
你得想想,当你使用await
时,变量值和返回到res
中的值是一样的无需await
.
如果你有:
登录(values.email, values.password).then(res => {})
这就像:
var login = await login(values.email, values.password);
所以使用这个逻辑,这个:
登录(values.email, values.password).then(res => {const token = res.data.token;//任何用户详细信息().then(res => {const 角色 = res.data.data.role;//任何})})
变成:
var login = await login(values.email, values.password)const token = login.data.token;//做任何事var userDetails = 等待 userDetails()const 角色 = userDetails.data.data.role;//任何
检查这个例子是如何工作的.代码是相同的".一个使用 .then
,另一个使用 await
.
runThenFunction();运行等待函数();函数 runThenFunction(){console.log("输入然后函数")this.returnPromise(2000).then(res => {控制台日志(res);this.returnPromise(1000).then(res => {控制台日志(res);});});//这里可以登录,在promise解决前会显示console.log("退出然后函数")}异步函数 runAwaitFunction(){console.log("进入等待函数")var firstStop = await returnPromise(1000);控制台日志(第一次停止)var secondStop = await returnPromise(4000);控制台日志(第二次停止)//使用 await 代码停止"直到 promise 被解决console.log("退出等待函数")}函数返回承诺(时间){return new Promise(resolve => setTimeout(() => resolve("hello: "+time+"ms later."), time));}
Working on a login form / logout button with React/Redux front end and my own nodejs/express api. Having an issue with the login form. Most of the time it works just fine, but I'm getting erros on a regular basis. First error is forbidden
, which tells me that the user is not quite authenticated before send the userDetails
request.
Then there's another bug where Redux doesn't change the role of the user, which I need to dynamically render the nav. I'm thinking converting handleLogin to async/await will be the solution, but I believe I'm not doing it right.
import React from 'react';
import { login, userDetails } from '../axios/homeApi';
import { useForm } from 'react-hook-form';
import { useDispatch } from 'react-redux';
import { setLogin, setRole } from '../redux/actions';
const LoginForm = () => {
const { handleSubmit, register, errors } = useForm();
const dispatch = useDispatch();
const handleLogin = values => {
login(values.email, values.password)
.then(res => {
const token = res.data.token;
window.localStorage.setItem('auth', token);
dispatch(setLogin({ loggedIn: true }));
userDetails()
.then(res => {
const role = res.data.data.role;
dispatch (setRole({ role }));
})
})
}
return (
<div>
<form action="" onSubmit={handleSubmit(handleLogin)} className="footer-form">
<input
type="email"
placeholder="Enter Email Here"
name="email"
ref={register({ required: "Required Field" })}
/>
<input
type="password"
placeholder="Enter Password Here"
name="password"
ref={register({
required: "Required Field",
minLength: { value: 6, message: "Minimum Length: 6 Characters" }
})}
/>
{errors.password && errors.password.message}
{errors.email && errors.email.message}
<input type="submit" value="Login" />
</form>
</div>
)
}
export default LoginForm;
Here's my best attempt at converting handleLogin to async/await. I'm trying to understand how I'm supposed to pull data from these calls.
const handleLogin = async values => {
try {
const {data: {token}} = await login(values.email, values.password)
window.localStorage.setItem('auth', token);
console.log(token);
const user = await userDetails();
await dispatch(setLogin({ loggedIn: true}))
await dispatch(setRole(user.data.data.role))
} catch(err) {
console.log(err)
}
}
Any help/guidance on this would be greatly appreciated.
You have to think when you use await
, the variable value is the same that returned into res
without await
.
So if you have:
login(values.email, values.password)
.then(res => {
})
This is like:
var login = await login(values.email, values.password);
So using this logic, this:
login(values.email, values.password)
.then(res => {
const token = res.data.token;
// whatever
userDetails()
.then(res => {
const role = res.data.data.role;
// whatever
})
})
Turn into:
var login = await login(values.email, values.password)
const token = login.data.token;
// do whatever
var userDetails = await userDetails()
const role = userDetails.data.data.role;
// whatever
Check how works this example. The code is "the same". One using .then
and the other using await
.
runThenFunction();
runAwaitFunction();
function runThenFunction(){
console.log("Enter then function")
this.returnPromise(2000).then(res => {
console.log(res);
this.returnPromise(1000).then(res => {
console.log(res);
});
});
//You can log here and it will be displayed before the promise has been resolved
console.log("Exit then function")
}
async function runAwaitFunction(){
console.log("Enter await function")
var firstStop = await returnPromise(1000);
console.log(firstStop)
var secondStop = await returnPromise(4000);
console.log(secondStop)
// Using await the code "stops" until promise is resolved
console.log("Exit await function")
}
function returnPromise(time){
return new Promise(resolve => setTimeout(() => resolve("hello: "+time+"ms later."), time));
}
这篇关于如何将 .then .catch 转换为 async/await的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!