0

当调用是异步的时,我在经典 ASP 下使用来自 JScript 的 MsXml.ServerXmlHttp 对象时遇到错误。错误消息是“找不到窗口类”


环境为:Windows Server 2003 SP2;IIS v6;经典ASP;脚本

当使用 asynch = true 调用 ServerXmlHttp.open 时,发送方法上会发生错误。当使用 asynch = false 调用 ServerXmlHttp.open 时,不会发生错误

该代码适用于具有所有相同版本的主要产品的测试环境(尽管它并未与生产环境保持相同)

在测试环境中,代码同时使用同步和异步打开

使用 MSXML2.ServerXMLHTTP.6.0 MSXML2.ServerXMLHTTP.4.0 MSXML2.ServerXMLHTTP.2.0 时出现错误

无论 URL 是什么,代码都会以相同的方式失败:google.com 和 stackoverflow.com 就像我需要调用的实际页面一样失败

在测试环境google.com、stackoverflow.com和我需要调用的页面都工作。

无论我使用 GET 还是 POST,都会发生错误

无论标题如何,都会发生错误。

无论协议是 HTTP 还是 HTTPS,都会发生错误。

错误发生得非常快 - 几乎肯定是客户端。

连接同步时不会发生错误。

我已经重新安装了 MSXML6.msi

我已经使用“proxycfg.exe -d”将互联网堆栈配置为不使用代理。( http://support.microsoft.com/kb/289481/ )


这是一个指示性代码示例(我已对其进行了简化,因为我认为代码不是问题):

var xmlServerHttp = Server.CreateObject("MSXML2.ServerXMLHTTP.6.0");
xmlServerHttp.open("POST", "http://some-url.com", true); //true causes error

xmlServerHttp.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");

xmlServerHttp.send("some=values&some=othervalues"); //error happens here

var responseXML;
var stateok = false;
var numOfWaits = 10;            
do {
    if (xmlServerHttp.readyState == READYSTATE_COMPLETED) {
     responseXML = String(xmlServerHttp.responseText);
     stateok = true;
    }
    else {
        xmlServerHttp.waitForResponse(1);
    }
 } while (!stateok && --numOfWaits > 0);

此代码在 xmlServerHttp.send 调用中引发错误:“找不到窗口类”。

这就是 MSDN 关于错误的说法 ( http://msdn.microsoft.com/en-us/library/ms820745.aspx )

应用程序尝试使用的窗口类不是向系统注册的特定于应用程序的类或预定义的控件类之一(例如 BUTTON、LISTBOX、SCROLLBAR 等)。

此知识库文章 ( http://support.microsoft.com/kb/303326 ) 包含以下异步特定说明:

ServerXMLHTTP 不使用 Urlmon.dll。但是,当您在异步模式下使用 ServerXMLHTTP 时,您还需要此消息泵,因为解析器通过将消息发送回线程来触发事件。

Urlmon.dll 确实存在于服务器的 system32 文件夹中。但是它在代码以异步模式工作的测试服务器上不存在:S。(我没有明确安装 urlmon.dll - 当我去寻找它时它就在那里。)

我的猜测是服务器上存在一些配置或安装问题。也许缺少 MSXML 依赖。但我不知道如何进一步调查。有没有人有什么建议?

特别是,谁能告诉我:

  • MsXml.ServerXmlHttp 的依赖是什么?

    或者我怎么能弄清楚它们。

  • 在这种情况下,错误消息“找不到窗口类”是什么意思?

  • 是否有任何特定于异步 HTTP 调用的设置或配置?

感谢您阅读本文。

4

1 回答 1

0

带有 COM 对象的 ASP 的单线程特性不允许您像您想象的那样处理异步事件。

有人可能认为这可以通过引用 中声明的事件处理程序来实现global.asa,但我怀疑这是否可行。

您的代码完全没有意义,因为您正在尝试完全复制所做的事情async=false。您可以使用该方法控制超时setTimeout()

于 2009-06-16T20:28:22.083 回答