你是否有過下面的需求:需要給所有ajax請求添加統一簽名、需要統計某個接口被請求的次數、需要限制http請求的方法必須為get或post、需要分析別人網絡協議等等,那么如何做?想想,如果能夠攔截所有ajax請求,那么問題就會變的很簡單!😄,少年,想法有點大膽,不過,我欣賞!直接上輪子,Ajax-hook不僅可以滿足你想要的,同時可以給你更多。
本博客原始地址:http://www.jianshu.com/p/9b634f1c9615
Ajax-hook源碼地址 : https://github.com/wendux/Ajax-hook 歡迎star
注:本文為作者之前在簡書博客發布的文章,掘金原創權限剛開,復制過來,如果您之前看過,跳過吧!
如何使用
###一. 直接引入腳本
-
引入ajaxhook.js
<script src="wendu.ajaxhook.js"></script>
-
攔截需要的ajax 回調或函數。
hookAjax({ //攔截回調 onreadystatechange:function(xhr){ console.log("onreadystatechange called: %O",xhr) }, onload:function(xhr){ console.log("onload called: %O",xhr) }, //攔截函數 open:function(arg){ console.log("open called: method:%s,url:%s,async:%s",arg[0],arg[1],arg[2]) } })
ok, 我們使用jQuery(v3.1) 的get方法來測一下:
// get current page source code $.get().done(function(d){ console.log(d.substr(0,30)+"...") })
結果 :
> open called: method:GET,url:http://localhost:63342/Ajax-hook/demo.html,async:true > onload called: XMLHttpRequest > <!DOCTYPE html> <html> <head l...
攔截成功了! 我們也可以看到jQuery3.1內部已經放棄onreadystatechange而改用onload了。
###二. CommonJs下的模塊構建工具環境中
假設在webpack下,第一步, 安裝ajax-hook npm插件
npm install ajax-hook --save-dev
第二步,引入模塊並調用api:
const ah=require("ajax-hook") ah.hookAjax({ onreadystatechange:function(xhr){ ... }, onload:function(xhr){ ... }, ... }) ... ah.unHookAjax()
API
hookAjax(ob)
- ob,類型是對象,key為想要攔截的回調或函數,value為我們的攔截函數。
- 返回值: 原始的 XMLHttpRequest。如果有寫請求不想被攔截,可以new 這個。
unHookAjax()
- 卸載攔截;卸載后,攔截將失效。
改變ajax行為
攔截所有ajax請求,檢測請求method,如果是“GET”,則中斷請求並給出提示
hookAjax({
open:function(arg){ if(arg[0]=="GET"){ console.log("Request was aborted! method must be post! ") return true; } } })
攔截所有ajax請求,請求統一添加時間戳
hookAjax({
open:function(arg){ arg[1]+="?timestamp="+Date.now(); } })
修改請求返回的數據“responseText”
hookAjax({
onload:function(xhr){ //請求到的數據首部添加"hook!" xhr.responseText="hook!"+xhr.responseText; } })
結果:
hook!<!DOCTYPE html>
<html>
<h...
有了這些示例,相信開篇提到的需求都很容易實現。最后測一下unHook
hookAjax({
onreadystatechange:function(xhr){ console.log("onreadystatechange called: %O",xhr) //return true }, onload:function(xhr){ console.log("onload called") xhr.responseText="hook"+xhr.responseText; //return true; }, open:function(arg){ console.log("open called: method:%s,url:%s,async:%s",arg[0],arg[1],arg[2]) arg[1]+="?hook_tag=1"; }, send:function(arg){ console.log("send called: %O",arg[0]) } }) $.get().done(function(d){ console.log(d.substr(0,30)+"...") //use original XMLHttpRequest console.log("unhook") unHookAjax() $.get().done(function(d){ console.log(d.substr(0,10)) }) })
輸出:
open called: method:GET,url:http://localhost:63342/Ajax-hook/demo.html,async:true send called: null onload called hook<!DOCTYPE html> <html> <he... unhook <!DOCTYPE
注意
- 攔截函數返回值是一個boolean,如果為true則會阻斷ajax請求,默認為false,不會阻斷請求。
- 所有的回調攔截函數的參數為當前的XMLHttpRequest 實例,如onreadystatechange、onload;所有ajax原始方法的攔截函數會將原始參數以數組的形式傳遞給攔截函數,你可以在攔截函數中修改它。
相關鏈接:
Ajax-hook原理解析:http://www.jianshu.com/p/7337ac624b8e
本文章允許免費轉載,但請注明原作者及原文鏈接。
ps: 我開博不久,幸得大家鼓勵和認可,由於之前沒有留聯系方式,有人在我之前的博客中找到我的github主頁,然后再找到郵箱,幾經周折才加到我 qq。在此,衷心感謝大家支持!所以,今天我專門建了一個微信群,給大家提供一個技術技術交流、扯淡、八卦的空間,在此廣發英雄帖,歡迎各路高手,也歡迎邀請身邊大牛。