JavaScript的XMLHttpRequest是什么?怎么用?

xmlhttprequest(xhr)在前端与服务器交互中依然有其价值,主要原因有三点:1. 浏览器兼容性极佳,适用于维护老旧项目;2. 提供底层控制能力,如请求进度监听,适合大文件上传等场景;3. 许多旧库基于xhr封装,理解其原理有助于调试和深入掌握网络请求机制。

JavaScript的XMLHttpRequest是什么?怎么用?

谈到前端与服务器交互,XMLHttpRequest(XHR)无疑是一个绕不开的话题。简单来说,它就是浏览器提供的一套API,让JavaScript能够发送HTTP请求到服务器,并在不刷新整个页面的情况下接收响应。这正是我们常说的AJAX(Asynchronous JavaScript and XML)技术的核心,它让网页体验从“点击刷新”走向了“无缝加载”的时代。

JavaScript的XMLHttpRequest是什么?怎么用?

解决方案

使用XMLHttpRequest进行网络请求,基本步骤是这样的:

创建XHR对象:这是所有操作的起点。

立即学习“Java免费学习笔记(深入)”;

JavaScript的XMLHttpRequest是什么?怎么用?

const xhr = new XMLHttpRequest();

配置请求:使用open()方法指定请求方法(GET, POST等)、URL和是否异步。

xhr.open('GET', '/api/data', true); // GET请求到/api/data,异步

设置回调函数:监听请求状态的变化。最常用的是onreadystatechange,它会在readyState属性改变时触发。readyState有五个值:

JavaScript的XMLHttpRequest是什么?怎么用?0: UNSENT (未初始化)1: OPENED (已打开)2: HEADERS_RECEIVED (已发送,接收到头信息)3: LOADING (下载中,接收到部分数据)4: DONE (完成,所有数据已接收)当readyState为4且status为200时,表示请求成功并接收到完整响应。也可以使用更现代的onloadonerror事件监听。

