let setProxyArr = function (proxyObjArr) {
for (let i = 0; i < proxyObjArr.length; i++) {
const handler = `{
get:function(target,property,receiver){
console.log("方法:","get","对象","${proxyObjArr[i]}","属性:",
property,"属性类型:",typeof property,"属性值:",target[property],"属性值类型:",typeof target[property]);
return Reflect.get(...arguments)
},
set:function(target,property,value,receiver){
console.log("方法:","set","对象:","${proxyObjArr[i]}","属性:",
property,"属性类型:",typeof property,"属性值:",value,"属性值类型:",typeof target[property]);
return Reflect.set(...arguments);
}
}`;
eval(`try{
${proxyObjArr[i]};
${proxyObjArr[i]} = new Proxy(${proxyObjArr[i]},${handler});
} catch (e){
${proxyObjArr[i]} = {};
${proxyObjArr[i]} = new Proxy(${proxyObjArr[i]},${handler});
}`);
}
}
function watch(object) {
const handler = {
get: function (target, property, receiver) {
if (property !== 'isNaN' && property !== 'encodeURI' && property !== "Uint8Array" && property !== 'undefined' && property !== 'JSON') {
console.log("方法:", "get", "对象", target, "属性:",
property, "属性类型:", typeof property, "属性值:", target[property], "属性值类型:", typeof target[property]);
}
return Reflect.get(...arguments)
},
set: function (target, property, value, receiver) {
console.log("方法:", "set", "对象:", target, "属性:",
property, "属性类型:", typeof property, "属性值:", value, "属性值类型:", typeof target[property]);
return Reflect.set(...arguments);
}
}
// return object
return new Proxy(object, handler)
}
const safeFunction = function safeFunction(func) {
//处理安全函数
Function.prototype.$call = Function.prototype.call;
const $toString = Function.toString;
const myFunction_toString_symbol = Symbol('('.concat('', ')'));
const myToString = function myToString() {
return typeof this === 'function' && this[myFunction_toString_symbol] || $toString.$call(this);
}
const set_native = function set_native(func, key, value) {
Object.defineProperty(func, key, {
"enumerable": false,
"configurable": true,
"writable": true,
"value": value
});
}
delete Function.prototype['toString'];
set_native(Function.prototype, "toString", myToString);
set_native(Function.prototype.toString, myFunction_toString_symbol, "function toString() { [native code] }");
const safe_Function = function safe_Function(func) {
set_native(func, myFunction_toString_symbol, "function" + (func.name ? " " + func.name : "") + "() { [native code] }");
}
return safe_Function(func)
}
//创建函数
const makeFunction = function makeFunction(name) {
// 使用 Function 保留函数名
let func = new Function("v_log", `
return function ${name}() {
v_log('函数${name}传参-->', arguments);
};
`)(v_log); // 传递 v_log 到动态函数
safeFunction(func);
func.prototype = myProxy(func.prototype, `方法${name}.prototype`);
return func;
}
//Window
Window = function Window() {}
Window.prototype = {}
safeFunction(Window)
window = global;
Object.setPrototypeOf(window, Window.prototype)
window.top =window.Window = window.self = window
window.chrome = {}
window.loadts = '1758137904794'
MouseEvent = function MouseEvent(){}
safeFunction(window.MouseEvent)
window.addEventListener = function addEventListener(){}
safeFunction(window.addEventListener)
window.DeviceMotionEvent = function (){}
safeFunction(window.DeviceMotionEvent)
delete Buffer
delete __dirname
delete __filename
delete process
delete global
Document = function Document(){}
safeFunction(Document)
//Node
Node = function Node(){}
Node.prototype.removeChild = function (){}
safeFunction(Node)
safeFunction(Node.prototype.removeChild)
//Element
Element = function Element(){
Node.call(this)
}
safeFunction(Element)
Element.prototype = Object.create(Node.prototype)
Element.prototype.constructor = Element
Element.prototype.getAttribute = function getAttribute(){}
Element.prototype.removeChild = function removeChild(){}
safeFunction(Element.prototype.getAttribute)
safeFunction(Element.prototype.removeChild)
//HTMLElement
HTMLElement = function HTMLElement(){
Element.call(this) //在 HTMLElement 构造函数内部通过 Element.call(this) 调用了父类 Element 的构造函数,并将 this 绑定为 HTMLElement 的实例。
}
safeFunction(HTMLElement)
HTMLElement.prototype = Object.create(Element.prototype)
HTMLElement.prototype.constructor = HTMLElement
//HTMLHtmlElement
HTMLHtmlElement = function HTMLHtmlElement(){
HTMLElement.call(this)
this.tagName = 'HTML'
}
safeFunction(HTMLHtmlElement)
HTMLHtmlElement.prototype = Object.create(HTMLElement.prototype)
HTMLHtmlElement.prototype.constructor = HTMLHtmlElement
//XMLHttpRequest
XMLHttpRequest = function XMLHttpRequest(){}
XMLHttpRequest.prototype.open = function (){}
XMLHttpRequest.prototype.send = function (){}
XMLHttpRequest.prototype.setRequestHeader = function (){}
XMLHttpRequest.prototype.addEventListener = function (){}
safeFunction(window.XMLHttpRequest)
//requestIdleCallback
requestIdleCallback = function (){}
safeFunction(window.requestIdleCallback)
//HtmlCollection
function HTMLCollection(){
this._element = [watch(new HTMLHtmlElement())]
}
HTMLCollection.prototype[Symbol.iterator] = function() {
// 获取文档根元素的子元素集合(迭代的目标)
const elements = this._element;
let index = 0; // 迭代索引
// 返回迭代器对象(必须包含next()方法)
return {
next: () => {
// 当索引小于元素数量时,返回当前元素并递增索引
if (index < elements.length) {
return {
value: elements[index++],
done: false
};
} else {
// 迭代结束
return {
value: undefined,
done: true
};
}
}
};
};
safeFunction(HTMLCollection)
//HTMLAllCollection
function HTMLAllCollection() {
this.length = 1048;
}
safeFunction(HTMLAllCollection)
//HTMLBodyElement
function HTMLBodyElement(){
HTMLElement.call(this);
this.tagName = "BODY"
}
HTMLBodyElement.prototype = Object.create(HTMLElement.prototype)
safeFunction(HTMLBodyElement)
//HTMLDocument 用于实现document上的属性
function HTMLDocument() {
}
safeFunction(HTMLDocument)
HTMLDocument.prototype.addEventListener = function addEventListener(){}
safeFunction(HTMLDocument.prototype.addEventListener)
HTMLDocument.prototype.getElementsByTagName = function getElementsByTagName(tagName){
console.log("HTMLDocument.prototype.getElementsByTagName的参数==>",tagName)
if(tagName === "*"){
return watch(new HTMLCollection())
}
}
safeFunction(HTMLDocument.prototype.getElementsByTagName)
HTMLDocument.prototype.all = watch(new HTMLAllCollection())
HTMLDocument.prototype.body = watch(new HTMLBodyElement())
HTMLDocument.prototype.documentElement = watch(new HTMLHtmlElement())
document = new HTMLDocument()
document.cookie = ""
//Permissions
function Permissions (){
function createPermissionStatus(name) {
return {
name: name, // 权限名称(如 'geolocation')
state: 'prompt', // 状态值:'granted' | 'denied' | 'prompt'
onchange: null, // 事件回调占位
// 模拟事件监听方法(空实现)
addEventListener: function() {},
removeEventListener: function() {}
};
}
this.query = function(permissionDesc) {
const permName = permissionDesc?.name || 'unknown';
// 返回 Promise,resolve 出模拟的状态对象
return Promise.resolve(createPermissionStatus(permName));
};
this.request = function(permissionDesc) {
const permName = permissionDesc?.name || 'unknown';
return Promise.resolve(createPermissionStatus(permName));
}
}
safeFunction(Permissions)
//Navigator
function Navigator() {
}
safeFunction(Navigator)
Navigator.prototype.webdriver = false;
Navigator.prototype.permissions = watch(new Permissions());
Navigator.prototype.userAgentData = watch(new NavigatorUAData());
Navigator.prototype.appName = 'Netscape'
Navigator.prototype.userAgent = 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/140.0.0.0 Safari/537.36'
navigator = new Navigator()
//NavigatorUAData
function NavigatorUAData() {
this["brands"] = [
{
"brand": "Chromium",
"version": "140"
},
{
"brand": "Not=A?Brand",
"version": "24"
},
{
"brand": "Google Chrome",
"version": "140"
}
];
this["mobile"] = false;
this["platform"] = "Windows"
}
safeFunction(NavigatorUAData)
//Screen
function Screen() {}
screen = new Screen()
safeFunction(Screen)
//History
function History() {
}
history = new History()
safeFunction(History)
//Location
function Location() {
}
location = new Location()
location.href = 'https://www.xiaohongshu.com/explore'
safeFunction(Location)
setProxyArr(["window",'document', 'location', 'history', 'screen', 'navigator'])
这个代码会发生无限递归,
我测试过,setProxyArr([“window”,‘document’, ‘location’, ‘history’, ‘screen’, ‘navigator’]) 里面如果没有window,在这个环境下执行业务代码不会发生无限递归,这是为什么,是不是window的某些属性导致的
最新发布