【发布时间】:2022-01-30 17:34:54
【问题描述】:
我试图这样做,但是对于三个请求,它会发送三个刷新请求:
- 1、2、3 失败并显示 401
- 刷新成功,1成功,2,3失败
- 刷新成功,2成功,3失败
- 刷新成功3成功
我不能在移动设备上放置那么多负载(即使只有 3 次刷新而没有“重新失败”)
这是我的代码:
function requestRefreshToken(refreshToken, accessToken) {
return axios
.create({
baseURL: apiUrl + Endpoints.AUTH.REFRESH,
skipAuthRefresh: true,
headers: {
'Accept-Language': 'ru',
'User-Agent': `${Platform.OS} ${packageJson.version}`,
Authorization: accessToken,
},
})
.post(
'',
{
grant_type: GrantTypes.REFRESH_TOKEN,
refresh_token: refreshToken,
client_id: Client.id,
client_secret: Client.secret,
},
{ validateStatus },
);
}
const refreshAuthLogic = async failedRequest =>
Keychain.getCredentials()
.then(old => requestRefreshToken(old.refreshToken, old.accessToken))
.then(({ data: credentials }) => {
failedRequest.config.headers.Authorization = `${credentials.token_type} ${
credentials.access_token
}`;
return Keychain.setCredentials(credentials);
});
createAuthRefreshInterceptor(axios, refreshAuthLogic, {
retryInstance: axios,
skipWhileRefreshing: true,
onRetry: function(config) {
return Keychain.getCredentials().then(({ accessToken }) =>
axios({
...config,
header: { ...config.headers, Authorization: accessToken },
}),
);
},
});
axios.interceptors.response.use(
r => r,
request => {
if (request.response.status === 401) {
return Keychain.getCredentials().then(({ accessToken }) =>
axios({
...request.config,
header: { ...request.config.headers, Authorization: accessToken },
}),
);
}
},
);
【问题讨论】:
-
你确定额外的请求不是由你在代码末尾的第二个拦截器触发的吗?使用 skipWhileRefreshing 设置为 true 时不应发生这种情况
-
另外,访问令牌也应该通过拦截器添加到请求中。这样,每当重试请求时,拦截器就会绑定正确的令牌。当然,您需要将令牌存储在状态或变量中,这应该不是问题。
-
如果我删除额外的拦截器并将skipWhileRefreshing设置为false,我们将得到下一个:1)所有3个请求都失败,401 2)刷新成功3)第一次成功,另外两个失败或者第一次成功两次其他人因失败而陷入困境
标签: axios refresh-token