Rename files according to xml tag contents

2019-08-17 07:06发布

I have a huge amount of XML files that I need to rename. They are .plist files.

Within each file are a few tags, like this:

<key>Name</key>
<string>Steve Allen</string>
<key>Place</key>
<string>London</string>

At the moment, all the files are named with long random numbers, like 659238592496052.record but I need them to be names according to the Name in the files, like SteveAllen.record (without any space).

How would I do this?

2条回答
孤傲高冷的网名
2楼-- · 2019-08-17 07:25
for file in *.record
do
  nameline=$(grep -A 1 '<key>Name</key>' "$file" | tail -n +2) # Get line after Name key
  name=${nameline/<string>/} # Remove initial <string>
  name=${name/<\/string>/} # Remove trailing </string>
  name=${name// /} # Remove all spaces
  mv "$file" "$name".record
done
查看更多
看我几分像从前
3楼-- · 2019-08-17 07:35

The fragment you've posted is not valid xml so let's pretend it looks like this

<body>
<item>
<key>Name</key>
<string>Steve Allen</string>
</item>
<item>
<key>Place</key>
<string>London</string>
</item>
</body>

Using that fragment as input, this program will rename any number of files given as args If you saved the program as "myrename" then "myrename file1.xml file2.xml file3.xml" would alter the pathname of file1.xml file2.xml and file3.xml to whatever the first item

The tag being called "key" seems to work in a sightly magical way :/

#!/usr/bin/perl

use XML::Simple;
for $file ( @ARGV[ 0 .. $#ARGV ] ) {

    my $ref = XMLin($file);

    $new_name = $ref->{'item'}->{'Name'}->{'string'};

    rename $file, "$new_name.xml" || warn "couldn't rename $file $!";
}
查看更多
登录 后发表回答