您的位置:首页 > 游戏 > 游戏 > 4 Ajax

4 Ajax

2024/12/23 15:03:54 来源:https://blog.csdn.net/ever__ever/article/details/140526809  浏览:    关键词:4 Ajax

Ajax 概述


Asynchronous JavaScript + XML(异步JavaScript和XML),其本身不是一种新技术,而是一个在 2005年被Jesse James Garrett提出的新术语,用来描述一种使用现有技术集合的‘新’方法,包括: HTML 或 XHTML, CSS,JavaScript,DOM,XML,XSLT,以及最重要的 XMLHttpRequest;当使用结合了这些技术的AJAX模型以后, 网页应用能够快速地将增量更新呈现在用户界面上,而不需要重载(刷新)整个页面;这使得程序能够更快地回应用户的操作;

尽管X在Ajax中代表XML,但由于JSON的许多优势,比如更加轻量以及作为Javascript的一部分,目前JSON的使用比XML更加普遍;JSON和XML都被用于在Ajax模型中打包信息;

Ajax 优点:

  1. 最大的一点是页面无刷新,用户的体验非常好
  2. 使用异步方式与服务器通信,具有更加迅速的响应能力
  3. 可以把以前一些服务器负担的工作转嫁到客户端,利用客户端闲置的能力来处理,减轻服务器和带宽的负担,节约空间和宽带租用成本。并且减轻服务器的负担, Ajax的原则是“按需取数据”,可以最大程度的减少冗余请求,和响应对服务器造成的负担
  4. 基于标准化的并被广泛支持的技术,不需要下载插件或者小程序

Ajax 缺点:

  1. Ajax不支持浏览器back按钮
  2. 安全问题,Ajax暴露了与服务器交互的细节
  3. 对搜索引擎的支持比较弱
  4. 破坏了程序的异常机制

Ajax 工作流程


  1. 网页中发生一个事件(页面加载、按钮点击)
  2. 由 JavaScript 创建 XMLHttpRequest 对象
  3. XMLHttpRequest 对象向 web 服务器发送请求
  4. 服务器处理该请求
  5. 服务器将响应发送回网页
  6. 由 JavaScript 读取响应
  7. 由 JavaScript 执行正确的动作(比如更新页面)

Ajax适用场景

  1. 表单驱动的交互
  2. 深层次的树的导航
  3. 快速的用户与用户间的交流响应
  4. 类似投票、yes/no等无关痛痒的场景
  5. 对数据进行过滤和操纵相关数据的场景
  6. 普通的文本输入提示和自动完成的场景

Ajax不适用场景

  1. 部分简单的表单
  2. 搜索
  3. 基本的导航
  4. 替换大量的文本
  5. 对呈现的操纵

XMLHttpRequest API


