我们的 React 应用程序在其大部分或全部区域使用 window.fetch 方法进行 http 调用。之前,它只有一个用于访问内容的令牌,而我们所做的是,我们在每个请求中单独添加一个标头,以发送令牌等。下面是此类请求的示例代码:
useEffect(() => {
// GET S3 CREDANTIONS
fetch("/dashboard/de/question/s3credentials", {
method: "GET",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${loginReducer}`,
},
})
但是现在我们已经将我们的 api 配置为访问两个令牌,一个用于访问内容,另一个用于刷新访问令牌。为此,在从互联网上搜索之后,我们决定在每次 http 调用之前添加一个 axios 拦截器,以检查 access_token 是否有效。因此,我制作了拦截器并将其放入 react 应用程序的 index.js 中。如果 access_token 有效,则在发送之前全局检查每个 http 请求;如果不是,请刷新。我从这个链接得到了这个想法: https ://blog.bitsrc.io/setting-up-axios-interceptors-for-all-http-calls-in-an-application-71bc2c636e4e 除了这个链接,我从许多其他网站,包括stackoverflow,我更了解这一点,因此应用了它。下面是 axios 拦截器在 index.js 文件中的代码(整体):
import React from "react";
import ReactDOM from "react-dom";
import App from "./App";
import reportWebVitals from "./reportWebVitals";
import axios from "axios";
import AdminIndex from "./AdminPanel/Pages/AdminIndex";
import Cookies from "js-cookie";
// React Redux
import allReducers from "./reducers/index";
import { createStore } from "redux";
import { Provider } from "react-redux";
import StateLoader from "./reducers/PresistedState";
const stateLoader = new StateLoader();
let store = createStore(
allReducers,
stateLoader.loadState(),
window.__REDUX_DEVTOOLS_EXTENSION__ && window.__REDUX_DEVTOOLS_EXTENSION__()
);
axios.interceptors.request.use(
async (config) => {
let serverCallUrl = new URL(config.url);
if (serverCallUrl.pathname.includes("/superuser/login")) return config;
let access_token = Cookies.get("access");
let refresh_token = localStorage.getItem("refresh_token");
await AdminIndex.hasAccess(access_token, refresh_token);
return config;
},
(error) => {
return Promise.reject(error);
}
);
store.subscribe(() => {
stateLoader.saveState(store.getState());
});
ReactDOM.render(
<Provider store={store}>
<App />
</Provider>,
document.getElementById("root")
);
我认为 axios 拦截器存在一些问题。因为当我启动应用程序并输入登录凭据时,应用程序会显示错误的用户名和密码等。我想知道问题是否是因为我们的应用程序使用的是 fetch 方法而不是 axios?因为我们正在尝试为 fetch http 调用实现 axios 拦截器。并且仅针对登录代码,我们已应用 axios 对用户进行身份验证。下面是登录的handleSubmit函数:
const handleSubmit = async (e) => {
e.preventDefault();
axios({
method: "post",
url: "/superuser/login",
headers: {
"content-type": "application/x-www-form-urlencoded;charset=utf-8",
},
data: `username=${values.username}&useremail=${values.useremail}`,
})
.then((res) => {
const { access_token, refresh_token } = res.data;
Cookies.set("access", access_token);
localStorage.setItem("refresh_token", refresh_token);
props.set_login(res.data.access_token);
history.push("/admin/panel/papers");
})
.catch((err) => setDialogStatus(true));
};
请查看导致无法登录应用程序的错误的原因。如果我删除拦截器,应用程序会成功登录,但是我将无法在 access_token 过期时刷新它。在拦截器中,我已经将刷新 access_token 的功能放入 app 的 props 中。希望我已经清楚地说明了我的问题。但是,如果缺少某些内容,请不要阻止问题,只需添加评论,我会立即回复。先感谢您!