/** * 请求封装 - 基于 useFetch 二次封装 * 提供统一的请求配置、错误处理、Loading 状态等 */ import type { UseFetchOptions } from "nuxt/app"; /** * 请求配置选项 - 继承 Nuxt UseFetchOptions 并添加自定义选项 */ export type RequestOptions = UseFetchOptions & { /** 是否显示加载状态 */ showLoading?: boolean /** 成功提示信息 */ successMsg?: string /** 错误提示信息 */ errorMsg?: string /** 是否手动触发 */ manual?: boolean } /** * 封装后的请求方法 * @param url - 请求地址 * @param options - 请求配置 */ export function useRequest(url: string, options: RequestOptions = {}) { const config = useRuntimeConfig(); const { // showLoading = false, successMsg = "", errorMsg = "", manual = false, ...restOptions } = options; // 计算完整 URL const fullUrl = computed(() => config.public.apiBaseUrl + url); // 显示成功提示 const showSuccessTip = (msg: string) => { if (msg) { console.log(`[Success] ${msg}`); } }; // 显示错误提示 const showErrorTip = (msg: string, err?: any) => { if (msg || errorMsg) { const tip = msg || errorMsg || (err as Error)?.message || "请求失败"; console.error(`[Error] ${tip}`, err); } }; // 使用 useFetch 发起请求 const { data, error, execute, ...rest } = useFetch(fullUrl, { ...restOptions, // 请求完成后的回调 onResponse({ response }: any) { if (showSuccessTip && response.ok) { showSuccessTip(successMsg); } }, // 请求出错后的回调 onResponseError({ error }: any) { showErrorTip(errorMsg, error); }, } as any); // 手动执行函数 const run = async () => { await execute(); return { data: data.value, error: error.value }; }; // 立即执行(如果 manual 为 false) if (!manual) { void execute(); } return { data, error, execute: run, ...rest, }; } /** * GET 请求 */ export function useGet(url: string, options: RequestOptions = {}) { return useRequest(url, { ...options, method: "get" }); } /** * POST 请求 */ export function usePost(url: string, options: RequestOptions = {}) { return useRequest(url, { ...options, method: "post" }); } /** * PUT 请求 */ export function usePut(url: string, options: RequestOptions = {}) { return useRequest(url, { ...options, method: "put" }); } /** * DELETE 请求 */ export function useDelete(url: string, options: RequestOptions = {}) { return useRequest(url, { ...options, method: "delete" }); }