File Coverage
| File: | tools/xml_pp/xml_pp |
| Coverage: | 58.1% |
| line | stmt | bran | cond | sub | pod | time | code |
|---|---|---|---|---|---|---|---|
| 1 | #!/usr/bin/perl -w | ||||||
| 2 | # $Id: /xmltwig/trunk/tools/xml_pp/xml_pp 32 2008-01-18T13:11:52.128782Z mrodrigu $ | ||||||
| 3 |
26
26
26
|
83872
32
668
|
use strict; | ||||
| 4 | |||||||
| 5 |
26
26
26
|
35332
38
167
|
use XML::Twig; | ||||
| 6 |
26
26
26
|
110998
268982
1132
|
use File::Temp qw/tempfile/; | ||||
| 7 |
26
26
26
|
88
18
39341
|
use File::Basename qw/dirname/; | ||||
| 8 | |||||||
| 9 |
26
|
1972685
|
my @styles= XML::Twig->_pretty_print_styles; # from XML::Twig | ||||
| 10 |
26
|
98
|
my $styles= join '|', @styles; # for usage | ||||
| 11 |
26
286
|
34
270
|
my %styles= map { $_ => 1} @styles; # to check option | ||||
| 12 | |||||||
| 13 |
26
|
43
|
my $DEFAULT_STYLE= 'indented'; | ||||
| 14 | |||||||
| 15 |
26
|
79
|
my $USAGE= "usage: $0 [-v] [-i<extension>] [-s ($styles)] [-p <tag(s)>] [-e <encoding>] [-l] [-f <file>] [<files>]"; | ||||
| 16 | |||||||
| 17 | # because of the -i.bak option I don't think I can use one of the core | ||||||
| 18 | # option processing modules, so it's custom handling and no clusterization :--( | ||||||
| 19 | |||||||
| 20 | |||||||
| 21 |
26
|
44
|
my %opt= process_options(); # changes @ARGV | ||||
| 22 | |||||||
| 23 |
21
|
51
|
my @twig_options=( pretty_print => $opt{style}, | ||||
| 24 | error_context => 1, | ||||||
| 25 | ); | ||||||
| 26 |
21
|
37
|
if( $opt{preserve_space_in}) | ||||
| 27 |
0
|
0
|
{ push @twig_options, keep_spaces_in => $opt{preserve_space_in};} | ||||
| 28 | |||||||
| 29 |
21
|
39
|
if( $opt{encoding}) | ||||
| 30 |
0
|
0
|
{ push @twig_options, output_encoding => $opt{encoding}; | ||||
| 31 | } | ||||||
| 32 | else | ||||||
| 33 |
21
|
36
|
{ push @twig_options, keep_encoding => 1; } | ||||
| 34 | |||||||
| 35 | # in normal (ie not -l) mode tags are output as soon as possible | ||||||
| 36 |
243
|
418
|
push @twig_options, twig_handlers => { _all_ => sub { $_[0]->flush } } | ||||
| 37 |
21
|
101
|
unless( $opt{load}); | ||||
| 38 | |||||||
| 39 |
21
|
41
|
if( @ARGV) | ||||
| 40 |
21
|
31
|
{ foreach my $file (@ARGV) | ||||
| 41 |
21
|
52
|
{ print STDERR "$file\n" if( $opt{verbose}); | ||||
| 42 | |||||||
| 43 |
21
|
62
|
my $t= XML::Twig->new( @twig_options); | ||||
| 44 | |||||||
| 45 |
21
|
19
|
my $tempfile; | ||||
| 46 |
21
|
48
|
if( $opt{in_place}) | ||||
| 47 |
21
|
721
|
{ (undef, $tempfile)= tempfile( DIR => dirname( $file)) or die "cannot create tempfile for $file: $!\n" ; | ||||
| 48 |
21
|
4993
|
open( PP_OUTPUT, ">$tempfile") or die "cannot create tempfile $tempfile: $!"; | ||||
| 49 |
21
|
103
|
select PP_OUTPUT; | ||||
| 50 | } | ||||||
| 51 |
21
|
65
|
$t= $t->safe_parsefile( $file); | ||||
| 52 | |||||||
| 53 |
21
|
40
|
if( $t) | ||||
| 54 |
21
0
|
42
0
|
{ if( $opt{load}) { $t->print; } | ||||
| 55 | |||||||
| 56 |
21
|
47
|
select STDOUT; | ||||
| 57 | |||||||
| 58 |
21
|
39
|
if( $opt{in_place}) | ||||
| 59 |
21
|
1015
|
{ close PP_OUTPUT; | ||||
| 60 |
21
|
52
|
my $mode= mode( $file); | ||||
| 61 |
21
|
58
|
if( $opt{backup}) | ||||
| 62 |
0
|
0
|
{ my $backup= backup( $file, $opt{backup}); | ||||
| 63 |
0
|
0
|
rename( $file, $backup) or die "cannot create backup file $backup: $!"; | ||||
| 64 | } | ||||||
| 65 |
21
|
23655
|
rename( $tempfile, $file) or die "cannot overwrite file $file: $!"; | ||||
| 66 |
21
21
|
39
605
|
if( $mode ne mode( $file)) { chmod $mode, $file or die "cannot set $file mode to $mode: $!"; } | ||||
| 67 | } | ||||||
| 68 | |||||||
| 69 | } | ||||||
| 70 | else | ||||||
| 71 |
0
|
0
|
{ if( defined $tempfile) | ||||
| 72 |
0
|
0
|
{ unlink $tempfile or die "cannot unlink temp file $tempfile: $!"; } | ||||
| 73 |
0
|
0
|
die $@; | ||||
| 74 | } | ||||||
| 75 | } | ||||||
| 76 | } | ||||||
| 77 | else | ||||||
| 78 |
0
|
0
|
{ my $t= XML::Twig->new( @twig_options); | ||||
| 79 |
0
|
0
|
$t->parse( \*STDIN); | ||||
| 80 |
0
0
|
0
0
|
if( $opt{load}) { $t->print; } | ||||
| 81 | } | ||||||
| 82 | |||||||
| 83 | |||||||
| 84 | sub mode | ||||||
| 85 |
42
|
55
|
{ my( $file)= @_; | ||||
| 86 |
42
|
242
|
return (stat($file))[2]; | ||||
| 87 | } | ||||||
| 88 | |||||||
| 89 | sub process_options | ||||||
| 90 |
26
|
25
|
{ my %opt; | ||||
| 91 |
26
|
147
|
while( @ARGV && ($ARGV[0]=~ m{^-}) ) | ||||
| 92 |
29
|
31
|
{ my $opt= shift @ARGV; | ||||
| 93 |
29
|
344
|
if( ($opt eq '-v') || ($opt eq '--verbose') ) | ||||
| 94 |
0
|
0
|
{ die $USAGE if( $opt{verbose}); | ||||
| 95 |
0
|
0
|
$opt{verbose}= 1; | ||||
| 96 | } | ||||||
| 97 | elsif( ($opt eq '-s') || ($opt eq '--style') ) | ||||||
| 98 |
1
|
2
|
{ die $USAGE if( $opt{style}); | ||||
| 99 |
1
|
1
|
$opt{style}= shift @ARGV; | ||||
| 100 |
1
|
68
|
die $USAGE unless( $styles{$opt{style}}); | ||||
| 101 | } | ||||||
| 102 | elsif( ($opt=~ m{^-i(.*)$}) || ($opt=~ m{^--in_place(.*)$}) ) | ||||||
| 103 |
23
|
109
|
{ die $USAGE if( $opt{in_place}); | ||||
| 104 |
22
|
28
|
$opt{in_place}= 1; | ||||
| 105 |
22
|
153
|
$opt{backup}= $1 ||''; | ||||
| 106 | } | ||||||
| 107 | elsif( ($opt eq '-p') || ($opt eq '--preserve') ) | ||||||
| 108 |
0
|
0
|
{ my $tags= shift @ARGV; | ||||
| 109 |
0
|
0
|
my @tags= split /\s+/, $tags; | ||||
| 110 |
0
|
0
|
$opt{preserve_space_in} ||= []; | ||||
| 111 |
0
0
|
0
0
|
push @{$opt{preserve_space_in}}, @tags; | ||||
| 112 | } | ||||||
| 113 | elsif( ($opt eq '-e') || ($opt eq '--encoding') ) | ||||||
| 114 |
2
|
66
|
{ die $USAGE if( $opt{encoding}); | ||||
| 115 |
1
|
4
|
$opt{encoding}= shift @ARGV; | ||||
| 116 | } | ||||||
| 117 | elsif( ($opt eq '-l') || ($opt eq '--load')) | ||||||
| 118 |
2
|
66
|
{ die $USAGE if( $opt{load}); | ||||
| 119 |
1
|
4
|
$opt{load}=1; | ||||
| 120 | } | ||||||
| 121 | elsif( ($opt eq '-f') || ($opt eq '--files') ) | ||||||
| 122 |
0
|
0
|
{ my $file= shift @ARGV; | ||||
| 123 |
0
|
0
|
push @ARGV, files_from( $file); | ||||
| 124 | } | ||||||
| 125 | elsif( ($opt eq '-h') || ($opt eq '--help')) | ||||||
| 126 |
1
1
|
52020
87
|
{ system "pod2text", $0; exit; } | ||||
| 127 | elsif( $opt eq '--') | ||||||
| 128 |
0
|
0
|
{ last; } | ||||
| 129 | else | ||||||
| 130 |
0
|
0
|
{ die $USAGE; } | ||||
| 131 | } | ||||||
| 132 | |||||||
| 133 |
21
|
72
|
$opt{style} ||= $DEFAULT_STYLE; | ||||
| 134 | |||||||
| 135 |
21
|
70
|
return %opt; | ||||
| 136 | } | ||||||
| 137 | |||||||
| 138 | # get the list of files (one per line) from a file | ||||||
| 139 | sub files_from | ||||||
| 140 |
0
|
{ my $file= shift; | |||||
| 141 |
0
|
open( FILES, "<$file") or die "cannot open file $file: $!"; | |||||
| 142 |
0
|
my @files; | |||||
| 143 |
0
0
0
|
while( <FILES>) { chomp; push @files, $_; } | |||||
| 144 |
0
|
close FILES; | |||||
| 145 |
0
|
return @files; | |||||
| 146 | } | ||||||
| 147 | |||||||
| 148 | sub backup | ||||||
| 149 |
0
|
{ my( $file, $extension)= @_; | |||||
| 150 |
0
|
my $backup; | |||||
| 151 |
0
|
if( $extension=~ m{\*}) | |||||
| 152 |
0
|
{ ($backup= $extension)=~ s{\*}{$file}g; } | |||||
| 153 | else | ||||||
| 154 |
0
|
{ $backup= $file.$extension; } | |||||
| 155 |
0
|
return $backup; | |||||
| 156 | } | ||||||
| 157 | |||||||