代码之家  ›  专栏  ›  技术社区  ›  Mike Hofer

JS:“被叫方(服务器[非服务器应用程序])不可用并消失。”访问window.opener

  •  14
  • Mike Hofer  · 技术社区  · 15 年前

    在我们的(相当大和旧的)ASP.NET应用程序中,我们使用许多加载到框架、iframes和模式对话框中的页面(使用window.showModalDialog)。我们已经开始看到上面的错误了,我似乎在任何地方都找不到一个合理的解释。

    1. 弹出窗口阻止程序。不。我们不是在管理他们。即使是内置的拦截器也不行。

    2. 受信任区域。不。应用程序现在在本地主机上运行,它在受信任的站点列表中。

    3. 杂散宇宙射线。可能,但不可能。太一致了。

    最终发现隐藏在微软网站上的错误信息 some dusty tome 关于检索自动化错误消息信息。在本文中,他们谈论的是Excel,他们说:“在这个例子中,Microsoft Excel是服务器应用程序。 在工作簿对象被销毁(或关闭)后引用该对象会生成错误。

    这很可能是我对错误原因的解释,但没有一个真正具体的解释。 有人在参考资料被处理后试图使用它。 奇怪的是,你仍然可以看到屏幕上的窗口。然而,奇怪的是,这对我来说是一个可疑的答案 this .

    这就是发生的事情。

    • A页是主页面。
    • pagea在一帧中显示pageb。pageb是一个工具栏。
    • pagea在另一帧中显示pagec。这就是内容。
    • pagec在非模态对话框中显示paged。
    • paged,由于我不知道的原因,想要修改pageb中的控件。它试图用window.opener来实现这一点,但失败了。

    如果有人能告诉我为什么会这样(代码在FF中工作),我会很感激。

    4 回复  |  直到 11 年前
        1
  •  11
  •   Johnny Oshika    12 年前

    虽然我的答案不直接适用于这个特定的问题,如果你得到这个错误( 被呼叫方(服务器[非服务器应用程序])不可用并消失; )在弹出窗口和打开器窗口之间进行通信时,这是因为弹出窗口创建了一个对象,然后将其传递给了打开器窗口。当弹出窗口关闭时,Internet Explorer将杀死弹出窗口创建的所有对象。而且由于对象是通过引用传递的,所以Opener窗口引用的对象现在已经不存在了。一个简单的解决方法是通过使用json.stringify将对象转换为JSON字符串来传递值。然后可以使用json.parse()将字符串转换回window.opener中的对象。

    例子:

    弹出窗口:

    window.opener.callback(JSON.stringify({
        id: 1,
        name: "foo"
    }));
    

    打开窗口:

    window.callback = function (response) {
        var foo = JSON.parse(response);
    };
    

    使用这种方法,打开器窗口不再引用在弹出窗口中创建的对象,因此关闭弹出窗口后,打开器窗口中的对象将继续存在。

        2
  •  6
  •   Mike Hofer    15 年前

    我应该早点更新这个问题,对此延误我深表歉意。自从我贴了以后,我学到了一些东西,这就是我学到的。

    对于使用window.showModalDialog打开的窗口,window.opener方法返回空值,而不是对打开窗口的引用。要获取对打开窗口的引用,必须将其作为对话参数传递。

    目前我还不清楚这是否是有意的行为;这显然是无证行为。此外,根据msdn,window.opener只对加载到frames和iframes中的页面有效。

        3
  •  2
  •   krul    15 年前

    在以下场景中,我收到了完全相同的错误消息: 窗口A弹出wind b,用户搜索某物,wind b调用wind a传递某个参数。 方法对wind a进行调用,假定在popup wind b完成其正在执行的操作后关闭它。 我将参数作为对象传递: P=A:1,B:“C” 在我重写代码分别传递每个参数后,错误就消失了。 校准方法(1,“c”);

    希望能帮助别人…

        4
  •  0
  •   BenMorel Manish Pradhan    11 年前

    您可以在Excel中获取此错误

    Sub LoadParameterForm()
    
    If frmParm Is Nothing Then
        Set frmParm = New frm_setParameters
    End If
    
    frmParm.Show
    end sub 
    

    这里frmparm是一个模块级变量。 单击“确定”按钮,我打算.hide()表单,这样用户的选择就很粘了。 如果用户单击控制框X并关闭窗体,那么实际上frmparm指向的是不再存在的内容。

    我找不到测试条件的方法,我会捕获错误,将表单设置为Nothing,然后重试。

    我意识到这并不是所要问的问题,但这是一个在帖子中多次提到的有关excel问题的具体例子。