我们知道,Javascript中函数有静态函数、成员函数和实例化对象的成员函数之分,这些函数的实现存在正常函数和匿名函数的区分。所以在我们Hook成员时,我们要对这些情况兼而顾之。
例如对与下列函数Hook调用,预想产生如下的输出:
//全局函数无参数
function Method1(){
alert('Method1');
}
Method1.hook(function()
{
alert('befor Method1');
return true;
},
function()
{
alert('after Method1');
}
);
Method1();
/* 输出
befor Method1
Method1
after Method1
*/
alert('-----------------');
//全局函数有参数
function Method2(name){
alert('Method2 with ' + name);
}
Method2.hook(function(name)
{
alert('befor Method2 with ' + name);
return true;
},
function()
{
alert('after Method2 ');
}
);
Method2('evlon');
/* 输出
befor Method2 with evlon
Method2 with evlon
after Method2
*/
alert('-----------------');
//Hook字符串的toString 函数
String.prototype.toString.hook(String.prototype, function()
{
alert('befor string.toString');
return true;
});
var s = "return s";
alert(s.toString());
/* 输出
befor string.toString
return s
*/
alert('-----------------');
//Hook 系统已有全局函数parseInt
parseInt.hook(function()
{
alert('befor parseInt');
return true;
});
alert(parseInt('5'));
/* 输出
befor parseInt
5
*/
alert('-----------------');
//Hook 所有数组对象的join 方法
Array.prototype.join.hook(Array.prototype, function(span)
{
alert('befor Array.prototype.join separator ' + span);
return true;
});
alert([3,5,6].join(','));
/* 输出
befor Array.prototype.join separator ,
3,5,6
*/
alert('-----------------');
var list = [3, 5, 6];
//Hook list 这个实例数组对象的join 方法
list.join.hook(list, function(span)
{
alert('befor list.join separator ' + span);
return true;
});
alert(list.join(','));
/* 输出
befor list.join separator ,
befor Array.prototype.join separator ,
3,5,6
*/
alert('-----------------');
var list2 = [3, 5, 6, 7];
// 此处调用不会产生befor list.join separator ,
alert(list2.join(','));
/* 输出
befor Array.prototype.join separator ,
3,5,6,7
*/
alert('-----------------');
//自定义类
function People() {
//成员函数带参数
this.getName = function(name) {
alert('in getName with ' + name);
return 'return evlon';
}
}
var p = new People();
var p2 = new People();
//这里我们只Hook实例p2 的函数调用
p2.getName.hook(p2, 'getName2',
function(name) {
alert('befor getName2 with ' + name);
return true;
},
function() {
alert('after getName2');
}
);
p2.getName.hook(p2,
function(name) {
alert('befor getName with ' + name);
return true;
},
function() {
alert('after getName');
}
);
//因为只Hook了P2, 对这个调用无影响
alert(p.getName('argName'));
/* 输出
in getName with argName
return evlon
*/
alert('-----------------');
alert(p2.getName('argName'));
/* 输出
befor getName with argName
in getName with argName
after getName
return evlon
*/
alert('-----------------');
alert(p2.getName2('argName2'));
/* 输出
befor getName2 with argName2
in getName with argName2
after getName2
return evlon
*/