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>
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值