抱歉,如果这是一个错误的问题,这是我第一次问!
使用 RTK 查询挂钩时捕获和处理错误的最佳方法是什么?我希望能够处理不同的状态 - 特别是 400,以便确定用户是否已登录。
我正在使用 JSON 服务器,并且创建了一个 RTK 查询 authAPiSlice,当我尝试登录 db.json 文件中存在的用户时,它可以正常工作。使用不存在的用户的详细信息测试登录确实会出错,但返回的错误和状态都是“未定义”。
这是我的 authApi.ts 文件:
export const authApiSlice = createApi({
reducerPath: "authApi",
baseQuery: fetchBaseQuery({ baseUrl: "http://localhost:3333/login" }),
tagTypes: ['User'],
endpoints: (builder) => ({
loginUser: builder.mutation({
query: (newUser: NewUser) => ({
url: ``,
method: "POST",
body: newUser,
// Getting the result as text makes it easier to parse into JSON
responseHandler: (response) => response.text(),
// responseHandler: (response) => response.json(),
}),
invalidatesTags: ["User"],
// transformResponse: (response: {data: User}) =>
// response.user,
}),
}),
});
这是我从handleSubmit 方法调用的函数,用于尝试登录并处理错误:
const [loginUser, { data: loginResult, status, error, isError, isLoading }] = useLoginUserMutation();
const attemptLogin = (user: NewUser): JSX.Element => {
// Attempt login using email and password
loginUser(user);
// Deal with any API related issues
if (isLoading) {
return <h1>Loading...</h1>;
}
if (isError || !loginResult || error) {
const errorString = JSON.stringify(error);
const statusString = JSON.stringify(status);
const resString = JSON.stringify(loginResult);
alert(`Login failed - error = ${errorString}
status = ${statusString}
result = ${resString}`);
console.error(`Login failed - Error = ${error}`);
return <h1>Unsuccessful login</h1>;
} else {
alert("Login successful");
console.log(loginResult);
storeUserNames();
return <h1></h1>;
};
调用方式如下:
const handleSubmit: FormEventHandler<HTMLFormElement> = (e) => {
e.preventDefault();
const user: NewUser = {
email: formData.email,
password: formData.password
};
attemptLogin(user);
};
抱歉,代码有点混乱,因为我刚刚尝试了不同的方法来访问错误,以便我可以阻止它引起问题。我之前尝试过 try {} catch {},但这似乎与 RTK 查询挂钩的设置方式不一致。
当我在 Postman 上尝试相同的请求时,状态返回为 400,正文返回为“无法找到用户”,这也在控制台中显示为来自调试器的错误。
控制台日志输出如下:
index.tsx:33 Login failed - Error = undefined
attemptLogin @ index.tsx:33
handleSubmit @ index.tsx:64
状态返回为“未初始化”,错误为“未定义”。
非常感谢任何帮助!
分派查询操作的工作方式与常规异步操作非常相似,例如谢谢。
给定登录突变钩子:
const [
loginUser,
{ data: loginResult, status, error, isError, isLoading }
] = useLoginUserMutation();
登录组件将调用触发函数并可以
await
完成它。
const handleSubmit = async (e) => {
e.preventDefault();
try {
const user: NewUser = {
email: formData.email,
password: formData.password
};
const data = await loginUser(user).unwrap();
// login successful, do what you need, e.g. navigate to a user dashboard, etc
} catch(error) {
// login failed
// handle any thrown exceptions or rejected Promises
}
};
UI 的其余部分可以使用突变结果元数据来处理渲染错误、加载指示器等。
...
useEffect(() => {
if (isError || !loginResult || error) {
const errorString = JSON.stringify(error);
const statusString = JSON.stringify(status);
const resString = JSON.stringify(loginResult);
alert(`
Login failed - error = ${errorString}
status = ${statusString}
result = ${resString}
`);
console.error(`Login failed - Error = ${error}`);
} else {
alert("Login successful");
console.log(loginResult);
storeUserNames();
}
}, [isError, error, loginResult]);
...
if (isLoading) {
return <h1>Loading...</h1>;
}
if (isError || !loginResult || error) {
return <h1>Unsuccessful login</h1>;
} else {
return <h1></h1>;
};
...