在Vue项目开发中,经常会遇到需要同时发起几十个请求的场景(如批量数据查询、批量提交、页面初始化加载多接口数据)。若直接同时发起所有请求,会导致网络拥堵、接口超时、浏览器卡顿,甚至触发后端接口限流,影响用户体验和系统稳定性。本文结合Vue2/Vue3实战,提供4种主流并发控制方案,覆盖不同场景,可直接落地使用,轻松管控几十个请求的并发逻辑。

并发控制的核心是:限制同一时间发起的请求数量,将几十个请求分批次、有序执行,避免一次性占用过多网络资源。核心要点的2个:
以下方案均适配Vue2/Vue3,基于Axios请求库(Vue项目主流请求工具),可直接复制到项目中修改使用。
核心思路:封装一个并发池工具,将所有请求放入队列,限制同时执行的请求数量,当某个请求完成后,自动从队列中取出下一个请求执行,循环直至所有请求完成。该方案灵活可控,可处理成功/失败回调、超时控制,是几十个请求并发管控的最优选择。
1. 封装并发池工具(Vue2/Vue3通用)
// utils/requestPool.jsimport axios from 'axios';// 极简版并发池(核心功能:限制并发、处理超时、返回结果)export async function requestPool(requestList, limit = 4, timeout = 10000) { const result = []; let running = 0; let queue = [...requestList]; const runRequest = async () => { if (queue.length === 0 && running === 0) return result; while (running < limit && queue.length > 0) { running++; const requestFn = queue.shift(); const index = requestList.length - queue.length - running; try { const res = await Promise.race([ requestFn(), new Promise((_, reject) => setTimeout(() => reject(new Error('请求超时')), timeout)) ]); result[index] = { success: true, data: res.data }; } catch (error) { result[index] = { success: false, error: error.message }; } finally { running--; await runRequest(); } } }; await runRequest(); return result;}// 极简请求函数(按需修改url和参数)export function createRequestFn(id) { return () => axios({ url: `/api/data/${id}`, method: 'get', timeout: 10000 });}2. Vue组件中使用(Vue3示例,Vue2可直接适配)
<template> <div> <button @click="handleBatchRequest">发起30个并发请求</button> <div class="result">成功:{{ successCount }} 个 | 失败:{{ failCount }} 个</div> </div></template><script setup>import { ref } from 'vue';import { requestPool, createRequestFn } from '@/utils/requestPool';const successCount = ref(0);const failCount = ref(0);// 极简使用示例(30个请求,并发数5)const handleBatchRequest = async () => { const requestList = Array.from({ length: 30 }, (_, i) => createRequestFn(i + 1)); const results = await requestPool(requestList, 5); successCount.value = results.filter(item => item.success).length; failCount.value = results.filter(item => !item.success).length;};</script><style scoped>.result { margin-top: 20px; font-size: 14px; color: #333; }</style>方案一优势与适配场景
核心思路:将几十个请求分成若干批次,每批次发起固定数量的请求(如每批5个),等待当前批次所有请求完成后,再发起下一批。实现简单,无需复杂封装,适合对请求顺序有严格要求的场景(如下一批请求依赖上一批请求结果)。
1. 封装分批次请求工具(Vue2/Vue3通用)
// utils/batchRequest.jsimport axios from 'axios';/** * 分批次请求控制 * @param {Array} requestList - 请求列表(每个元素是请求参数,如id) * @param {Number} batchSize - 每批请求数量(默认5个) * @returns {Promise} - 所有请求结果数组 */export async function batchRequest(requestList, batchSize = 5) { const result = []; // 计算总批次 const totalBatch = Math.ceil(requestList.length / batchSize); // 循环发起每批次请求 for (let i = 0; i < totalBatch; i++) { // 截取当前批次的请求参数 const currentBatch = requestList.slice(i * batchSize, (i + 1) * batchSize); // 发起当前批次的所有请求(并行) const batchResult = await Promise.allSettled( currentBatch.map(id => axios({ url: `/api/data/${id}`, method: 'get', timeout: 10000 }).then(res => ({ success: true, data: res.data })) .catch(err => ({ success: false, error: err.message })) ) ); // 将当前批次结果存入总结果 result.push(...batchResult); } return result;}2. Vue组件中使用
<script setup>import { ref } from 'vue';import { batchRequest } from '@/utils/batchRequest';const successCount = ref(0);const failCount = ref(0);const handleBatchRequest = async () => { // 生成30个请求参数(如id数组) const requestList = Array.from({ length: 30 }, (_, i) => i + 1); // 分批次请求,每批5个 const results = await batchRequest(requestList, 5); // 处理结果 successCount.value = results.filter(item => item.success).length; failCount.value = results.filter(item => !item.success).length;};</script>方案二优势与适配场景
核心思路:通过Axios的请求拦截器和响应拦截器,维护一个“正在执行的请求”计数器,当计数器达到并发限制时,将后续请求存入队列,等待正在执行的请求完成后,再依次发起。适合简单场景,无需在组件中单独处理,全局统一管控。
1. 全局配置Axios并发控制(Vue2/Vue3通用)
// utils/axiosConfig.jsimport axios from 'axios';// 并发限制数const CONCURRENT_LIMIT = 4;// 正在执行的请求计数器let requestCount = 0;// 请求队列const requestQueue = [];// 创建Axios实例const service = axios.create({ baseURL: import.meta.env.VITE_API_BASE_URL, timeout: 10000});// 请求拦截器:控制并发service.interceptors.request.use( config => { return new Promise(resolve => { // 若当前请求数未达限制,直接发起请求 if (requestCount < CONCURRENT_LIMIT) { requestCount++; resolve(config); } else { // 达到限制,存入请求队列 requestQueue.push(resolve); } }); }, error => { return Promise.reject(error); });// 响应拦截器:请求完成后,从队列中取出下一个请求service.interceptors.response.use( response => { // 请求完成,计数器减1 requestCount--; // 若队列中有请求,取出并执行 if (requestQueue.length > 0) { const resolve = requestQueue.shift(); requestCount++; resolve(service.defaults); } return response; }, error => { // 失败也需计数器减1,避免队列卡住 requestCount--; if (requestQueue.length > 0) { const resolve = requestQueue.shift(); requestCount++; resolve(service.defaults); } return Promise.reject(error); });export default service;2. Vue组件中使用
<script setup>import { ref } from 'vue';import request from '@/utils/axiosConfig';const successCount = ref(0);const failCount = ref(0);// 直接发起30个请求,Axios拦截器自动控制并发const handleBatchRequest = async () => { const requestList = []; for (let i = 1; i <= 30; i++) { requestList.push( request({ url: `/api/data/${i}`, method: 'get' }).then(res => ({ success: true, data: res.data })) .catch(err => ({ success: false, error: err.message })) ); } // 等待所有请求完成 const results = await Promise.allSettled(requestList); successCount.value = results.filter(item => item.success).length; failCount.value = results.filter(item => !item.success).length;};</script>方案三优势与适配场景
核心思路:借助成熟的第三方库(如p-limit),快速实现并发控制,无需自己封装工具,适合复杂场景(如并发数动态调整、请求优先级控制)。p-limit轻量、易用,是前端并发控制的常用库。
1. 安装与使用(Vue2/Vue3通用)
// 1. 安装依赖// npm install p-limit --save// 2. 组件中使用<script setup>import { ref } from 'vue';import axios from 'axios';import pLimit from 'p-limit';// 设置并发限制数为4const limit = pLimit(4);const successCount = ref(0);const failCount = ref(0);const handleBatchRequest = async () => { // 生成30个请求函数,并用p-limit包装 const requestList = []; for (let i = 1; i <= 30; i++) { // 用limit包装请求函数,限制并发 requestList.push( limit(() => axios({ url: `/api/data/${i}`, method: 'get', timeout: 10000 }).then(res => ({ success: true, data: res.data })) .catch(err => ({ success: false, error: err.message })) ) ); } // 等待所有请求完成 const results = await Promise.allSettled(requestList); successCount.value = results.filter(item => item.success).length; failCount.value = results.filter(item => !item.success).length;};</script>方案四优势与适配场景
针对Vue中几十个请求的并发控制,4种方案各有适配场景,可根据项目需求灵活选择:
实际开发中,建议优先使用“并发池控制”方案,既能灵活控制并发数、处理异常,又能保证请求顺序,可直接复制本文代码,修改请求地址和参数即可快速落地,轻松解决几十个请求的并发难题。
以上就是一文分享4种Vue并发控制的实战方案的详细内容,更多关于Vue并发控制的资料请关注本站其它相关文章!