代码之家  ›  专栏  ›  技术社区  ›  polemon

为什么XML::LibXML在禁用打印错误时仍会继续打印错误?

  •  4
  • polemon  · 技术社区  · 15 年前

    XML::LibXML

    后面的HTML文件有一些小错误,解析器会报告这些错误:

    http://is.gd/create.php?longurl=http://google.com:15: validity error : ID smallink already defined
    nal URL was <a href="http://google.com">http://google.com</a><span id="smallink"
                                                                                    ^
    http://is.gd/create.php?longurl=http://google.com:15: validity error : ID smallink already defined
    and use <a href="http://is.gd/fNqtL-">http://is.gd/fNqtL-</a><span id="smallink"
                                                                                    ^
    

    但是,我禁用了错误报告:

    my $parser = XML::LibXML->new();
    $parser->set_options({ recover           => 2,
                           validation        => 0,
                           suppress_errors   => 1,
                           suppress_warnings => 1,
                           pedantic_parser   => 0,
                           load_ext_dtd      => 0, });
    
    my $doc = $parser->parse_html_file("http://is.gd/create.php?longurl=$url");
    

    2>/dev/null ,我不想要。有人能帮我摆脱这些错误吗?

    2 回复  |  直到 15 年前
        1
  •  2
  •   Eugene Yarmash    15 年前

    一个可能的解决方案是安装一个 $SIG{__WARN__} 用于过滤消息或只是使所有警告静音的处理程序:

    local $SIG{__WARN__} = sub { /* $_[0] is the message */ };
    
        2
  •  6
  •   rafl    15 年前

    每次要打印警告时,perl都会查找 $SIG{__WARN__} 如果其中包含代码引用,则调用它而不是打印警告本身。

    您可以使用它来停止要打印的警告 STDERR . 但是,你应该小心。确保只抑制假阳性,而不是 警告。警告通常是有用的。另外,请确保您使用的 尽可能小的范围来避免奇怪的副作用。

    # warnings happen just as always
    my $parser = ...;
    $parser->set_options(...);
    
    { # in this scope we filter some warnings
        local $SIG{__WARN__} = sub {
            my ($warning) = @_;
            print STDERR $warning if $warning !~ /validity error/;
        };
    
        $parser->parse_html_file(...);
    }
    
    # more code, now the warnings are back to normal again
    

    还要注意,这一切都是假设这些警告来自perl空间。libxml2(XML::LibXML暗中使用的C库)很可能直接将警告写入stderr本身。 $SIG{uu警告} 无法阻止它这么做。

    推荐文章