ajaxHooker拦截跨域问题求助
本帖最后由 sdcsdv 于 2024-3-12 17:41 编辑> 本帖最后由 sdcsdv 于 2024-3-12 16:40 编辑
计划通过拦截axios请求,实现跨域访问,但发现axios跨域先被浏览器抓到了,请教如何实现拦截跨域访问?
!(data/attachment/forum/202403/12/163119w0m200yz0wz8y8mb.png)
前端代码:
```html
const onClick = async () => {
axios.get('https://www.baidu.com/', {})
.then(res => {
console.log(res);
})
.catch((e) => {
console.log('获取数据失败');
});
};
```
油猴代码:
```js
// ==UserScript==
// @name ajaxHooker拦截-2024
// @namespace http://tampermonkey.net/
// @version 0.1
// @descriptiontry to take over the world!
// @author You
// @match http://localhost:5173/*
// @grant unsafeWindow
// @grant GM_xmlhttpRequest
// @connect *
// @require https://scriptcat.org/lib/637/1.3.3/ajaxHooker.js
// @run-at document-start
// ==/UserScript==
(function() {
'use strict';
ajaxHooker.hook(request => {
console.log('request:', request);
request.response = res => {
const responseText = res.responseText; // 注意保存原数据
res.responseText = new Promise(resolve => {
setTimeout(() => {
//跨域访问
GM_xmlhttpRequest({
url: request.url,
method: request.method,
headers: request.headers,
data: request.body,
onload: function(res) {
console.log('res:', res);
//返回修改后数据
resolve(res);
},
onerror: function(error) {
console.log('error:', error);
reject(error);
}
});
//resolve('test');
}, 2000);
});
};
});
})();
``` 你的意思是前端直接写跨域吗?那可以保存request.url的值,然后改一个同源url让其正常响应,再替换响应值:
ajaxHooker.hook(request => {
const trueUrl = request.url;
request.url = location.href;
request.response = res => {
res.responseText = new Promise(resolve => {
GM_xmlhttpRequest({
url: trueUrl,
....
});
});
};
});
严格来说这不是最理想的方案,会多发生一次不必要的同源请求,因为ajaxHooker的主要目的是在原值上修改,而非整个替换原值,所以没有实现这部分特性。解决方案在那个库下面的回复中也有讨论(151楼),加入异步的话需要处理好事件的触发时机,通用的方案还得劫持更多事件,挺复杂的。 cxxjackie 发表于 2024-3-12 22:32
你的意思是前端直接写跨域吗?那可以保存request.url的值,然后改一个同源url让其正常响应,再替换响应值: ...
给大佬补一下:
https://bbs.tampermonkey.net.cn/forum.php?mod=viewthread&tid=3284&page=16#pid76429
感觉如果可以拦截请求,然后返回自定义的内容还是挺爽的 王一之 发表于 2024-3-13 09:45
给大佬补一下:
https://bbs.tampermonkey.net.cn/forum.php?mod=viewthread&tid=3284&page=16#pid76429 ...
是可以做到的,再加一个参数就行了,只是我看着那堆缝缝补补的代码就头大,之前为了兼容各种奇怪的网站加了太多东西,比如我被迫采用defineProperty + Proxy结合的方案,到现在还有一点遗留问题没处理干净。
吐槽下XMLHttpRequest,这个接口太老旧了,调用繁琐,注入点也非常多,而且由于太繁琐了很多网站还喜欢把他包装一下,导致我的库要与他们共存就成了大问题,很多看起来一步到位的操作需要兜兜转转绕几步来完成。还有xhr实例可以被复用是最草的,相当于一个实例中发生了多次请求,这对异步劫持是个很大挑战,假设前端一边复用xhr一边自己劫持xhr,然后我的库可能还有多个实例在同时运行(多个脚本引用),这中间的兼容问题想想就头秃。反观fetch就好太多了,没有什么open、send这种莫名其妙的接口,一个Promise干净利落,劫持起来是真省心。
页:
[1]