ykt-wxapp/utils/http.js

230 lines
5.2 KiB
JavaScript
Raw Normal View History

2026-01-19 18:52:18 +08:00
import { loading, hideLoading } from "./widget";
const env = __VITE_ENV__;
const baseUrl = env.MP_API_BASE_URL;
const defaultOptions = {
header: {
"Content-Type": "application/json",
},
method: "POST",
timeout: 1000 * 60, // 请求超时设置为60秒
};
const tasks = [];
// 是否正在刷新 token
let isRefreshing = false;
// 重试队列
let retryQueue = [];
/**
* 处理重试队列
* @param {String} token - 新的 token
*/
function processQueue(token) {
retryQueue.forEach(({ resolve, reject, config }) => {
if (token) {
// 更新 token 并重试请求
if (!config.header) config.header = {};
config.header.Authorization = `Bearer ${token}`;
uni.request({
...config,
success: (res) => resolve(res),
fail: (err) => reject(err),
});
} else {
reject(new Error("Token 刷新失败"));
}
});
retryQueue = [];
}
/**
* 刷新 token
* @returns {Promise<String|null>}
*/
async function refreshAccessToken() {
const refreshToken = uni.getStorageSync("refreshToken");
if (!refreshToken) {
return null;
}
if (isRefreshing) {
// 等待刷新完成
await new Promise((resolve) => setTimeout(resolve, 100));
return uni.getStorageSync("accessToken");
}
isRefreshing = true;
try {
const res = await uni.request({
url: `${baseUrl}/auth/refresh`,
method: "POST",
header: {
"Content-Type": "application/json",
},
data: {
refreshToken,
},
});
if (res && res.data && res.data.success && res.data.data) {
const newToken = res.data.data.accessToken;
uni.setStorageSync("accessToken", newToken);
processQueue(newToken);
return newToken;
} else {
// 刷新失败,清空队列
processQueue(null);
// 清除登录状态
uni.removeStorageSync("accessToken");
uni.removeStorageSync("refreshToken");
uni.removeStorageSync("jwtUserInfo");
return null;
}
} catch (error) {
console.error("Token 刷新异常:", error);
processQueue(null);
uni.removeStorageSync("accessToken");
uni.removeStorageSync("refreshToken");
uni.removeStorageSync("jwtUserInfo");
return null;
} finally {
isRefreshing = false;
}
}
const request = async (options = {}, showLoading = true) => {
// 合并用户传入的配置和默认配置
if (!options.data) options.data = {};
const config = {
...defaultOptions,
...options,
url: baseUrl + options.url,
};
// 添加 token 到请求头
// const accessToken = uni.getStorageSync("accessToken");
// if (accessToken) {
// if (!config.header) config.header = {};
// config.header.Authorization = `Bearer ${accessToken}`;
// }
const key = `${JSON.stringify(config)}_${Date.now()}`;
if (showLoading) {
recordTask(key)
}
try {
// 发起请求
const res = await uni.request(config);
if (showLoading) {
removeTask(key)
}
// 如果返回 401尝试刷新 token
// if (res.statusCode === 401) {
// if (showLoading) {
// removeTask(key)
// }
// // 尝试刷新 token
// const newToken = await refreshAccessToken();
// if (newToken) {
// // 刷新成功,重试原请求
// if (!config.header) config.header = {};
// config.header.Authorization = `Bearer ${newToken}`;
// if (showLoading) {
// recordTask(key)
// }
// const retryRes = await uni.request(config);
// if (showLoading) {
// removeTask(key)
// }
// const success = retryRes && retryRes.data && retryRes.data.success === true;
// if (success) {
// return retryRes.data;
// }
// return {
// success: false,
// message: retryRes.data && retryRes.data.message ? retryRes.data.message : "请求失败",
// };
// } else {
// return {
// success: false,
// message: "登录已过期,请重新登录",
// };
// }
// }
const success = res && res.data && res.data.success === true;
if (success) {
return res.data;
}
return {
success: false,
message: res.data && res.data.message ? res.data.message : "请求失败",
};
} catch (error) {
console.log("error:", error);
if (showLoading) {
removeTask(key)
}
return Promise.reject(error);
}
};
function recordTask(task) {
if (tasks.length === 0) {
loading("请求中...");
}
tasks.push(task);
}
function removeTask(task) {
const index = tasks.findIndex((i) => i === task);
if (index > -1) {
tasks.splice(index, 1);
}
if (tasks.length === 0) {
hideLoading();
}
}
export default request;
export const uploadUrl = `${baseUrl}/upload`;
export function getFullPath(path) {
2026-01-20 19:04:24 +08:00
return `${baseUrl}/${path}`;
}
export function upload(path) {
return new Promise((resolve) => {
uni.uploadFile({
url: uploadUrl, // 替换为你的上传接口地址
filePath: path,
name: 'file',
fileType: 'image',
success: (res) => {
try {
const url = JSON.parse(res.data).filePath;
resolve(url ? getFullPath(url) : '')
} catch (e) {
resolve()
}
},
fail: res => {
resolve()
}
})
})
2026-01-19 18:52:18 +08:00
}