0

出力を解析できるように、WSMAN からの XML 出力を複数の XML ファイルに分割したいと考えています。

WSMAN は以下のような出力を提供します。これには基本的に、それぞれが独自のルート ノードを持つ 2 つの異なる XML ファイルがあります。

<?xml version="1.0" encoding="UTF-8"?>
  <s:Body>
    <wsen:PullResponse>
      <wsen:Items>
        <n1:DCIM_SoftwareIdentity>
          <n1:ComponentType>BIOS</n1:ComponentType>
          <n1:InstanceID>DCIM:CURRENT#741__BIOS.Setup.1-1</n1:InstanceID>
          <n1:VersionString>1.3.6</n1:VersionString>
        </n1:DCIM_SoftwareIdentity>
      </wsen:Items>
    </wsen:PullResponse>
  </s:Body>
<?xml version="1.0" encoding="UTF-8"?>
  <s:Body>
    <wsen:PullResponse>
      <wsen:Items>
        <n1:DCIM_SoftwareIdentity>
          <n1:ComponentType>BIOS</n1:ComponentType>
          <n1:InstanceID>DCIM:INSTALLED#741__BIOS.Setup.1-1</n1:InstanceID>
          <n1:VersionString>1.3.6</n1:VersionString>
        </n1:DCIM_SoftwareIdentity>
      </wsen:Items>
    </wsen:PullResponse>
  </s:Body>

上記の出力には、 XMLXML::Simpleに関して「ジャンク」である 2 つのルート要素が含まれているため、上記の出力を解析できません。

質問/声明:

上記の出力を、以下のようにそれぞれ独自のルート要素を含む 2 つの異なる XML ファイルに分割したいと考えています。

<?xml version="1.0" encoding="UTF-8"?>
  <s:Body>
    <wsen:PullResponse>
      <wsen:Items>
        <n1:DCIM_SoftwareIdentity>
          <n1:ComponentType>BIOS</n1:ComponentType>
          <n1:InstanceID>DCIM:CURRENT#741__BIOS.Setup.1-1</n1:InstanceID>
          <n1:VersionString>1.3.6</n1:VersionString>
        </n1:DCIM_SoftwareIdentity>
      </wsen:Items>
    </wsen:PullResponse>
  </s:Body>

……

<?xml version="1.0" encoding="UTF-8"?>
  <s:Body>
    <wsen:PullResponse>
      <wsen:Items>
        <n1:DCIM_SoftwareIdentity>
          <n1:ComponentType>BIOS</n1:ComponentType>
          <n1:InstanceID>DCIM:INSTALLED#741__BIOS.Setup.1-1</n1:InstanceID>
          <n1:VersionString>1.3.6</n1:VersionString>
        </n1:DCIM_SoftwareIdentity>
      </wsen:Items>
    </wsen:PullResponse>
  </s:Body>

私の論理:

1) 出力を 1 行ずつ解析する

2) パターンに遭遇した場合は?xml version、新しい XML ファイルを作成し、?xml version再びパターンに遭遇するまで、この新しいファイルに 1 行以上の行を書き込みます?xml version

?xml version3)パターンに遭遇するたびにステップ 2 に従う

これが私のコードです:

#!/usr/bin/perl -w
use strict;
use XML::Simple;
use Data::Dumper;

my $counter = 0;
my $fileName;

while (my $line = <DATA>)
{
    if ( $line =~ /\?xml version/ )
    {   
        $counter++;
        print "Creating the BIOS file \n";
        $fileName = "BIOS"."_".$counter;
    }   
    open (my $sub_xml_file, ">" , $fileName) or die "Canot create $fileName: $!\n";
    print $sub_xml_file $line;
}

__DATA__
## omitting this part as this contains the XML info listed above.

さて、私のスクリプトはファイルBIOS_1を作成しますBIOS_2が、上記の XML 出力の最後の行のみを書き込みます。

# cat BIOS_1
  </s:Body>
# cat BIOS_2
  </s:Body>

2 つの異なる XML ファイルを作成するためにスクリプトを修正するのを手伝ってくれませんか...

4

1 に答える 1

0

$line将来のループ パスのために保持することはありません。

すべてをメモリ内にロードする方法:

my $count;
my $file; { local $/; $file = <>; }
for my $xml (split /^(?=<\?xml)/m, $file) {
   my $fn = sprintf("BIOS_%d.xml", ++$count);
   open(my $fh, '>', $fn) or die $!;
   print $fh $xml;
}

行ごとのアプローチ:

my $fh;
my $count;
while (<>) {
   if (/^<\?xml/) {
      my $fn = sprintf("BIOS_%d.xml", ++$count);
      open($fh, '>', $fn) or die $!;
   }

   print $fh $_;
}
于 2013-02-22T10:58:41.417 に答える