阅读 74

Ajax学习笔记——Ajax基础总结

1. AJAX 简介

AJAX 全称为 Asynchronous JavaScript And XML,就是异步的 JS 和 XML。通过 AJAX 可以在浏览器中向服务器发送异步请求,最大的优势:==无刷新获取数据==。AJAX 不是新的编程语言,而是一种将现有的标准组合在一起使用的新方式。

2. AJAX特点

2.1AJAX 的优点
  1. 可以无需刷新页面而与服务器端进行通信。

  2. 允许你根据用户事件来更新部分页面内容。

2.2 AJAX 的缺点
  1. 没有浏览历史,不能回退

  2. 存在跨域问题(同源)

  3. SEO 不友

3.使用

3.1 XMLHttpRequest

有关Ajax的所有操作都是通过XMLHttpRequest来操作的。

3.2 服务端的准备

在使用Ajax之前,因为需要对服务端发送请求,因此这里使用express框架,创建server.js文件搭建一个服务器。由于Ajax默认是服从同源策略,因此在服务器中设置Access-Control-Allow-Origin响应头在解决跨域问题(CORS跨域)。

// server.js const express = require('express') // 创建应用对象 const app = express() // 创建路由规则 app.get('/index', (request, response) => {   // 设置允许跨域的响应头   response.setHeader('Access-Control-Allow-Origin', '*')   // 设置响应体   response.send('hello ajax') }) app.post('/index', (request, response) => {   response.setHeader('Access-Control-Allow-Origin', '*')   response.send('post ajax') }) // 监听端口,启动服务 app.listen(8282, () => {   console.log('服务器启动,8000端口监听中...'); }) 复制代码

在测试过程中,要保证服务端处于开启状态,开启命令:node server.js

3.3 ajax发送get请求

准备一个html文档,点击按钮向接口http://127.0.0.1:8282/index发送请求,请求的数据显示在div

