剥离 CData 标签 XML Perl
Stripping CData Tags XML Perl
在 PHP 中,您可以通过执行以下操作简单地去除 XML 中的 CDATA 标签:
simplexml_load_string($string, 'SimpleXMLElement', LIBXML_NOCDATA);
我想知道如何使用 XML::Bare
或任何其他模块在 Perl 中执行此操作?
我的客户倾向于发送这样的 xml:
<msg t='sys'><body action='login' r='0'><login z='w1'><nick><![CDATA[Test]]></nick><pword><![CDATA[4c24a5558542bf35cca54d8749c78de6]]></pword></login></body></msg>
使用 XML::Bare 我会这样解析它:
$string = "<msg t='sys'><body action='login' r='0'><login z='w1'><nick><![CDATA[Test]]></nick><pword><![CDATA[4c24a5558542bf35cca54d8749c78de6]]></pword></login></body></msg>";
$strXML = XML::Bare->new('text' => $string)->parse;
say $strXML->{msg}->{body}->{login}->{nick}->{value};
它有效,但我想去掉 cdata 标签以防止 sql 在我的服务器中注入。有谁知道我该怎么做?我在网上搜索了解决方案,但一直找不到。
您可以像这样尝试使用 HTML::Parser
:
#!/usr/bin/env perl
use strict;
use warnings;
use HTML::Parser;
my $xml = <<XML;
<msg t='sys'><body action='login' r='0'><login z='w1'><nick><![CDATA[Test]]></nick><pword><![CDATA[4c24a5558542bf35cca54d8749c78de6]]></pword></login></body></msg>
XML
my $parsed_xml;
HTML::Parser->new(default_h => [ sub { $parsed_xml .= shift }, 'text' ],
xml_mode => 1,
marked_sections => 1,
)->parse($xml) or die $!;
print $parsed_xml;
marked_sections
参数导致解析器 return CDATA
部分的内容作为 text
,然后连接到 $parsed_xml
变量。
例如:
use 5.014;
use warnings;
use XML::LibXML;
#the input xml
my $str = q{<msg t='sys'><body action='login' r='0'><login z='w1'><nick><![CDATA[Test]]></nick><pword><![CDATA[4c24a5558542bf35cca54d8749c78de6]]></pword></login></body></msg>};
#the parsing
my $dom = XML::LibXML->load_xml(
string => $str,
no_cdata => 1, #strip CDATA
);
#nice-print the parsed xml
say $dom->toString(2);
#print the "nick" and pword
say "the nick is ==", $dom->find( '//nick' )->string_value, "==";
say "the pword is ==", $dom->find( '//pword' )->string_value, "==";
打印没有CDATA的原始XML,例如:
<?xml version="1.0"?>
<msg t="sys">
<body action="login" r="0">
<login z="w1">
<nick>Test</nick>
<pword>4c24a5558542bf35cca54d8749c78de6</pword>
</login>
</body>
</msg>
the nick is ==Test==
the pword is ==4c24a5558542bf35cca54d8749c78de6==
在 PHP 中,您可以通过执行以下操作简单地去除 XML 中的 CDATA 标签:
simplexml_load_string($string, 'SimpleXMLElement', LIBXML_NOCDATA);
我想知道如何使用 XML::Bare
或任何其他模块在 Perl 中执行此操作?
我的客户倾向于发送这样的 xml:
<msg t='sys'><body action='login' r='0'><login z='w1'><nick><![CDATA[Test]]></nick><pword><![CDATA[4c24a5558542bf35cca54d8749c78de6]]></pword></login></body></msg>
使用 XML::Bare 我会这样解析它:
$string = "<msg t='sys'><body action='login' r='0'><login z='w1'><nick><![CDATA[Test]]></nick><pword><![CDATA[4c24a5558542bf35cca54d8749c78de6]]></pword></login></body></msg>";
$strXML = XML::Bare->new('text' => $string)->parse;
say $strXML->{msg}->{body}->{login}->{nick}->{value};
它有效,但我想去掉 cdata 标签以防止 sql 在我的服务器中注入。有谁知道我该怎么做?我在网上搜索了解决方案,但一直找不到。
您可以像这样尝试使用 HTML::Parser
:
#!/usr/bin/env perl
use strict;
use warnings;
use HTML::Parser;
my $xml = <<XML;
<msg t='sys'><body action='login' r='0'><login z='w1'><nick><![CDATA[Test]]></nick><pword><![CDATA[4c24a5558542bf35cca54d8749c78de6]]></pword></login></body></msg>
XML
my $parsed_xml;
HTML::Parser->new(default_h => [ sub { $parsed_xml .= shift }, 'text' ],
xml_mode => 1,
marked_sections => 1,
)->parse($xml) or die $!;
print $parsed_xml;
marked_sections
参数导致解析器 return CDATA
部分的内容作为 text
,然后连接到 $parsed_xml
变量。
例如:
use 5.014;
use warnings;
use XML::LibXML;
#the input xml
my $str = q{<msg t='sys'><body action='login' r='0'><login z='w1'><nick><![CDATA[Test]]></nick><pword><![CDATA[4c24a5558542bf35cca54d8749c78de6]]></pword></login></body></msg>};
#the parsing
my $dom = XML::LibXML->load_xml(
string => $str,
no_cdata => 1, #strip CDATA
);
#nice-print the parsed xml
say $dom->toString(2);
#print the "nick" and pword
say "the nick is ==", $dom->find( '//nick' )->string_value, "==";
say "the pword is ==", $dom->find( '//pword' )->string_value, "==";
打印没有CDATA的原始XML,例如:
<?xml version="1.0"?>
<msg t="sys">
<body action="login" r="0">
<login z="w1">
<nick>Test</nick>
<pword>4c24a5558542bf35cca54d8749c78de6</pword>
</login>
</body>
</msg>
the nick is ==Test==
the pword is ==4c24a5558542bf35cca54d8749c78de6==