Files
template-MP/hooks/useRequest.js
2025-11-05 16:20:06 +08:00

113 lines
2.4 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import { ref, reactive } from 'vue'
import tool from '@/common/utils/tool.js'
/**
* 通用请求Hook
* @param {Function} apiFunction API函数
* @param {Object} options 配置选项
* @returns {Object} 请求相关状态和方法
*/
export function useRequest(apiFunction, options = {}) {
const {
manual = false, // 是否手动触发
defaultParams = [], // 默认参数
onSuccess = () => {}, // 成功回调
onError = () => {}, // 失败回调
loadingDelay = 0, // loading延迟时间
} = options
// 状态
const data = ref(null)
const loading = ref(false)
const error = ref(null)
const params = ref([])
// loading延迟定时器
let loadingTimer = null
/**
* 执行请求
* @param {...any} args 请求参数
*/
async function run(...args) {
// 清除之前的loading延迟定时器
if (loadingTimer) {
clearTimeout(loadingTimer)
loadingTimer = null
}
// 设置参数
params.value = args
// 如果有loading延迟先启动定时器
if (loadingDelay > 0) {
loadingTimer = setTimeout(() => {
loading.value = true
}, loadingDelay)
} else {
loading.value = true
}
try {
const result = await apiFunction(...args)
// 清除loading延迟定时器
if (loadingTimer) {
clearTimeout(loadingTimer)
loadingTimer = null
}
data.value = result
error.value = null
onSuccess(result, args)
return result
} catch (err) {
// 清除loading延迟定时器
if (loadingTimer) {
clearTimeout(loadingTimer)
loadingTimer = null
}
error.value = err
data.value = null
console.error('请求失败:', err)
onError(err, args)
throw err
} finally {
loading.value = false
}
}
/**
* 取消请求
*/
function cancel() {
if (loadingTimer) {
clearTimeout(loadingTimer)
loadingTimer = null
}
loading.value = false
}
/**
* 重新执行请求
*/
function refresh() {
return run(...params.value)
}
// 如果不是手动触发,立即执行
if (!manual) {
// 使用nextTick确保在组件挂载后执行
Promise.resolve().then(() => {
run(...defaultParams)
})
}
return {
data,
loading,
error,
params,
run,
cancel,
refresh,
}
}