JavaScript通过策略层优化网络请求,如用AbortController取消冗余fetch请求、合理使用loading="lazy"、按需加载、接口合并及多级缓存协同。

JavaScript 本身不直接“优化”网络请求,而是通过控制请求时机、方式和资源处理逻辑来减少请求数量、降低带宽占用、提升响应速度。真正的优化发生在策略层,不是语法层。
如何用 fetch 配合 AbortController 主动取消冗余请求
用户快速输入搜索词时,前一个 fetch 还没返回,后一个已发出——若不取消旧请求,不仅浪费带宽,还可能因响应乱序导致 UI 显示错误结果。
-
AbortController是唯一被所有现代浏览器支持的原生取消机制,XMLHttpRequest.abort()已过时且行为不一致 - 每次新请求前必须新建
AbortController实例,复用会导致AbortError报错 - 需在
catch中显式检查error.name === 'AbortError',避免误当真实错误处理
let controller = null;
function search(query) {
if (controller) controller.abort();
controller = new AbortController();
fetch(`/api/search?q=${query}`, { signal: controller.signal })
.then(r => r.json())
.then(data => render(data))
.catch(err => {
if (err.name !== 'AbortError') console.error(err);
});
}
图片与脚本加载:什么时候该用 loading="lazy",什么时候必须手动控制
loading="lazy" 只对 和 生效,对 或动态 import() 无效;且在 Safari 15.4 之前不支持 。
- 首屏关键图(如 logo、主 Banner)禁用
loading="lazy",否则可能触发 CLS(布局偏移) - 列表页中大量头像或商品图适合启用,但需配合
width/height属性预留空间 - 动态导入模块(
import('./module.js'))无法用 HTML 属性控制,必须靠代码节流或预加载提示()
如何判断一个请求是否真该发——避免“防御性请求”
常见反模式:页面加载后立刻发 5 个 API 请求,只为了“把数据都准备好”,结果 80% 的数据用户根本没点开。
立即学习“Java免费学习笔记(深入)”;
- 用 IntersectionObserver 替代滚动监听,检测元素是否真正进入视口再加载(如评论区、分页内容)
- 对非关键数据(如用户偏好、统计埋点),用
setTimeout(..., 0)或queueMicrotask延迟到主线程空闲时发送,避免阻塞渲染 - 服务端支持时,优先合并接口(如 GraphQL 或 BFF 层聚合),而不是前端发多个 REST 请求
缓存控制:别只依赖 Cache-Control 响应头
HTTP 缓存策略由服务端决定,前端能做的有限,但可以补足边界情况:
- 对静态资源(JS/CSS/字体),确保服务端返回
Cache-Control: public, max-age=31536000并用哈希文件名(如main.a1b2c3.js)避免缓存失效问题 - 对 API 响应,
max-age=0或no-cache不代表“不缓存”,只是强制每次校验ETag或Last-Modified;若服务端未返回这些头,实际仍是无缓存 - 前端可加内存缓存(Map 或 WeakMap)临时存住刚请求过的数据,适用于短时间重复调用(如表单校验中的用户名查重)
最易被忽略的是:CDN 缓存、浏览器预加载、Service Worker 三者叠加时,缓存行为可能完全偏离预期——必须用 Network 面板逐层确认 x-cache、from ServiceWorker、from disk cache 等标记。











