问题

fetch 的优势在哪里? 为什么有人会在前端项目中用 fetch?

回答
为什么要在前端项目里头拥抱 Fetch API?

在前端开发的漫漫长路上,我们总是在与各种数据打交道:从服务器获取用户信息、加载产品列表、提交表单数据……而这一切的核心,都离不开网络请求。过去,JavaScript 提供了 `XMLHttpRequest` (XHR) 来实现这些功能,但随着 Web 技术的不断发展,Fetch API 横空出世,带来了许多令人惊喜的改进。那么,Fetch API 究竟有什么过人之处,让它如此受前端开发者青睐呢?

1. 更简洁、更易读的 API 设计:

这是 Fetch API 最直观的优势。相较于 XHR 那一套繁琐的事件监听、状态码检查,Fetch API 的代码风格更加符合现代 JavaScript 的使用习惯。

Promise 原生支持: Fetch API 本身就返回 Promise 对象。这意味着我们可以直接使用 `.then()` 和 `.catch()` 来处理异步操作,构建更清晰的链式调用。再也不用担心回调地狱或者层层嵌套的 `if` 语句了。
```javascript
// XHR 时代的常见写法
const xhr = new XMLHttpRequest();
xhr.open('GET', '/api/data', true);
xhr.onload = function() {
if (xhr.status >= 200 && xhr.status < 300) {
const data = JSON.parse(xhr.responseText);
console.log(data);
} else {
console.error('Request failed:', xhr.status);
}
};
xhr.onerror = function() {
console.error('Network error');
};
xhr.send();

// Fetch API 的优雅写法
fetch('/api/data')
.then(response => {
if (!response.ok) { // response.ok 检查 HTTP 状态码是否在 2xx 范围内
throw new Error(`HTTP error! status: ${response.status}`);
}
return response.json(); // 将响应体解析为 JSON
})
.then(data => {
console.log(data);
})
.catch(error => {
console.error('Fetch error:', error);
});
```
你看,Fetch API 的代码量更少,逻辑也更顺畅。`response.ok` 的存在,使得检查请求是否成功的逻辑更加明确,而 `response.json()` 则直接将响应体转换为 JavaScript 对象,省去了手动 `JSON.parse()` 的步骤。

清晰的请求和响应对象: Fetch API 将请求(`Request`)和响应(`Response`)抽象成了独立的 JavaScript 对象。这使得我们可以更精细地控制请求的各个方面,例如设置请求头、请求体、请求方法等,并且能更方便地处理响应,如获取响应头、检查响应状态、读取响应体等。

2. 强大的请求配置能力:

Fetch API 提供了非常灵活的配置选项,允许我们精细地控制网络请求的行为。

请求方法(Method): 支持 `GET`、`POST`、`PUT`、`DELETE` 等各种 HTTP 方法。
请求头(Headers): 可以轻松地设置自定义的请求头,比如 `ContentType`、`Authorization` 等。
```javascript
fetch('/api/users', {
method: 'POST',
headers: {
'ContentType': 'application/json',
'Authorization': 'Bearer your_token_here'
},
body: JSON.stringify({ name: 'Alice', email: 'alice@example.com' })
})
.then(...)
```
请求体(Body): 可以发送各种类型的数据,包括字符串、FormData、Blob,甚至 ReadableStream。这对于文件上传、发送 JSON 数据等场景非常有用。
模式(Mode): Fetch API 引入了 `mode` 选项,用于处理跨域请求,如 `cors`、`nocors`、`sameorigin`。这为前端处理跨域问题提供了更标准化的解决方案。
凭证(Credentials): 同样可以通过 `credentials` 选项控制是否发送 cookies 或认证信息,例如 `include`、`sameorigin`、`omit`。

3. 流式处理(Streaming)的可能性:

Fetch API 的一个重要特性是它支持流式处理。`response.body` 是一个 `ReadableStream`,这意味着我们可以开始处理响应数据,而无需等待整个响应下载完成。

服务器发送事件(ServerSent Events, SSE): Fetch API 非常适合处理 SSE。当服务器持续发送数据时,我们可以逐块地读取响应体,实现实时更新。
大文件下载: 在下载大型文件时,同样可以利用流式处理,将数据分块写入文件,避免一次性加载大量数据到内存中,提高效率并降低内存占用。

4. 与 Service Worker 的无缝集成:

Service Worker 是前端实现离线访问、消息推送、背景同步等高级功能的关键。Fetch API 与 Service Worker 天生就非常契合。