<!DOCTYPE html> <html lang="en"> <head>   <meta charset="UTF-8">   <meta name="viewport" content="width=device-width, initial-scale=1.0">   <title>ajax get请求</title>   <style>     .result{       border: 1px solid black;       width: 250px;       height: 150px;     }   </style>    </head> <body>   <button>发送请求</button>   <br>   <br>   <div class="result"></div>   <script>     let button = document.getElementsByTagName('button')[0]     let divObj = document.getElementsByClassName('result')[0]     button.addEventListener('click', function(){       // 创建对象       const xhr = new XMLHttpRequest()       // 设置请求方法和url       xhr.open('GET', 'http://127.0.0.1:8282/index')       // 发送请求       xhr.send()       // 处理服务端返回的结果       xhr.onreadystatechange = function() {         /*            readyState属性值:             0 - 对象未初始化             1 - open方法执行             2 - send方法执行             3 - 服务端返回部分结果             4 - 服务端返回全部结果         */         if(xhr.readyState === 4) {           // 判断响应状态码  2xx成功           if(xhr.status >= 200 && xhr.status < 300) {             // 响应行             // console.log(xhr.status)             // console.log(xhr.statusText) // 状态描述             // // 响应头             // console.log(xhr.getAllResponseHeaders())             // // 响应体             // console.log(xhr.response)             divObj.innerHTML = xhr.response           }         }       }     })   </script> </body> </html> 复制代码

结果: 在这里插入图片描述 若需要在发送get请求时携带参数,则url应写为:

xhr.open('GET', 'http://127.0.0.1:8282/index?a=100&b=200&c=300') 复制代码

3.4 发送post请求

将原来代码中xhr.open()第一个参数右GET改为POST

xhr.open('POST','http://127.0.0.1:8282/index') 复制代码

在这里插入图片描述 使用post方法发送请求体时,要将请求体内容放在send方法中,格式不固定,只要服务端能够处理即可:

// 形式一 xhr.send('a=100&b=200&c=300') // 形式二 xhr.send('a:100&b:200&c:300') // ... 复制代码

3.5 设置请求头信息
// Content-Type  请求体类型 // application/x-www-form-urlencoded 查询字符串类型 xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded') 复制代码

自定义请求头

xhr.setRequestHeader('Name', 'Alice') 复制代码

此时服务端需要设置Access-Control-Allow-Headers字段,表示可以接收处理的请求头,否则会报错:

app.post('/index', (request, response) => {   response.setHeader('Access-Control-Allow-Origin', '*')   response.setHeader('Access-Control-Allow-Headers', '*')   response.send('post ajax') }) 复制代码

一般可以在请求头中存放服务端要校验的信息。

3.6 服务端响应 json数据时

服务端若需要将json对象的数据返回给客户端,需要将其转为JSON字符串再发送,server.js添加代码如下:

// all()表示可以匹配所有请求的方法 app.all('/json-data', (request, response) => {   response.setHeader('Access-Control-Allow-Origin', '*')   response.setHeader('Access-Control-Allow-Headers', '*')   // 响应json数据,需要将json对象转为字符串格式   const data = {     'name': 'Alice',     'age': 34   }   response.send(JSON.stringify(data)) }) 复制代码

客户端处理结果时,需要将json字符串转为json对象:

button.addEventListener('click',function() {   let xhr = new XMLHttpRequest()   xhr.open('GET', 'http://127.0.0.1:8282/json-data')   xhr.send()   xhr.onreadystatechange = function() {     if(xhr.readyState === 4) {       if(xhr.status >= 200 && xhr.status < 300) {         // 将服务端返回的json数据转为json对象         let data = JSON.parse(xhr.response)         console.log(data)       }     }   } }) 复制代码

控制台: 在这里插入图片描述 或者可以直接在xhr对象上设置响应体类型为json,就不用执行转换步骤:

button.addEventListener('click',function() {   let xhr = new XMLHttpRequest()   xhr.responseType = 'json'   xhr.open('GET', 'http://127.0.0.1:8282/json-data')   xhr.send()   xhr.onreadystatechange = function() {     if(xhr.readyState === 4) {       if(xhr.status >= 200 && xhr.status < 300) {         let data = xhr.response         console.log(data)       }     }   } }) 复制代码

控制台: 在这里插入图片描述

3.7 解决IE缓存问题

在IE浏览器中,发送Ajax请求回来的数据会被缓存,导致在某些时效性比较强的场景下会得到错误的数据。因此需要在url中携带一个表示时间戳的参数,使得IE浏览器认为每次都在发送不同的请求:

 xhr.open('get', 'http://127.0.0.1:8282/json-data?t='+Date.now()) 复制代码

3.8 请求超时和网络异常处理

可以在xhr对象上设置超时时间,若在这个时间之内没有获取到响应结果,则会自动取消。例如,在服务端设置3秒后返回结果:

// 延迟响应 app.get('/delay', (request, response) => {   response.setHeader('Access-Control-Allow-Origin', '*')   setTimeout(() => {     response.send('延迟响应')   }, 3000) }) 复制代码

客户端设置超时时间为2s

<script>   let button = document.getElementsByTagName('button')[0]   let divObj = document.getElementsByTagName('div')[0]   button.addEventListener('click', function() {     let xhr = new XMLHttpRequest()     // 设置超时2s取消请求     xhr.timeout = 2000     // 超时回调     xhr.ontimeout = function() {       alert('网络较慢,请稍后重试!')     }     xhr.open('GET', 'http://127.0.0.1:8282/delay')     xhr.send()     xhr.onreadystatechange = function() {       if(xhr.readyState === 4) {         if(xhr.status >= 200 && xhr.status < 300) {           divObj.innerHTML = xhr.response         }       }     }   }) </script> 复制代码

控制台: 在这里插入图片描述 也可以设置网络异常时的回调:

xhr.onerror = function() {   alert('网络异常!') } 复制代码

在浏览器中,将网络状态设为offline,模拟没有网络的情况 在这里插入图片描述

3.9 取消请求

xhr对象上的abort()可以用于取消请求:

xhr.abort() 复制代码

3.10 重复发送请求问题

当我们多次点击按钮发送请求时,会对服务器造成一定压力,且多次请求的操作并不是必要的,解决这个重复请求问题,需要当再次发送请求时,把上一次没完成的请求取消掉。

<body>   <button>发送请求</button>   <script>     let button = document.getElementsByTagName('button')[0]     // 是否正在处理ajax请求的标识     let isSending = false       let xhr     button.addEventListener('click', function() {       // 如果上一次请求还在,取消,重新发起请求       if(isSending) {         xhr.abort()       }       xhr = new XMLHttpRequest()       isSending = true       xhr.open('GET', 'http://127.0.0.1:8282/delay')       xhr.send()       xhr.onreadystatechange = function() {         if(xhr.readyState === 4) {           // 请求处理完,无论状态码是什么,都是为false           isSending = false         }       }     })   </script> </body>


作者:前端小木屋
链接:https://juejin.cn/post/6997333407583862814


文章分类
后端
文章标签
版权声明:本站是系统测试站点,无实际运营。本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 XXXXXXo@163.com 举报,一经查实,本站将立刻删除。
相关推荐