File Coverage

blib/lib/XML/WriterX/Simple.pm
Criterion Covered Total %
statement 55 62 88.7
branch 40 54 74.0
condition 11 11 100.0
subroutine 7 7 100.0
pod 3 4 75.0
total 116 138 84.0


line stmt bran cond sub pod time code
1             package XML::WriterX::Simple;
2             $XML::WriterX::Simple::VERSION = '0.151401';
3             #ABSTRACT:Make XML production simpler.
4 2     2   54991 use 5.010;
  2         6  
  2         83  
5 2     2   11 use strict;
  2         2  
  2         75  
6 2     2   9 use warnings FATAL => 'all';
  2         6  
  2         1997  
7              
8              
9              
10             sub XML::Writer::produce{
11 21     21 0 9260 my $writer = shift;
12            
13             TAG:
14 21         55 while( my $tagName = shift ){
15 22         60 my ($attr, $children, $text) = XML::WriterX::Simple::arrange_args( $writer, shift );
16 22 100 100     154 if(($text//'') eq '' and !@$children){
      100        
17 1         6 $writer->emptyTag( $tagName, @$attr );
18             }
19             else{
20 21 100       34 if(ref($text) eq 'CODE'){
21 3         8 XML::WriterX::Simple::produce_content( $writer, $tagName => $text );
22             }
23             else{
24 18         57 $writer->startTag( $tagName, @$attr );
25 18 50       760 $writer->characters( $text ) if defined $text;
26 18         35 while( @$children ){
27 26         100 my ($tag, $content) = (shift(@$children), shift(@$children));
28 26 100 100     131 $tag = ".$tagName" if $tag =~ /^[&"]$/ and ref $content eq 'CODE';
29 26         50 XML::WriterX::Simple::produce_content( $writer, $tag => $content );
30             }
31 18         340 $writer->endTag( $tagName );
32             }
33             }
34             }
35             #return writer to allow chaining
36 21         408 $writer;
37             }
38              
39              
40             sub stringify{
41 16     16 1 21 local $_ = shift;
42 16 50       78 return $_ unless ref;
43 0 0       0 if(ref eq 'ARRAY'){
    0          
    0          
    0          
44             }
45             elsif(ref eq 'HASH'){
46             }
47             elsif(ref eq 'SCALAR'){
48 0         0 return $$_;
49             }
50             elsif(ref eq 'REF'){
51 0         0 return stringify( $$_ );
52             }
53 0         0 return "$_";#? REGEXP or GLOB or blessed object... : let's use perl stringifier
54             }
55              
56             sub arrange_args{
57 22     22 1 28 my ($writer, $tagContent) = @_;
58 22         23 my (@attr, @children, $text);
59 22 100       65 if(ref $tagContent eq 'CODE'){
    100          
60 3         4 $text = $tagContent;
61             }
62             elsif(defined $tagContent){
63 18 100       64 @_ = @$tagContent if ref $tagContent eq 'ARRAY';
64 18 100       39 @_ = %$tagContent if ref $tagContent eq 'HASH';
65 18 100       54 @_ = ('"', $$tagContent) if ref($tagContent) =~ /^(SCALAR|REF)$/;
66 18 100       57 @_ = ('"', $tagContent) if !ref $tagContent;
67 18         35 while( @_ ){
68 31         39 my ($tag,$content) = (shift, shift);
69 31 100 100     148 if($tag =~ /^#/){
    100          
    100          
70             #comment is added as a children
71 2         6 push @children, $tag => $content;
72             }
73             elsif($tag =~ /^:attr/ and ref($content) =~ /^(ARRAY|HASH)$/){
74             #multiple attributes in $content
75 1 50       8 my @attrs = $1 eq 'ARRAY' ? @$content : %$content;
76             #!warning if %attr != @$content : attribute name must be unique!
77 1         10 push @attr, shift(@attrs), shift(@attrs) while @attrs;
78             }
79             elsif($tag =~ /^:(.*)/){
80             #single attribute named $1 value is stringify($content)
81 4         17 push @attr, $1 => $content;
82             }
83             else{
84             #(processing instruction are added as a children like all other cases)
85 24         66 push @children, $tag => $content;
86             }
87             }
88             }
89 22         65 return (\@attr, \@children, $text);
90             }
91              
92              
93             #CANNOT:
94             # - produce a comment from a sub{}
95             # - produce a tag attributes from a sub{}
96             # - prodice attributes from a sub{} ?
97             sub produce_content{
98 29     29 1 39 my ($writer, $tag, $content) = @_;
99              
100 29 50       52 unless($tag){
101 0         0 warn "try to produce content without any tag name!";
102 0         0 $DB::single=1;
103 0         0 return;
104             }
105              
106 29 100       55 if(ref($content) eq 'CODE'){
107 5 100       21 $writer->startTag( $tag ) unless $tag =~ /^\./;
108 5         82 $content->( $writer, $tag );
109 5 100       72 $writer->endTag( $tag ) unless $tag =~ /^\./;
110 5         44 return;
111             }
112              
113 24 100       64 return $writer->characters( stringify( $content ) )
114             if $tag eq '"';
115              
116 10 100       29 return $writer->comment( stringify $content )
117             if $tag =~ /^#/;
118              
119 8 50       22 return $writer->pi( $1 => stringify $content )
120             if $tag =~ /^\?(.*)/;
121            
122 8 50       15 return $writer->produce( $tag, $$content )
123             if ref $content eq 'SCALAR';
124            
125 8         25 return $writer->produce( $tag, $content );
126             }
127              
128              
129             1; # End of XML::WriterX::Simple
130              
131             __END__