# 前端请求

#### XMLHttpRequest

```javascript
//XMLHttpRequest.UNSENT
//XMLHttpRequest.OPENED
//XMLHttpRequest.HEADERS_RECEIVED
//XMLHttpRequest.LOADING
//XMLHttpRequest.DONE
let xhr
if (window.XMLHttpRequest) {
	// Mozilla, Safari...
	xhr = new XMLHttpRequest()
} else if (window.ActiveXObject) {
	// IE
	try {
		xhr = new ActiveXObject('Msxml2.XMLHTTP')
	} catch (e) {
		try {
			xhr = new ActiveXObject('Microsoft.XMLHTTP')
		} catch (e) {}
	}
}
if (xhr) {
	xhr.onreadystatechange = function onReadyStateChange() {
		if (xhr.readyState === 4 && xhr.status === 200) {
			console.log('执行成功')
		} else {
			console.log('执行出错')
		}
	}
	xhr.open('POST', '/api', true)
	// 以表单的形式传递数据
	xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded')
	xhr.send('username=admin&password=root')
}
```

#### JQuery Ajax

```javascript
$.ajax({
   type: 'POST',
   url: url,
   data: data,
   dataType: dataType,
   success: function () {},
   error: function () {}
});
$.get(url,function(){}); //get请求
$.post(url,body,function(){}); //post请求
$.getJSON(url,function(){}); //get请求从服务器加载Json编码
```

优点：

* 对原生XHR的封装
* 针对MVC的编程
* 完美的兼容性
* 支持jsonp

缺点：

* 不符合MVVM
* 异步模型不够现代，不支持链式，代码可读性差
* 整个Jquery太大，引入成本过高

#### Fetch

```javascript
fetch(url).then(function(res) {
 return res.json()
}).then(function(data) {
  console.log(data)
}).catch(function(e) {
  console.log("Oops, error")
})
```

优点：

* 更加底层，提供的API丰富（request, response）
* 语法简单，脱离了XHR，基于ES新的Promise设计

缺点：

* 兼容性比较凄惨，低级别浏览器均不支持，需要实现fetch的polyfill了。思路其实很简单，就是判断浏览器是否支持原生的fetch，不支持的话，就仍然使用XMLHttpRequest的方式实现，同时结合Promise来进行封装。常见的polyfill就有：es6-promise,babel-polyfill,fetch-ie8等
* 不支持jsonp，可以引入fetch-jsonp

```javascript
npm install fetch-jsonp --save-dev

fetchJsonp(url, {
  timeout: 3000,
  jsonpCallback: 'callback'
}).then(function(res) {
  console.log(res.json());
}).catch(function(e) {
  console.log(e)
});
```

* 没有拦截器，需要额外再封装一层或者fetch-interceptor
* 默认不带cookie，需要添加配置
* 没有abort，不支持timeout超时处理
* 无法获取progress状态

#### Axios

* 支持node，创建http请求
* 支持Promise API
* 客户端防止CSRF：每个请求带一个cookie拿到的key
* 拦截请求和响应
* 可取消请求

安装

```javascript
npm install axios

//cdn
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
```

基本使用

```javascript
axios({
    method: 'GET',
    url: url,
})
.then(res => {console.log(res)})
.catch(err => {console.log(err)})

// get请求
axios.get(url)
 .then(function (response) {
    console.log(response);
 })
 .catch(function (error) {
    console.log(error);
 });

// post请求
axios.post（‘/user’, {
    name: 'Jerry',
    lastName: 'Meng'
 })
 .then(function (response) {
    console.log(response);
 })
 .catch(function (error) {
    console.log(error);
 });
```

#### 多请求串行

```javascript
// ajax
$.ajax({
   url: '',
   data: '',
   success: function (data) {
   	$.ajax({
   		url: '',
   		data: '',
   		success: function (data) {
   			$.ajax({
   				...
   			})
   		}
   	})
   }
})

//axios
axios
   .get(url)
   .then((res) => {
   	return axios.get(url)
   })
   .then((res) => {
   	//如此一层层嵌套
   })
```

#### 多请求并行

```javascript
//axios
function getInfo() {
 return axios.get(url)
}
function getUser() {
 return axios.get(url)
}
axios.all([getInfo(), getUser()])
 .then(axios.spread(function (info, user) {
 // 两个请求现在都执行完成
 }))
```


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://jackmeng.gitbook.io/note/frontend/js/qian-duan-qing-qiu.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