xhr.onreadystatechange = function() {if (xhr.readyState === 4) {    if (xhr.status >= 200 && xhr.status < 300) {        // 请求成功        console.log('响应数据:', xhr.responseText);    } else {        // 请求失败        console.error('请求失败,状态码:', xhr.status);    }}};

// 或者使用更简洁的事件监听xhr.onload = function() {if (xhr.status >= 200 && xhr.status

xhr.onerror = function() {console.error(‘网络错误或请求被阻止。’);};


发送请求:使用send()方法发送请求。如果是POST请求,数据会作为参数传给send()

xhr.send(); // 对于GET请求,send()通常不带参数// 对于POST请求,可能需要设置Content-Type并发送数据// xhr.setRequestHeader('Content-Type', 'application/json');// xhr.send(JSON.stringify({ key: 'value' }));

为什么在现代Web开发中,XMLHttpRequest依然有其一席之地?

尽管前端世界日新月异,fetch API等新星层出不穷,但XMLHttpRequest这老伙计依然没有完全退出历史舞台。我个人觉得,这主要有几个原因。首先,它的浏览器兼容性简直是无敌的。你几乎不用担心任何主流甚至一些老旧浏览器不支持XHR,这对于维护一些历史项目或者需要极致兼容性的场景来说,是个巨大的优势。

其次,XHR提供了一些底层控制能力,比如它内置了对请求进度(onprogress事件)的良好支持,这在上传大文件或者需要展示精确进度条的场景下,用起来比fetch要直观方便不少,fetch需要一些额外的操作才能实现类似效果。再者,很多现有的JavaScript库和框架,特别是那些年代稍久远的,它们的底层网络请求依然是基于XHR封装的。理解XHR的工作原理,对于我们深入理解这些库的运作机制,以及调试一些老代码中的网络问题,都是非常有帮助的。它就像是Web请求的“根基”,即便上面盖了高楼大厦,地基的知识依然重要。

当然,这并不是说它比fetch更好,而是说它有其存在的合理性,特别是在特定的需求和历史背景下。

如何处理XMLHttpRequest的异步操作和常见的错误?

处理XHR的异步操作,最经典的方式就是依赖回调函数。就像前面提到的onreadystatechange,它会在请求的不同生命周期阶段被触发。这种基于事件和回调的模式,在处理简单请求时没问题,但如果你的业务逻辑涉及到多个串联的请求,或者需要复杂的错误处理和状态管理,就很容易陷入所谓的“回调地狱”(Callback Hell),代码会变得层层嵌套,难以阅读和维护。

为了缓解这个问题,现代JavaScript中我们通常会用Promise来封装XHR,或者直接使用async/await语法糖。虽然XHR本身不返回Promise,但我们可以很容易地把它包装起来:

function makeRequest(method, url, data = null) {    return new Promise((resolve, reject) => {        const xhr = new XMLHttpRequest();        xhr.open(method, url, true);        xhr.onload = function() {            if (xhr.status >= 200 && xhr.status  {        console.log('用户数据:', response);    })    .catch(error => {        console.error('获取用户数据失败:', error);    });

至于常见的错误,主要有几类:

网络错误(Network Error):这通常发生在请求无法发送或在传输过程中中断时,比如用户断网、服务器宕机、DNS解析失败等。onerror事件就是用来捕获这类错误的。HTTP状态码错误:服务器成功接收并处理了请求,但返回了一个非2xx的状态码,比如404(未找到)、401(未授权)、500(服务器内部错误)等。这类错误需要你在onreadystatechangeonload中通过检查xhr.status来判断。跨域请求(CORS)问题:当你的前端页面尝试请求一个与当前页面不同源(协议、域名、端口任一不同)的资源时,浏览器会执行同源策略。如果服务器没有正确配置CORS响应头(如Access-Control-Allow-Origin),请求就会被浏览器拦截,导致onerror触发,或者虽然请求发出了但响应被浏览器屏蔽。这是前端开发中非常常见且让人头疼的问题,通常需要在后端进行配置。超时(Timeout):如果请求在设定的时间内没有得到响应,XHR会触发ontimeout事件。你可以通过xhr.timeout = milliseconds来设置超时时间。

处理这些错误的关键在于细致的错误捕获和清晰的错误信息反馈,让用户知道发生了什么,或者方便开发者调试。

XMLHttpRequest与Fetch API相比,有哪些优劣势?

当我们在讨论XHR时,很难不把它和现代的fetch API拿出来比较。它们都是浏览器提供的网络请求方式,但设计理念和使用方式上有着明显的差异。

XMLHttpRequest的优势:

成熟且兼容性极佳:这是它最大的资本,几乎所有浏览器都支持,无需担心兼容性问题。内置进度事件onprogressonloadstartonloadend等事件,对于文件上传下载等需要实时进度反馈的场景,用起来非常直接方便。可中断请求:通过xhr.abort()方法,可以随时取消一个正在进行的请求。

XMLHttpRequest的劣势:

API设计相对老旧和繁琐:基于事件和回调的模式,对于复杂的异步流程,容易导致代码可读性差,陷入回调地狱。不直接支持Promise:虽然可以通过封装实现Promise化,但原生API并非基于Promise,与现代JavaScript的异步编程风格不符。处理JSON不够直接:通常需要手动解析responseText为JSON。

Fetch API的优势:

Promise化设计:原生返回Promise,与async/await结合使用,使得异步代码更加简洁、直观、易读,彻底摆脱回调地狱。API设计更现代化和模块化RequestResponse对象的使用,让请求和响应的处理更加清晰和灵活。默认处理JSONresponse.json()方法直接返回解析后的JSON数据,非常方便。支持流(Streams):可以处理大型响应数据流,提高性能。

Fetch API的劣势:

不直接支持请求进度:虽然可以通过ReadableStream实现,但不如XHR的onprogress事件直接。对HTTP错误码不抛出异常fetch只有在网络错误时才reject Promise,对于4xx或5xx等HTTP错误码,它依然会resolve,需要手动检查response.okresponse.status来判断请求是否成功。这在使用时需要特别注意,否则很容易漏掉服务器返回的业务错误。无法直接中断请求:需要配合AbortController才能实现请求的取消。兼容性不如XHR:虽然现在主流浏览器支持度已经很高,但在一些老旧环境中可能仍需polyfill。

总的来说,对于新的项目开发,fetch API因其现代化的Promise设计和简洁的API,通常是首选。但XHR依然有其不可替代的价值,尤其是在处理特定需求(如进度条)和维护老旧代码时。理解两者,才能在实际开发中做出更合适的选择。

以上就是JavaScript的XMLHttpRequest是什么?怎么用?的详细内容,更多请关注创想鸟其它相关文章!

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 chuangxiangniao@163.com 举报,一经查实,本站将立刻删除。
发布者:程序猿,转转请注明出处:https://www.chuangxiangniao.com/p/1508967.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2025年12月20日 05:11:47
下一篇 2025年12月20日 05:12:06

相关推荐

  • 优化HTML表单文件上传与URL重定向:异步操作的正确处理

    本文探讨了在html表单提交过程中,当需要异步动态设置表单 `action` 属性时,如何避免因 `e.preventdefault()` 和异步操作时序问题导致的提交失败或重定向失效。我们将深入分析常见错误模式,并提供一种将异步 `action` 更新与显式表单提交结合的解决方案,确保文件上传和页…

    好文分享 2025年12月21日
    000
  • React Native 动态音效播放指南:实现点击播放对应声音

    本教程详细介绍了如何在 React Native 应用中实现动态音效播放功能。我们将使用 `react-native-sound` 库,涵盖从环境搭建、音频资源管理、核心播放逻辑到 UI 交互的全过程,并提供示例代码和重要注意事项,帮助开发者轻松实现点击按钮播放特定音效的需求。 在移动应用开发中,音…

    2025年12月21日
    000
  • JavaScript可选链操作符(?.)深度解析

    本文深入探讨了javascript中的可选链操作符(`?.`),这一es2020新特性,旨在解决访问对象深层属性或调用方法时,因中间引用为`null`或`undefined`而导致的`typeerror`。通过详细的语法解析、工作原理和代码示例,文章展示了可选链如何简化条件判断,提升代码健壮性和可读…

    2025年12月21日
    000
  • JavaScript Promise在计算器函数中的应用与优化

    本文探讨了如何在javascript的`calculator`类中实现一个返回promise的`calculate`方法。通过分析测试用例,我们指出了原始实现中的常见误区,如不必要的延迟、错误的参数处理和上下文绑定问题。最终,我们提供了一个基于`async/await`和`try…cat…

    2025年12月21日
    000
  • JavaScript索引数据库与离线应用

    IndexedDB是浏览器内存储结构化数据的低层API,支持索引、事务和异步操作,可存储对象、Blob等复杂类型,结合Service Worker实现离线优先应用,通过创建索引优化查询性能,保障数据一致性与高效访问。 现代Web应用需要在用户离线时依然保持可用,同时快速访问大量数据。JavaScri…

    2025年12月21日
    000
  • 使用 Promise 实现计算器中的异步计算

    本文将介绍如何使用 Promise 在 JavaScript 计算器类中实现异步计算功能。我们将分析现有代码的问题,并提供一个简洁、高效的解决方案,确保计算在成功时返回结果,并在出现错误时拒绝 Promise 并返回 NaN。 问题分析 原代码中的 calculate 函数存在以下几个主要问题: 不…

    2025年12月21日
    000
  • 使用 Vuetify 构建所见即所得(WYSIWYG)编辑器:原理与实践

    本文将探讨如何利用 vuetify 框架高效构建所见即所得(wysiwyg)编辑器。我们将介绍 vuetify 的核心组件,如 v-textarea 和 v-btn-toggles,如何简化编辑器的实现过程。同时,文章也将触及不依赖 vuetify 进行开发,以深入理解响应式属性绑定和动态文本样式控…

    2025年12月21日
    000
  • Vue.js v-if 多条件判断及与 v-for 结合的优化策略

    本文详细探讨了 vue.js 中 `v-if` 指令如何进行多条件判断,并纠正了常见的语法错误。鉴于 vue 3 不推荐在同一元素上同时使用 `v-if` 和 `v-for`,文章提供了使用 “ 标签的替代方案。更进一步,我们推荐利用计算属性(`computed` property)来高…

    2025年12月21日
    000
  • 深入探讨:检测原生密码输入框可见状态的挑战与解决方案

    本文旨在探讨如何检测html密码输入框的原生“显示密码”图标(如::-ms-reveal)的激活状态,并根据此状态触发css样式或javascript动画。我们将详细解析当前css :has()选择器与伪元素结合使用的局限性,解释为何无法直接通过原生机制检测密码可见性。最后,文章将提供一个健壮且跨浏…

    2025年12月21日
    000
  • Node.js 循环中错误处理与流程控制策略

    本文探讨在 Node.js 循环中如何有效处理迭代内部错误并控制循环后续流程。针对不同业务需求,提供了两种核心策略:一是使用 `break` 语句在首次错误时立即中断循环;二是利用错误标志(`errorFlag`)完成所有迭代,但根据是否发生错误来决定循环后的操作,从而实现更精细的错误管理和程序流控…

    2025年12月21日
    000
  • 增强按钮可访问性:动态值与 aria-describedby 的正确用法

    当按钮既需要触发动作又需显示动态值时,直接使用 `aria-label` 会覆盖文本内容,导致屏幕阅读器无法读取当前值。最佳实践是将动态值作为独立DOM元素,并通过 `aria-describedby` 关联至按钮,确保屏幕阅读器用户能同时获取按钮功能和相关信息,但需注意用户可能禁用描述性内容。 在…

    2025年12月21日
    000
  • JavaScript函数组合与柯里化

    柯里化将多参函数转化为单参函数链,便于参数复用;函数组合通过pipe或compose连接函数,实现数据流式传递;二者结合可提升代码的模块化与可读性。 函数组合与柯里化是函数式编程中的两个核心概念,它们能帮助我们写出更简洁、可复用、易测试的JavaScript代码。理解并掌握这两个技巧,可以显著提升代…

    2025年12月21日
    000
  • 深入理解CSS :has() 与原生密码显示按钮的交互限制及实现替代方案

    本文探讨了如何检测原生密码输入框的可见性状态,特别是针对 `::-ms-reveal` 伪元素的交互。我们深入分析了css `:has()` 伪类在处理伪元素时的当前限制,解释了为何无法直接通过css判断密码是否可见。鉴于这些技术壁垒,文章提供了一种基于自定义切换控件的可靠替代方案,并附带了详细的代…

    2025年12月21日
    000
  • Angular Formly 自定义组件验证消息未在失焦时显示问题的解决方案

    在 angular 应用中,当我们需要将自定义组件集成到响应式表单或 formly 表单中时,通常会实现 `controlvalueaccessor` 接口。这个接口允许自定义组件充当表单控件,与 angular 的表单系统进行双向数据绑定和状态同步。然而,一个常见的挑战是,在自定义组件中,表单验证…

    2025年12月21日
    000
  • 构建基于Vuetify的所见即所得(WYSIWYG)编辑器

    本文探讨了如何利用vuetify的现有组件快速构建一个功能性的所见即所得(wysiwyg)编辑器。我们将重点介绍v-textarea作为内容输入区,以及v-btn-toggle和v-btn作为格式化工具栏的实现方式,并提供示例代码以帮助开发者理解其核心逻辑。同时,文章也提及了脱离框架,从零开始构建w…

    2025年12月21日
    000
  • React组件正确渲染JSON数据的实践指南

    本文旨在解决react应用中渲染json数据时常见的“不显示”问题。我们将深入探讨如何正确通过`props`传递数据、利用`usestate`和`useeffect`管理组件状态与数据加载,以及在列表渲染中`key`属性的重要性。通过示例代码,帮助开发者掌握从本地json文件或异步api有效加载并展…

    2025年12月21日
    000
  • JavaScript blob流式数据处理

    Blob与流式处理可提升大文件性能,通过分块读取减少内存占用;利用Blob.stream()和ReadableStream实现异步逐块处理,适用于大文本解析、日志分析等场景。 在现代Web开发中,处理大文件或大量数据时,直接加载整个资源到内存中会带来性能问题。JavaScript中的Blob和流式处…

    2025年12月21日
    000
  • JavaScript自动化测试框架

    Jest适合React项目快速上手,Vitest适配Vite提升性能,Mocha灵活自定义,Cypress/Playwright用于E2E测试,选型需结合技术栈,配合单元、集成、E2E测试保障质量。 JavaScript自动化测试框架帮助开发者验证代码的正确性,提升开发效率,保障项目质量。随着前端工…

    2025年12月21日
    000
  • JavaScript WebAssembly混合编程架构

    WebAssembly负责计算密集型任务,JavaScript处理交互与API调用,通过共享内存与TypedArray高效通信,结合Emscripten、Rust或AssemblyScript等工具链实现高性能混合架构。 在现代Web开发中,JavaScript与WebAssembly的混合编程架构…

    2025年12月21日
    000
  • JavaScript惰性求值与延迟计算模式

    惰性求值通过延迟计算提升性能,核心是仅在需要时执行。JavaScript可用函数封装、生成器或自定义链式结构实现,如Lodash的chain方法,避免中间结果开销,适用于大数据与复杂运算场景。 惰性求值和延迟计算是优化JavaScript性能的重要手段,尤其在处理大量数据或复杂运算时能显著提升效率。…

    2025年12月21日
    000

发表回复

登录后才能评论
关注微信