JavaScript:覆盖alert()


207

有没有人有过重写alert()JavaScript函数的经验?

  • 哪些浏览器支持此功能?
  • 哪些浏览器版本支持此功能?
  • 覆盖该功能有哪些危险?

那不是无限循环吗?
游泳池

1
@尼克-不,不是。“正常”的window.alert函数将分配给window._alert。> After <之后,将重新定义window.alert函数。
克里斯·谢特

@roosteronacid:您的代码虽然人性化,但在语义和语法上都很好,如@ paper1337所指出的那样……在那儿没有递归的机会……本质上,您只是在一开始就将函数体作为某种expando temp进行了交换_alert
非续集,09年

嗯 我回滚了一下,以免掩盖这个问题:)
cllpse

Answers:


210

绝对是“受支持的”。这是您的网页,您可以使用它进行任何操作。

我已经这样做了,无需修改库而是通过潜入事件来跟踪分析事件。

使用代理模式:

(function(proxied) {
  window.alert = function() {
    // do something here
    return proxied.apply(this, arguments);
  };
})(window.alert);

如果需要,也可以绕过对原始函数的调用(代理)

更多信息在这里:jQuery类型#Proxy模式


在代理模式上+1以真正覆盖功能并确保其不被篡改!
乔什·斯托多拉

15
啊! 在Internet Explorer 8中apply()不可用window.alert
。– cllpse

很遗憾听到.. apply是该Function对象的方法。因此,他们必须明确地将其限制为alert?!
迈克·格里森

4
他们必须使用代理模式覆盖它:D
Josh Stodola,

较旧的浏览器不支持此功能,并且会在“ window.alert =“
Chris Pietschmann

23

尽管大多数浏览器都支持覆盖它,但是请谨慎使用它。

由于默认警报框阻止了执行线程,因此某些依赖于此行为的库可能不再工作(至多)。

您应该是一个好公民,并避免接触本机API。如果这样做,在使用第三方代码时,您可能会分手。

但是,如果要在特定上下文中重新定义警报行为,则可以使用匿名函数将其括起来,如下所示:

/* new funky alert */
function myFunkyAlert(msg) { 
    /* here goes your funky alert implementation */
    alert("Look ma!\n" + msg);
}

(function(alert) { // anonymous function redefining the "alert"

    /* sample code */
    alert("Hello World!");

})(myFunkyAlert);

15

Overring警报功能没有危险。每个浏览器都支持它。

例如:

// function over riding. Redirecting to Console with Firebug installed.
function alert(message) { 
    console.info(message);
} 

alert('This is an override.');

11
可能是一个危险,如果你更换无阻塞。例如,调用alert("Reloading")然后重新加载网页的代码。用户可能永远不会看到警报文本。
达里安

13

我认为每个Javascript实现都会支持这一点,并且没有任何危险。通常可以用HTML / CSS将普通的OS样式的警报框替换为更优雅的东西。以这种方式进行操作意味着您不必更改现有代码!可能的事实使Javascript很棒。


12

正如在其他许多答案中所说的那样,您可以使用

window.alert = null

要么

window.alert = function(){}

但是,这不一定会覆盖Window构造函数原型上的函数(请注意大写字母W),因此黑客仍然可以键入:

Window.prototype.alert.apply(window, ["You were hacked!"]);

因此,您还需要使用以下方法覆盖该功能:

Window.prototype.alert = null

要么

Window.prototype.alert = function(){}

这不一定会覆盖其他框架中的功能。参见jsfiddle.net/18znqbjd/1
罗伯特

罗伯特:是的,并且有充分的理由。不同的框架基本上是不同的HTML文档,每个文档都有自己的Java实例。
罗尔夫(Rolf)

您确定Window.prototype.alert在2017年仍然是一个函数吗?:P
iplus26 '17

6

拉迪斯拉夫。
对于IE8,您可以像这样重新定义alert()

/** 
 * Definition of global attached to window properties <br/>
 */ 
    (function() {
      nalert = window.alert;
      Type = {
          native: 'native',
          custom: 'custom'
      };
    })();

/**
 * Factory method for calling alert(). 
 * It will be call a native alert() or a custom redefined alert() by a Type param.
 * This defeinition need for IE
 */ 
    (function(proxy) {

          proxy.alert = function () {
          var message = (!arguments[0]) ? 'null': arguments[0];
          var type = (!arguments[1]) ? '': arguments[1];

          if(type && type == 'native') {
           nalert(message);
          }
          else {
               document.write('<h1>I am redefiend alert()<br/>Alert say: '+message+'</h1>');
          }     
      };
   })(this);

并称为

alert('Hello, hacker!');
nalert('I am native alert');
alert('Hello, user!', Type.custom);

4

我对覆盖alert()函数的经验是,我们曾经使用它来“破解”显示“请注册!”的JavaScript库的试用版。时不时提醒屏幕。

我们只是定义了自己的alert()函数和瞧。

这只是出于测试目的,我们稍后购买了完整版,因此这里没有不道德的事情;-)


3

现代浏览器中的所有JavaScript实现都支持重写。

危险非常简单,那就是您将通过覆盖众所周知的函数(例如alert())而使其他团队成员绝对发疯。

因此,除非您将功能作为一种工具来调试或破解现有代码,否则我看不出有任何理由这样做。只需创建一个新功能。


2

它肯定可以在Firefox和ie8中工作。我看不到有任何浏览器无法使用。这是javascript工作原理的基本原理,即使人们并不经常看到它与诸如那==的本机函数一起使用


1
专门针对的浏览器是IE6,其他浏览器也可以。
AnthonyWJones

1

我要查找警报的来源的一个快速技巧是进入控制台,然后输入

function alert(message) { 
  console.info(message);
  debugger;
} 

0

当涉及到js时,浏览器功能window.alert是最著名的,最知名的是不了解js的人知道alert()-放心,今天使用的所有浏览器都支持js ,您的代码段也是如此。但是,alert()对于您的特定用例,我不会覆盖(嗯,这更像是重构,而不是在OOP中覆盖),因为当您实际上需要不使用alert()模板时,并且可能会,那么您将需要另一个非警报功能。


0

我已经遇到了必须显示默认消息以及实际警报消息的要求。这就是我设法做到的方式。


    const actualAlertFunc = window.alert;
    window.alert = function(msg) {
         actualAlertFunc('some default message '+ msg);
    }

我已经在chrome上测试过了。我不确定它是否是一个很好的实践,但是它可以达到目的。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.