拦截和修改请求: Service Worker 可以拦截所有的网络请求,并使用 Fetch API 来处理它们。这意味着我们可以自定义请求的响应,例如从缓存中提供数据,或者在没有网络连接时返回预设的响应。
缓存策略的实现: Service Worker 结合 Fetch API,使得开发者能够完全掌控资源的缓存策略,实现精细化的离线体验。

5. 逐步淘汰 `XMLHttpRequest` 的趋势:

`XMLHttpRequest` 已经存在了相当长的时间,虽然功能强大,但其 API 设计确实显得有些陈旧。Fetch API 的出现,不仅是对 XHR 的一个现代化升级,也代表了 Web 平台未来发展的方向。各大浏览器厂商都在积极推广和支持 Fetch API,而新的 Web API 也大多是基于 Promise 和 Fetch API 的理念来设计的。

6. 标准化和未来的发展:

Fetch API 是一个 W3C 标准,这意味着它拥有更广泛的浏览器支持和更长远的生命周期。随着 Web 技术的发展,Fetch API 也会不断得到更新和增强,为前端开发者提供更强大的网络请求能力。

总结一下,为什么要在前端项目中用 Fetch API?

代码更简洁、可读性更强: Promise 的原生支持,让异步操作的管理变得轻松愉快。
更精细的控制: 灵活的请求配置选项,满足各种复杂的网络请求场景。
高性能潜力: 流式处理能力,尤其在处理大量数据或实时通信时优势明显。
与现代 Web 技术(如 Service Worker)的良好集成: 为构建更高级的 Web 应用打下基础。
符合 Web 标准,面向未来: 顺应技术发展趋势,选择更现代、更具扩展性的解决方案。

虽然 `XMLHttpRequest` 仍然有效,但 Fetch API 凭借其现代化的设计和强大的功能,已经成为了前端开发中处理网络请求的首选方案。拥抱 Fetch API,就是拥抱更高效、更优雅、更具未来感的 Web 开发方式。

网友意见

user avatar

axios 是给 Node 用的 fetch 替代品,因为 Node 一直没有原生的 fetch,只提供一个从 Node 早起延续下来的 http 模块。因为 http 模块不好用,axios 封装的 API 有价值。因为 axios 能够在 Node 和前端共用同一个 API,所以如果前后端都用 JavaScript 写,使用 axios 的代码可以服用。

Node v17 终于要引入 fetch API 了,虽然暂时只是实验性支持:

这意味着以后使用 fetch 的代码也可以在前后端之间复用了。其实之前也可以,但后端需要引入 node-fetch 而前端不需要。有了原生 fetch 之后,前后端无需引入任何外部依赖就能使用同一个网络 API。


因为 axios 在前端的实现依赖于 XMLHttpRequest,而这个东西不会再向前演化,所以 axios 在前端不太可能有语法之外的新功能。fetch 还可以继续向前演化,如果 Node 同步演化的话,fetch 在两端都会持续获得新功能。

前端在引入 fetch 时已经做好了跟其它前端内建类型的兼容,这也是 axios 底层的 XMLHttpRequest 不可能支持的。当然,axios 可以在封装的时候加入支持,但 fetch 的支持是原生的。这包括为 fetch 引入的 Header、Request、Response 类型,也包括 fetch 之外的内建类型如 URL、Blob、BufferArray、FormData、URLSearchParams、ReadableStream、WritableStream 等。这些内建类型还有机会继续演化,fetch 可能会跟着进行兼容性演化。

前端的 axios 如同被智子锁定了科技一样,fetch 支持的流式(stream)请求和响应都没办法做。理论上 axios 最终可以在不改变 API 的前提下切换到 fetch 上面去,但如果 axios 变成了一个 fetch 的封装,那等 Node 有了 fetch 之后为什么不直接用 fetch 呢?

类似的话题

  • 回答
    为什么要在前端项目里头拥抱 Fetch API?在前端开发的漫漫长路上,我们总是在与各种数据打交道:从服务器获取用户信息、加载产品列表、提交表单数据……而这一切的核心,都离不开网络请求。过去,JavaScript 提供了 `XMLHttpRequest` (XHR) 来实现这些功能,但随着 Web .............

本站所有内容均为互联网搜索引擎提供的公开搜索信息,本站不存储任何数据与内容,任何内容与数据均与本站无关,如有需要请联系相关搜索引擎包括但不限于百度google,bing,sogou

© 2025 tinynews.org All Rights Reserved. 百科问答小站 版权所有