javascript - 拦截 XHR - 在提高负载之前运行功能
问题描述
在带有扩展注入自定义XMLHttpRequest
类的网页上,我需要在文档的其余部分引发事件之前拦截和修改某些响应。load
现在,我的修改代码对加载事件做出反应。load
在触发事件之前,我将如何使用函数来修改响应?
这是我正在使用的代码:
let oldXHROpen = window.XMLHttpRequest.prototype.open;
window.XMLHttpRequest.prototype.open = function (method, url, async, user, password) {
var originalresp = this;
//Do something with the method, url and etc.
originalresp.addEventListener('load', async function () {
//Do something with the response text
//***This function needs to execute before load is raised for the rest of the document***
value = '<note><body>This is a test XML document.</body></note>';
parser = new DOMParser();
apiresponsexml = parser.parseFromString(value, 'application/xml');
//Replace data in the response
Object.defineProperties(originalresp, {
'response': {
value: value
},
'responseXML': {
value: apiresponsexml,
},
'responseText': {
value: value,
}
});
});
return oldXHROpen.apply(originalresp, arguments);
};
这个问题是这个先前线程的延续。
解决方案
内部覆盖onreadystatechange
(在加载/加载之前触发)send()
:
function plantXhrHook() {
let origStateChange;
function modifyResponse(e) {
if (this.readyState === 4) {
const value = 'foo';
let xml;
Object.defineProperties(this, {
response: {value},
responseText: {value},
responseXML: {
get() {
if (typeof xml === 'undefined')
xml = new DOMParser().parseFromString(value, 'application/xml');
return xml;
},
},
});
}
if (origStateChange) {
origStateChange.apply(this, arguments);
}
};
const origSend = XMLHttpRequest.prototype.send;
XMLHttpRequest.prototype.send = function () {
origStateChange = this.onreadystatechange;
this.onreadystatechange = modifyResponse;
origSend.apply(this, arguments);
};
}
const script = document.createElement('script');
script.textContent = `(${plantXhrHook})()`;
document.documentElement.appendChild(script);
script.remove();
由于其他扩展或页面脚本也可能挂钩 XHR,因此使用"run_at": "document_start"在内容脚本中运行您的代码是有意义的。
推荐阅读
- reactjs - 如何在反应阿波罗中全局处理错误
- java - 使用 .compareTo 比较日期时,为什么不考虑月份?
- php - 如果数据不匹配,如何比较 2 个 PHP 对象数组然后填充空字符串?
- .htaccess - 如何将 Nginx 规则转换为 htaccess?
- django - 尝试以更新配置文件表单获取用户数据时,“用户”对象没有属性“获取”
- javascript - 当图像在视图中时开始视差滚动
- android - 为什么无法将 apk 上传到 google play 控制台?
- c++ - 为什么相同的字符不相等
- php - 使用关联和索引数组循环多维数组
- c# - 添加绑定到在代码隐藏中创建的元素