XMLHttpRequest(XHR)对象用于与服务器交互;通过 XMLHttpRequest 可以在不刷新页面的情况下请求特定 URL,获取数据;这允许网页在不影响用户操作的情况下,更新页面的局部内容;XMLHttpRequest 在 AJAX 编程中被大量使用;
尽管名称如此,XMLHttpRequest 可以用于获取任何类型的数据,而不仅仅是 XML;它甚至支持 HTTP 以外的协议(包括 file:// 和 FTP),尽管可能受到更多出于安全等原因的限制;
如果您的通信流程需要从服务器端接收事件或消息数据,请考虑通过 EventSource 接口使用 server-sent events;对于全双工的通信, WebSocket 可能是更好的选择;

1. XMLHttpRequest 构造函数

XMLHttpRequest() // 该构造函数用于初始化一个 XMLHttpRequest 实例对象;在调用下列任何其他方法之前,必须先调用该构造函数,或通过其他方式,得到一个实例对象;

2. XMLHttpRequest 属性

XMLHttpRequest.readyState // 只读,返回一个 XMLHttpRequest  代理当前所处的状态- 0	- UNSENT -- XMLHttpRequest 代理已被创建,但尚未调用 open() 方法- 1 - OPENED -- open() 方法已经被触发;在这个状态中,可以通过 setRequestHeader() 方法来设置请求的头部,可以调用 send() 方法来发起请求- 2 - HEADERS_RECEIVED -- send() 方法已经被调用,响应头也已经被接收- 3 - LOADING -- 响应体部分正在被接收;如果 responseType 属性是“text”或空字符串,responseText 将会在载入的过程中拥有部分响应数据- 4 - DONE -- 请求操作已经完成;这意味着数据传输已经彻底完成或失败XMLHttpRequest.status // 只读,返回 XMLHttpRequest 响应中的数字状态码- 只读属性 XMLHttpRequest.status 返回了XMLHttpRequest 响应中的数字状态码- status 的值是一个无符号短整型;在请求完成前,status的值为0- 值得注意的是,如果 XMLHttpRequest 出错,浏览器返回的 status 也为0XMLHttpRequest.responseText // 只读,一个请求被发送后,从服务器端返回文本

3. XMLHttpRequest 方法

XMLHttpRequest.open(method,url,async,user,password) // 初始化一个请求- method -- 要使用的HTTP方法- url -- 一个DOMString表示要向其发送请求的URL- async -- 一个可选的布尔参数,表示是否异步执行操作,默认为true;如果值为false,send()方法直到收到答复前不会返回;如果true,已完成事务的通知可供事件监听器使用;如果
multipart属性为true则这个必须为true,否则将引发异常- user -- 可选的用户名用于认证用途;默认为null- password -- 可选的密码用于认证用途;默认为nullXMLHttpRequest.setRequestHeader('Content-Type','application/x-www-form-urlencoded') // 设置HTTP请求头部的方法;此方法必须在 open() 方法和 send() 之间调用- 如果没有设置 Accept 头部信息,则会发送带有 "*/*" 的Accept 头部XMLHttpRequest.send(body) // 用于发送 HTTP 请求;如果是异步请求(默认为异步请求),则此方法会在请求发送后立即返回;如果是同步请求,则此方法直到响应到达后才会返回- body -- 在XHR请求中要发送的数据体. 可以是 Document,在这种情况下,它在发送之前被序列化XMLHttpRequest.onreadystatechange = callback // 监听 readyState 属性发生变化触发

axios (网络请求库)


1. axios 方法

axios.create([config]) // 创建 axios 实例

2. axios 请求配置

{// `url` 是用于请求的服务器 URLurl: '/user',// `method` 是创建请求时使用的方法method: 'get',// default// `baseURL` 将自动加在 `url` 前面,除非 `url` 是一个绝对 URL;// 它可以通过设置一个 `baseURL` 便于为 axios 实例的方法传递相对 URLbaseURL: 'https://some-domain.com/api/',// `transformRequest` 允许在向服务器发送前,修改请求数据// 只能用在 'PUT','POST' 和 'PATCH' 这几个请求方法// 后面数组中的函数必须返回一个字符串,或 ArrayBuffer,或 StreamtransformRequest: [function (data,headers) {// 对 data 进行任意转换处理return data;}],// `transformResponse` 在传递给 then/catch 前,允许修改响应数据transformResponse: [function (data) {// 对 data 进行任意转换处理return data;}],// `headers` 是即将被发送的自定义请求头headers: {'X-Requested-With': 'XMLHttpRequest'},// `params` 是即将与请求一起发送的 URL 参数// 必须是一个无格式对象(plain object)或 URLSearchParams 对象params: {ID: 12345},// `paramsSerializer` 是一个负责 `params` 序列化的函数// (e.g. https://www.npmjs.com/package/qs,http://api.jquery.com/jquery.param/)paramsSerializer: function(params) {return Qs.stringify(params,{arrayFormat: 'brackets'})},// `data` 是作为请求主体被发送的数据// 只适用于这些请求方法 'PUT','POST',和 'PATCH'// 在没有设置 `transformRequest` 时,必须是以下类型之一:// - string,plain object,ArrayBuffer,ArrayBufferView,URLSearchParams// - 浏览器专属:FormData,File,Blob// - Node 专属: Streamdata: {firstName: 'Fred'},// `timeout` 指定请求超时的毫秒数(0 表示无超时时间)// 如果请求话费了超过 `timeout` 的时间,请求将被中断timeout: 1000,// `withCredentials` 表示跨域请求时是否需要使用凭证withCredentials: false,// default// `adapter` 允许自定义处理请求,以使测试更轻松// 返回一个 promise 并应用一个有效的响应 (查阅 [response docs](#response-api)).adapter: function (config) {/* ... */},// `auth` 表示应该使用 HTTP 基础验证,并提供凭据// 这将设置一个 `Authorization` 头,覆写掉现有的任意使用 `headers` 设置的自定义 `Authorization`头auth: {username: 'janedoe',password: 's00pers3cret'},// `responseType` 表示服务器响应的数据类型,可以是 'arraybuffer','blob','document','json','text','stream'responseType: 'json',// default// `responseEncoding` indicates encoding to use for decoding responses// Note: Ignored for `responseType` of 'stream' or client-side requestsresponseEncoding: 'utf8',// default// `xsrfCookieName` 是用作 xsrf token 的值的cookie的名称xsrfCookieName: 'XSRF-TOKEN',// default// `xsrfHeaderName` is the name of the http header that carries the xsrf token valuexsrfHeaderName: 'X-XSRF-TOKEN',// default// `onUploadProgress` 允许为上传处理进度事件onUploadProgress: function (progressEvent) {// Do whatever you want with the native progress event},// `onDownloadProgress` 允许为下载处理进度事件onDownloadProgress: function (progressEvent) {// 对原生进度事件的处理},// `maxContentLength` 定义允许的响应内容的最大尺寸maxContentLength: 2000,// `validateStatus` 定义对于给定的HTTP 响应状态码是 resolve 或 reject  promise ;如果 `validateStatus` 返回 `true` (或者设置为 `null` 或 `undefined`),promise 将被 resolve; 否则,promise 将被 rejectevalidateStatus: function (status) {return status >= 200 && status < 300; // default},// `maxRedirects` 定义在 node.js 中 follow 的最大重定向数目// 如果设置为0,将不会 follow 任何重定向maxRedirects: 5,// default// `socketPath` defines a UNIX Socket to be used in node.js.// e.g. '/var/run/docker.sock' to send requests to the docker daemon.// Only either `socketPath` or `proxy` can be specified.// If both are specified,`socketPath` is used.socketPath: null,// default// `httpAgent` 和 `httpsAgent` 分别在 node.js 中用于定义在执行 http 和 https 时使用的自定义代理;允许像这样配置选项:// `keepAlive` 默认没有启用httpAgent: new http.Agent({ keepAlive: true }),httpsAgent: new https.Agent({ keepAlive: true }),// 'proxy' 定义代理服务器的主机名称和端口// `auth` 表示 HTTP 基础验证应当用于连接代理,并提供凭据// 这将会设置一个 `Proxy-Authorization` 头,覆写掉已有的通过使用 `header` 设置的自定义 `Proxy-Authorization` 头;proxy: {host: '127.0.0.1',port: 9000,auth: {username: 'mikeymike',password: 'rapunz3l'}},// `cancelToken` 指定用于取消请求的 cancel token// (查看后面的 Cancellation 这节了解更多)cancelToken: new CancelToken(function (cancel) {})
}

3. axios 响应结构

{// `data` 由服务器提供的响应data: {},// `status` 来自服务器响应的 HTTP 状态码status: 200,// `statusText` 来自服务器响应的 HTTP 状态信息statusText: 'OK',// `headers` 服务器响应的头headers: {},// `config` 是为请求提供的配置信息config: {},// 'request'// `request` is the request that generated this response// It is the last ClientRequest instance in node.js (in redirects)// and an XMLHttpRequest instance the browserrequest: {}
}

4. axios 配置默认值

// 全局的 axios 默认值
axios.defaults.baseURL = 'https://api.example.com';
axios.defaults.headers.common['Authorization'] = AUTH_TOKEN;
axios.defaults.headers.post['Content-Type'] = 'application/x-www-form-urlencoded';// 在创建 axios 实例的同时,自定义实例默认值
const instance = axios.create({baseURL: 'https://some-domain.com/api/',timeout: 1000,headers: {'X-Custom-Header': 'foobar'}
});

5. axios 拦截器

在请求或响应被 thencatch 处理前拦截它们

5.1 添加拦截器

// 添加请求拦截器
axios.interceptors.request.use(function (config) {// 在发送请求之前做些什么return config;},function (error) {// 对请求错误做些什么return Promise.reject(error);});// 添加响应拦截器
axios.interceptors.response.use(function (response) {// 对响应数据做点什么return response;},function (error) {// 对响应错误做点什么return Promise.reject(error);});

5.2 移除拦截器

const myInterceptor = axios.interceptors.request.use(function () {/*...*/});
axios.interceptors.request.eject(myInterceptor);

5.3 为自定义 axios 实例添加拦截器

const instance = axios.create();
instance.interceptors.request.use(function () {/*...*/});

手写封装 axios 函数


/*** ! Ajax 方法封装实现* * axios.get(url,options) 调用 axios 实现* * axios.post(url,options) 调用 axios 实现* * axios.put(url,options) 调用 axios 实现* * axios.delete(url,options) 调用 axios 实现*//*** ! Ajax 封装** @param {*} { method<请求方式>,url<请求地址>,params<请求参数>,data<请求体> }* @return {*} promise 对象*/
function axios({ method,url,params,data }) {// method 转换大写method = method.toUpperCase()// 返回 promise 对象return new Promise((resolve,reject) => {// 请求四步走// 1.创建对象const xhr = new XMLHttpRequest()// 2.初始化// 2.1 处理 params 对象 X=XXXX&X=XXXlet str = ''for (const key in params) {str += `${key}=${params[key]}&`}str = str.slice(0,-1)xhr.open(method,url + '?' + str)// 3.发送if (method === 'POST' || method === 'PUT' || method === 'DELETE') {// Content-type mime类型设置xhr.setRequestHeader('Content-type','application/json')// 设置请求体xhr.send(JSON.stringify(data))} else {xhr.send()}// 响应结果格式设置为 JSON 创建的 JS 对象xhr.responseType = 'json'// 4.处理结果// 现代写法(指定多个回调)xhr.addEventListener("load",()=>{})// 原有写法xhr.onreadystatechange = function () {// 判断 XMLHttpRequest 代理当前所处的状态 4 === 下载操作已完成;if (xhr.readyState === 4) {// 判断响应状态码if (xhr.status >= 200 && xhr.status < 300) {// 成功状态resolve({status: xhr.status,message: xhr.statusText,body: xhr.response,})} else {reject(new Error('请求失败,失败的状态码为:' + xhr.status))}}}})
}
axios.get = function (url,options='') {// 发起 Ajax 请求return axios(Object.assign(options,{ method: 'GET',url: url }))
}
axios.post = function (url,options='') {// 发起 Ajax 请求return axios(Object.assign(options,{ method: 'POST',url: url }))
}
axios.put = function (url,options='') {// 发起 Ajax 请求return axios(Object.assign(options,{ method: 'PUT',url: url }))
}
axios.delete = function (url,options='') {// 发起 Ajax 请求return axios(Object.assign(options,{ method: 'DELETE',url: url }))
}

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com