一篇文章讓你學會如何選擇 JS HTTP 請求庫
以前前端提到網路請求通常是指瀏覽器,但現在隨著 Node.js、小程式的出現,網路請求不再侷限於瀏覽器。本文將帶你瞭解不同請求的原理,以及如何為專案選擇合適的請求庫。
1. 請求原理
1.1 瀏覽器
瀏覽器通過 XMLHttpRequest 物件實現 http 請求。
遠古時代 ie6 是藉助 ActiveXObject 物件實現 http 請求,目前已無人使用,不考慮相容。
W3C 標準新提出的 Fecth API,基於 Promise 實現,相對 XMLHttpRequest 物件呼叫更方便,但舊瀏覽器不支援 Promise,需要對 Promise 進行 pollyfill。
- XMLHttpRequest
let xhr = new XMLHttpRequest(); xhr.open('get', url, true); xhr.send(); xhr.onreadystatechange = function() { if(xhr.readyState === 4 && xhr.status === 200 ) { let response = JSON.parse(xhr.responseText); } }
- Fetch
fetch(url) .then(response => response.json()) .then(data => console.log(data)) .catch(e => console.log("error", e))
1.2 Node.js
Node.js 釋出於 2009 年,是一個基於 Chrome V8 引擎的 JavaScript 執行環境,Node.js 的頂層物件是 global,不存在 window 物件,不能通過 XMLHttpRequest 物件實現 http 請求。
Node.js 中通過引入 http/https/http2 模組實現 http 請求,下面為 http 模組實現的例子:
const http = require('http'); const server = http.createServer((req, res) => { res.end('hello world'); }); server.on('clientError', (err, socket) => { socket.end('HTTP/1.1 400 Bad Request\r\n\r\n'); }); server.listen(8000);
1.3 React Native
React Native 是 Facebook 2015 開源跨平臺移動應用開發工具。
React Native 中已經內建了 XMLHttpRequest API,同時提供了和 web 標準一致的Fetch API,所以大部分在 web 端可以使用的網路請求庫在 React Native 中也可以使用。
1.4 Weex
Weex 是 阿里 2016 開源跨平臺移動應用開發工具。
Weex 通過封裝模組來呼叫原生功能,提供了 stream 模組來實現網路請求。
1.5 小程式
2017 年微信小程式上線,隨後各大平臺都推出自己的小程式。
小程式由於要對 http 請求做引數校驗、相容各平臺(iOS、Android)或版本問題,所以提供了一套屬於自己的 API,不提供 window 物件。
下面為微信小程式和支付寶小程式的官網示例:
- 微信小程式
wx.request({ url: 'test.php', // 僅為示例,並非真實的介面地址 data: { x: '', y: '' }, header: { 'content-type': 'application/json' // 預設值 }, success(res) { console.log(res.data) } })
- 支付寶小程式
my.httpRequest({ url: 'http://httpbin.org/post', method: 'POST', data: { from: '支付寶', production: 'AlipayJSAPI', }, dataType: 'json', success: function(res) { my.alert({content: 'success'}); }, fail: function(res) { my.alert({content: 'fail'}); }, complete: function(res) { my.hideLoading(); my.alert({content: 'complete'}); } });
2. 請求庫
從上文可以看出,平臺間的請求方式存在各種差異,請求庫就是為解決這種差異。下面為目前較火的請求庫。
2.1 $.ajax(支援瀏覽器)
$.ajax 為 jQuery 對 XMLHttpRequest 物件進行相容封裝。
需要補充的是 React Native 可以使用部分瀏覽器網路請求庫,但是不能使用 jQuery,因為 jQuery 中還使用了很多瀏覽器中才有而 React Native 中沒有的東西。
此外,現在使用框架的專案中我們通常採用其他請求庫,或者自己根據專案對 XMLHttpRequest 或 Fetch 進行封裝,不會為了網路請求引入 jQuery。
2.2 Request(支援 Node.js)
Request 是對 Node.js 的 http/https 模組封裝的 http 庫。
var request = require('request'); request('http://www.google.com', function (error, response, body) { console.log('error:', error); // Print the error if one occurred console.log('statusCode:', response && response.statusCode); // Print the response status code if a response was received console.log('body:', body); // Print the HTML for the Google homepage. });
2.3 SuperAgent(支援 Node.js)
SuperAgent 和 Request 類似,都是對 Node.js 的 http/https 模組封裝的 http 庫。
var request = require('superagent') request .post('/api/pet') .send({ name: 'Manny', species: 'cat' }) .set('X-API-Key', 'foobar') .set('Accept', 'application/json') .then(res => { alert('yay got ' + JSON.stringify(res.body)); });
2.4 Axios(支援 React Native,Node,瀏覽器)
Axios 是一個基於 promise 的 HTTP 請求庫,可以用在瀏覽器和 Node.js 中。瀏覽器中使用 XMLHttpRequest,Node.js 中使用 http/https 模組。下面為請求示例:
axios.get('/user?ID=12345') .then(function (response) { console.log(response); }) .catch(function (error) { console.log(error); });
Vue 2.0 推薦使用 Axios 作為 Vue 的請求庫。而且在 SSR 的時候我們在服務端、客戶端都需要請求,所以通常會選擇 Axios。
2.5 Fly.js(支援 Node.js 、微信小程式 、Weex 、React Native 、Quick App 和瀏覽器)
Fly.js 是一個基於 promise 的 HTTP 請求庫,可以用在Node.js 、微信小程式 、Weex 、React Native 、Quick App 和瀏覽器中,對上述平臺都做了相容。
fly.get('/user?id=133') .then(function (response) { console.log(response); }) .catch(function (error) { console.log(error); });
除了 Fly.js,有些小程式開發框架本身提供網路請求庫,對平臺做了相容,比如 Taro.request。
總結
不同請求庫之間的 API、使用都會存在區別。專案開始時,根據需要相容的平臺選擇合適的請求庫,會大大減少以後程式碼重構的麻煩。
- 本文首發於公眾號,更多內容歡迎關注我的公眾號: 阿誇漫談