File Coverage

blib/lib/ePod.pm
Criterion Covered Total %
statement 106 147 72.1
branch 35 66 53.0
condition 13 29 44.8
subroutine 8 10 80.0
pod 4 6 66.6
total 166 258 64.3


line stmt bran cond sub pod time code
1             #############################################################################
2             ## Name: ePod.pm
3             ## Purpose: ePod - easy-POD converter to POD.
4             ## Author: Graciliano M. P.
5             ## Modified by:
6             ## Created: 2004-01-13
7             ## RCS-ID:
8             ## Copyright: (c) 2004 Graciliano M. P.
9             ## Licence: This program is free software; you can redistribute it and/or
10             ## modify it under the same terms as Perl itself
11             #############################################################################
12            
13             package ePod ;
14 1     1   6144 use 5.006 ;
  1         2  
  1         35  
15            
16 1     1   4 use strict qw(vars);
  1         2  
  1         41  
17 1     1   5 no warnings ;
  1         10  
  1         61  
18            
19 1     1   5 use vars qw($VERSION @ISA) ;
  1         2  
  1         2851  
20            
21             $VERSION = '0.05' ;
22            
23             require Exporter;
24             @ISA = qw(Exporter);
25            
26             our @EXPORT = qw(to_pod epod2pod) ;
27             our @EXPORT_OK = @EXPORT ;
28            
29             ########
30             # VARS #
31             ########
32            
33             my $OVER_SIZE_DEF = 4 ;
34            
35             my $OVER_SIZE = $OVER_SIZE_DEF ;
36            
37             #######
38             # NEW #
39             #######
40            
41             sub new {
42 1     1 1 11 my $this = shift ;
43 1 50       3 return( $this ) if ref($this) ;
44 1   50     3 my $class = $this || __PACKAGE__ ;
45 1         3 $this = bless({} , $class) ;
46            
47 1         3 my ( %args ) = @_ ;
48            
49 1         5 foreach my $Key ( keys %args ) {
50 1         3 my $k = $Key ;
51 1         6 $k =~ s/[\W_]//gs ; $k = uc($k) ;
  1         4  
52 1         10 $this->{$k} = $args{$Key} ;
53             }
54            
55 1 50 33     12 $this->{OVERSIZE} = $OVER_SIZE_DEF if !$this->{OVERSIZE} || $this->{OVERSIZE} !~ /^\d+$/s ;
56            
57 1         4 return $this ;
58             }
59            
60             ##########
61             # TO_POD #
62             ##########
63            
64             sub to_pod {
65 0 0   0 1 0 my $this = UNIVERSAL::isa($_[0] , 'ePod') ? shift : undef ;
66 0 0       0 $this = ePod->new() if !$this ;
67            
68 0         0 my ($data , $file) ;
69            
70 0 0 0     0 if ( ref($_[0]) eq 'GLOB' ) {
    0          
71 0         0 1 while( read($_[0], $data , 1024*8 , length($data) ) ) ;
72 0         0 shift ;
73             }
74             elsif ( $_[0] !~ /[\r\n]/s && -s $_[0] ) {
75 0         0 $file = shift ;
76 0         0 open (my $fh,$file) ; binmode($fh) ;
  0         0  
77 0         0 1 while( read($fh, $data , 1024*8 , length($data) ) ) ;
78 0         0 close ($fh) ;
79             }
80 0         0 else { $data = shift ;}
81            
82 0 0 0     0 my $new_file = ( $_[0] =~ /\.pod$/i && $_[0] !~ /[\r\n]/s ) ? shift : $file ;
83 0         0 my $replace = shift ;
84            
85 0 0       0 if ($new_file eq '') { 'unamed' ;}
  0         0  
86            
87 0         0 $new_file =~ s/\.epod$/.pod/i ;
88 0 0       0 if ( $new_file !~ /\.pod$/i) { $new_file .= '.pod' ;}
  0         0  
89            
90 0   0     0 while ( !$replace && -e $new_file ) {
91 0         0 $new_file =~ s/(?:-?(\d+))?(\.pod)$/ my $n = $1 + 1 ; "-$n$2" /gei ;
  0         0  
  0         0  
92             }
93            
94 0         0 $data = $this->epod2pod($data) ;
95            
96 0         0 open (my $fh,">$new_file") ; binmode($fh) ;
  0         0  
97 0         0 print $fh $data ;
98 0         0 close ($fh) ;
99            
100 0 0       0 if ( wantarray ) { return( $new_file , $data ) ;}
  0         0  
101 0         0 return $new_file ;
102             }
103            
104             ############
105             # EPOD2POD #
106             ############
107            
108             sub epod2pod {
109 5 50   5 1 903 my $this = UNIVERSAL::isa($_[0] , 'ePod') ? shift : undef ;
110 5 50       14 $this = ePod->new() if !$this ;
111            
112 5         8 $OVER_SIZE = $this->{OVERSIZE} ;
113            
114 5         6 my ($data , $fh , $no_close) ;
115 5 50 33     26 if ( ref($_[0]) eq 'GLOB' ) { $fh = $_[0] ; $no_close = 1 ;}
  0 50       0  
  0         0  
116 0         0 elsif ( $_[0] =~ /[\r\n]/s && !-e $_[0] ) { $data = $_[0] ;}
117 5         148 else { open ($fh,$_[0]) ;}
118            
119 5 50       14 if ( $fh ) {
120 5         9 binmode($fh) ;
121 5         160 1 while( read($fh, $data , 1024*8 , length($data) ) ) ;
122 5 50       45 close ($fh) if !$no_close ;
123             }
124            
125 5         180 $data =~ s/\r\n?/\n/gs ;
126            
127 5         14 $data = "\n\n$data\n" ;
128            
129 5         540 $data =~ s/(\S)[ \t]+\n/$1\n/gs ;
130            
131 5         244 1 while( $data =~ s/(\n\S[^\n]*)(?:\n[ \t]*){2,}(\n\S[^\n]*\n)/$1\n$2/gxs );
132            
133 5         718 1 while( $data =~ s/((?:^|\n)\S[^\n]*\n)([ \t]+\n)+/
134 0         0 my $init = $1 ;
135 0         0 my $ns = $2 ;
136 0         0 $ns =~ s~[ \t]~~gs ;
137 0         0 "$init$ns"
138             /gexs ) ;
139            
140 5         32 $data =~ s/\n=((?:head\d+|item)\s)/\n=EPOD_FIX_$1/gs ;
141            
142 5   66     29 $data =~ s/\n(?:=(>+)|(=+)>)[ \t]*/ my $n = length($1||$2) ; "\n=head$n " /ges ;
  22         57  
  22         143  
143            
144 5         86 my @blocks = split(/\n+=head[ \t]*/s , $data) ;
145 5         10 foreach my $blocks_i ( @blocks ) {
146 27         41 $blocks_i = adjust_spaces($blocks_i) ;
147 27         37 $blocks_i = adjust_itens($blocks_i) ;
148 27         42 $blocks_i = adjust_itens($blocks_i) ;
149             }
150 5         25 $data = join("\n=head", @blocks) ;
151            
152 5 50       18 return undef if $data !~ /\S/s ;
153            
154 5         11 $data =~ s/\n=EPOD_FIX_(\w+)/\n=$1/gs ;
155            
156 5         140 $data =~ s/\n(=\w)/\r$1/gs ;
157            
158 5         190 $data =~ s/((?:\r|^)=\w+[^\r\n]*)\n+/$1\r\n\n/gs ;
159            
160 5         44 $data =~ s/\r\n\n\r/\n\n/gs ;
161 5         90 $data =~ s/\r(=\w)/\n$1/gs ;
162 5         54 $data =~ s/\r//gs ;
163            
164 5         17 $data =~ s/^\s*/\n\n/s ;
165            
166 5 50       25 $data =~ s/^\s*/\n\n=pod\n\n/s if $data !~ /^\s*?\n=\w+\s/s ;
167            
168 5 50       576 $data =~ s/\s*$/\n\n=cut\n\n/s if $data !~ /\n=cut\s*$/ ;
169            
170 5         36 return $data ;
171             }
172            
173             ###########
174             # IS_EPOD #
175             ###########
176            
177             sub is_epod {
178 0 0   0 1 0 if ( $_[0] =~ /(?:[\r\n]|^)(?:=+>|=>+|\*+>|\*>+)[^>]/ ) { return 1 ;}
  0         0  
179 0         0 return 1 ;
180             }
181            
182             #################
183             # ADJUST_SPACES #
184             #################
185            
186             sub adjust_spaces {
187 96     96 0 125 my $block = shift ;
188 96         93 my ( $not_init ) = @_ ;
189 96 100       373 $block =~ s/^((?:[^\n]+\n))\n*/$1\n\n/s if !$not_init ;
190 96         1750 $block =~ s/\n*$/\n/s ;
191 96         309 return( $block ) ;
192             }
193            
194             ################
195             # ADJUST_ITENS #
196             ################
197            
198             sub adjust_itens {
199 100     100 0 99 my $block = shift ;
200 100         91 my $level = shift ;
201            
202             {
203 100         90 my (@items) = ( $block =~ /(?:\n|^)
  100         2054  
204             (
205             \/?
206             (?:
207             \*>+
208             |
209             \*+>
210             )
211             |
212             \*+\/
213             )
214             /sxg ) ;
215            
216 100 100       295 return( $block ) if !@items ;
217            
218 23 100       44 if ( !$level ) {
219 12         16 foreach my $items_i ( @items ) {
220 12         36 my ($n1,$n2) = ( $items_i =~ /^(?:(\*+)>|\*(>+))$/ );
221 12   66     29 my $n = length($n1 || $n2) ;
222 12 50       31 next if !$n ;
223 12         10 $level = $n ;
224 12         30 last ;
225             }
226             }
227             else {
228 11         11 my $min_level ;
229            
230 11         14 foreach my $items_i ( @items ) {
231 32         103 my ($n1,$n2) = ( $items_i =~ /^(?:(\*+)>|\*(>+))$/ );
232 32   100     112 my $n = length($n1 || $n2) ;
233 32 100       60 next if !$n ;
234 26 100 100     110 $min_level = $n if $n < $min_level || !$min_level ;
235             }
236            
237 11 100       29 if ( $min_level > $level ) { $level = $min_level ;}
  1         2  
238             }
239             }
240            
241 23 50       43 $level = 1 if $level < 1 ;
242            
243             ##########################
244            
245 23         628 my ($block_itens , $block_rest) = split(/
246             \n
247             (?:
248             \/\*>{$level}
249             |
250             \/\*{$level}>
251             |
252             \*{$level}\/
253             )
254             [^>]
255             \n*
256             /sx , "$block\n" , 2) ;
257            
258 23 100       74 if ( $block_rest ) { $block_rest =~ s/\n$//s ;}
  8         24  
259 15         44 else { $block_itens =~ s/\n$//s ;}
260            
261 23         38 $block_itens =~ s/\n=(item\s)/\n=EPOD_FIX_$1/gs ;
262            
263             ##########################
264            
265 23         1042 $block_itens =~ s/
266             (?:\n|^)
267             (?:
268             \*>{$level}
269             |
270             \*{$level}>
271             )
272             ([^>])
273             [ \t]*
274             /\n=item$1/gsx ;
275            
276             ##########################
277            
278 23         156 my @itens = split(/\n+=item[ \t]*/s , $block_itens) ;
279            
280 23         36 my $top = shift(@itens) ;
281            
282 23         31 foreach my $itens_i ( @itens ) {
283 37         59 $itens_i = adjust_spaces($itens_i) ;
284 37         104 $itens_i = adjust_itens($itens_i , $level+1) ;
285             }
286            
287 23 100       175 if ( $top =~ /(?:\n|^)(?:\*+>|\*>+)[^>]/s ) {
288 1         4 $top = adjust_itens( adjust_spaces($top,1) ) ;
289             }
290            
291 23 100       213 $top =~ s/\s*$/\n\n=over $OVER_SIZE\n/s if @itens ;
292            
293 23 100       290 $itens[ $#itens ] =~ s/\s*$/\n\n=back\n/s if @itens ;
294            
295 23 100       47 $block_rest = adjust_itens( adjust_spaces($block_rest,1) ) if $block_rest ;
296 23         70 $block_rest =~ s/^\s*/\n/s ;
297            
298 23         57 $block = join("\n=item ", $top , @itens ) . $block_rest ;
299            
300 23         32 $block = adjust_spaces($block , 1) ;
301            
302 23         67 return $block ;
303             }
304            
305             #######
306             # END #
307             #######
308            
309             1;
310            
311            
312             __END__