親愛なるPerlとXMLの達人
XPathを使用してXMLファイル内の値を更新するタスクがあります。
私はPerlのライブラリを使用して、XMLファイルを読み取り、変更し、保存します。XML::LibXML
# Read XML file
my $parser = XML::LibXML->new();
my $doc = $parser->load_xml(location => $config_file);
my $root = $doc->documentElement();
# Alter nodes\attributes
foreach (keys %environment_values) {
my @nodes = $root->findnodes($_);
if (scalar @nodes < 1) {
print "ERROR: element not found in $config_file by XPath: $_\n";
die;
} elsif (scalar @nodes > 1) {
print "ERROR: more than 1 element (" . scalar @nodes . ") is found in $config_file by XPath: $_\n";
die;
}
my $node = $nodes[0];
if ($node->nodeType == XML_ELEMENT_NODE) {
$node->removeChildNodes();
$node->appendText($environment_values{$_});
} elsif ($node->nodeType == XML_ATTRIBUTE_NODE) {
$node->setValue($environment_values{$_});
} else {
print "ERROR: unknown node type: " . $node->nodeType . "\n";
die;
}
}
# Save the resulting XML file
open (my $fh, '>:raw', $config_file) or die $!;
print $fh $doc->toString();
close $fh;
元のファイルと非常によく似たファイルを生成しますが、それでもいくつかの厄介な問題があります。
- 改行文字(行末)はUnixスタイルですが、元のファイルにはWindowsスタイルがあります。
- 終了/>の前のスペースが削除されます。たとえば、に
<node />
なり<node/>
ます。
これらを修正するチャンスはありますか?元のファイルとまったく同じXMLファイルを取得したいと思っていますが、修正する属性値が異なるだけです...
<xmlpoke>
PS私はNAntのシンプルさが本当に好きです。ただし、この作業にはPerlを使用する必要があります。