[英]Internet Explorer COM automation: Converting numeric error code to string
我正在编写一些代码,用于通过Win32::OLE
从Perl 5程序驱动Internet Explorer,我正在寻找方法将通过事件(例如NavigateError
)传递回Perl程序的数字状态/错误代码转换为更具人性化的形式。
是否有某种库函数将0x800C0005L或-2146697211转换为"INET_E_RESOURCE_NOT_FOUND"
或更具可读性的东西?
我尝试过Win32::FormatMessage()
,但这似乎只适用于非特定于应用程序的错误条件。
更新:以下是一些示例代码供澄清。 一些测试输出如下所示。
#!/usr/bin/perl
use strict;
use warnings;
use 5.010;
use Time::HiRes qw(sleep time);
use Win32::OLE qw(EVENTS);
use Win32::OLE::Variant;
$|++;
sub ie_browse {
my $url = shift;
my $ie = Win32::OLE->new('InternetExplorer.Application') or die;
Win32::OLE->WithEvents($ie,
sub {
my ($obj, $event, @args) = @_;
given ($event) {
when ('NavigateComplete2') {
push @extra,
'url='.($args[1]->As(VT_BSTR));
say "$event: @extra";
}
when ('NavigateError') {
push @extra,
'url='.($args[1]->As(VT_BSTR)),
'statuscode='.($args[3]->As(VT_I4));
say "$event: @extra";
}
}
}, 'DWebBrowserEvents2');
Win32::OLE->SpinMessageLoop;
$ie->{visible} = 1;
Win32::OLE->SpinMessageLoop;
$ie->Navigate2($url);
Win32::OLE->SpinMessageLoop;
while(1) {
Win32::OLE->SpinMessageLoop;
sleep(0.1);
}
}
ie_browse $ARGV[0];
这是两次获取尝试的输出。 当然,获取Stack Overflow页面是成功的。
C:\Documents and Settings\nobody\Desktop>perl ie.pl http://stackoverflow.com/
NavigateComplete2: url=http://stackoverflow.com/
Terminating on signal SIGINT(2)
但是example.invalid
不存在。
C:\Documents and Settings\nobody\Desktop>perl ie.pl http://example.invalid/
NavigateError: url=http://example.invalid/ statuscode=-2146697211
NavigateComplete2: url=http://example.invalid/
Terminating on signal SIGINT(2)
我有兴趣将那个已经传回有用的数值(-2146697211)转换。 这不是OLE错误,而是Internet Explorer COM对象发出的错误情况。
更新:根据您的评论,我相信您正在寻找有关NavigateError
事件的Microsoft文档:
INET_E_INVALID_URL (0x800C0002L or -2146697214) INET_E_NO_SESSION (0x800C0003L or -2146697213) INET_E_CANNOT_CONNECT (0x800C0004L or -2146697212) ...
您可以通过解析此列表来创建模块:
package Win32::WebBrowserControl::ErrorMnemonics;
use strict;
use warnings;
my %lookup;
sub import {
my $class = shift;
while ( my $x = <DATA> ) {
my ($mnemonic, $code) = ( $x =~ m{
^(INET_E_[A-Z_]+)
[ ]
\(
0x[[:xdigit:]]+L
[ ] or [ ]
(-[[:digit:]]+)
\)
}x ) or next;
$lookup{$code} = $mnemonic;
}
}
sub lookup {
my $self = shift;
return $lookup{shift()};
}
1;
__DATA__
INET_E_INVALID_URL (0x800C0002L or -2146697214)
INET_E_NO_SESSION (0x800C0003L or -2146697213)
INET_E_CANNOT_CONNECT (0x800C0004L or -2146697212)
INET_E_RESOURCE_NOT_FOUND (0x800C0005L or -2146697211)
INET_E_OBJECT_NOT_FOUND (0x800C0006L or -2146697210)
INET_E_DATA_NOT_AVAILABLE (0x800C0007L or -2146697209)
INET_E_DOWNLOAD_FAILURE (0x800C0008L or -2146697208)
INET_E_AUTHENTICATION_REQUIRED (0x800C0009L or -2146697207)
INET_E_NO_VALID_MEDIA (0x800C000AL or -2146697206)
INET_E_CONNECTION_TIMEOUT (0x800C000BL or -2146697205)
INET_E_INVALID_REQUEST (0x800C000CL or -2146697204)
INET_E_UNKNOWN_PROTOCOL (0x800C000DL or -2146697203)
INET_E_SECURITY_PROBLEM (0x800C000EL or -2146697202)
INET_E_CANNOT_LOAD_DATA (0x800C000FL or -2146697201)
INET_E_CANNOT_INSTANTIATE_OBJECT (0x800C0010L or -2146697200)
INET_E_REDIRECT_FAILED (0x800C0014L or -2146697196)
INET_E_REDIRECT_TO_DIR (0x800C0015L or -2146697195)
INET_E_CANNOT_LOCK_REQUEST (0x800C0016L or -2146697194)
INET_E_USE_EXTEND_BINDING (0x800C0017L or -2146697193)
INET_E_TERMINATED_BIND (0x800C0018L or -2146697192)
INET_E_INVALID_CERTIFICATE (0x800C0019L or -2146697191)
INET_E_CODE_DOWNLOAD_DECLINED (0x800C0100L or -2146696960)
INET_E_RESULT_DISPATCHED (0x800C0200L or -2146696704)
INET_E_CANNOT_REPLACE_SFP_FILE (0x800C0300L or -2146696448)
INET_E_CODE_INSTALL_BLOCKED_BY_HASH_POLICY (0x800C0500L or -2146695936)
INET_E_CODE_INSTALL_SUPPRESSED (0x800C0400L or -2146696192)
对于OLE相关的错误,请参阅Win32::OLE
文档:
Win32::OLE->LastError()
LastError()
类方法返回最后记录的OLE错误。 这是一个像$!
这样的双重价值$!
变量:在数字上下文中,它返回错误号,在字符串上下文中,它返回错误消息。 错误号是带符号的HRESULT
值。 请使用HRESULT(ERROR)
函数将无符号十六进制常量转换为带符号的HRESULT
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.