File Coverage

blib/lib/XML/Handler/ExtOn/TieAttrs.pm
Criterion Covered Total %
statement 116 116 100.0
branch 18 22 81.8
condition 11 13 84.6
subroutine 20 20 100.0
pod 1 5 20.0
total 166 176 94.3


line stmt bran cond sub pod time code
1             package XML::Handler::ExtOn::TieAttrs;
2              
3             =head1 NAME
4              
5             XML::PSAX::TieAttrs
6              
7             =head1 SYNOPSIS
8              
9             use XML::PSAX::TieAttrs;
10              
11             tie %hasha, 'XML::PSAX::TieAttrs', \%hash1, default=>;
12              
13             =head1 DESCRIPTION
14              
15            
16            
17             =cut
18              
19 7     7   79579 use strict;
  7         12  
  7         252  
20 7     7   35 use warnings;
  7         11  
  7         183  
21 7     7   33 use strict;
  7         20  
  7         181  
22 7     7   32 use Carp;
  7         13  
  7         436  
23 7     7   36 use Data::Dumper;
  7         12  
  7         1689  
24             require Tie::Hash;
25             @XML::Handler::ExtOn::TieAttrs::ISA = qw(Tie::StdHash);
26             $XML::Handler::ExtOn::TieAttrs::VERSION = '0.01';
27              
28             sub attr_from_sax2 {
29 6   50 6 0 20 my $sax_attr = shift || {};
30 6         13 my %res = ();
31 6         26 while ( my ( $key, $value ) = each %$sax_attr ) {
32 6         17 my ( $prefix, $name, $ns_uri ) =
33 6         9 @{$value}{qw/ Prefix LocalName NamespaceURI/};
34 6 100       16 $prefix = '' unless defined $prefix;
35 6 50       15 $ns_uri = '' unless defined $ns_uri;
36 6         61 $res{qq/{$ns_uri}$name/} = {%$value};
37             }
38 6         19 return \%res;
39             }
40              
41             my $attrs = {
42             __temp_array => [],
43             _orig_hash => {},
44             _default => undef,
45             _template => {},
46              
47             };
48              
49             ### install get/set accessors for this object.
50             for my $key ( keys %$attrs ) {
51 7     7   40 no strict 'refs';
  7         11  
  7         7741  
52             *{ __PACKAGE__ . "::$key" } = sub {
53 233     233   696 my $self = shift;
54 233 100       480 $self->{$key} = $_[0] if @_;
55 233         583 return $self->{$key};
56             }
57             }
58              
59             =head2 new
60              
61             tie %hasha, 'XML::PSAX::TieAttrs', \%hash1, default=>;
62              
63             =cut
64              
65             sub new {
66 5     5 1 8 my $class = shift;
67 5 50       15 $class = ref $class if ref $class;
68 5   50     15 my $orig_hash = shift || {};
69 5         18 my %props = @_;
70 5         15 my $self = bless( \%props, $class );
71 5         18 $self->_orig_hash($orig_hash);
72              
73             #set filters by
74 5   100     17 my $field_name = $props{by} || 'Name';
75 5   100     15 my $value = $props{value} || '';
76 5         26 $self->_default( [ $field_name, $value ] );
77              
78             #setup template
79 5   100     26 $self->_template( $props{template} || {} );
80 5         18 return $self;
81             }
82              
83             sub get_by_filter {
84 42     42 0 54 my $self = shift;
85 42         46 my $flocal_name = shift;
86 42         74 my $ahash = $self->_orig_hash;
87 42         62 my %res = ();
88 42         39 my ( $field_name, $value ) = @{ $self->_default() };
  42         144  
89 42         61 my $i = -1;
90 42         68 foreach my $val (@$ahash) {
91 145         129 $i++;
92 145 100       303 next unless defined( $val->{$field_name} );
93 125 100       315 next unless $val->{$field_name} eq $value;
94 87 100 100     336 next if defined $flocal_name && $val->{LocalName} ne $flocal_name;
95 44         107 $res{$i} = $val;
96             }
97 42         155 return \%res;
98             }
99              
100             sub create_attr {
101 5     5 0 9 my $self = shift;
102 5         9 my $key = shift;
103 5         12 my %template =
104 5         7 ( %{ $self->_template() }, @{ $self->_default() }, LocalName => $key );
  5         20  
105 5         13 my $prefix = $template{Prefix};
106 5         9 my $local_name = $template{LocalName};
107 5 100       17 $template{Name} = $prefix ? "$prefix:$local_name" : $local_name;
108 5         25 return attr_from_sax2( { 1 => \%template } );
109             }
110              
111             sub DELETE {
112 5     5   505 my ( $self, $key ) = @_;
113 5         7 my ( $fkey, $fhash ) = %{ $self->get_by_filter($key) };
  5         21  
114 5 50       19 return unless $fhash;
115 5         9 my $val = $fhash->{Value};
116 5         11 my $ahash = $self->_orig_hash;
117 5         11 delete $ahash->[$fkey];
118 5         9 @{$ahash} = grep { defined } @{$ahash};
  5         12  
  18         32  
  5         8  
119 5         23 return $val;
120             }
121              
122             sub STORE {
123 12     12   1061 my ( $self, $key, $val ) = @_;
124             # warn " store: $key, $val ";
125 12         15 my ( $pkey, $fhash ) = %{ $self->get_by_filter($key) };
  12         36  
126 12 100       36 if ($fhash) {
127 6         46 $fhash->{Value} = $val;
128             }
129             else {
130 6         19 my $new_add_to_hash = $self->create_attr($key);
131 6         25 my $ahash = $self->_orig_hash;
132 6         28 while ( my ( $pkey, $pval ) = each %$new_add_to_hash ) {
133 6         8 push @{$ahash}, $pval;
  6         31  
134             }
135 6         32 $self->STORE( $key, $val );
136             }
137 12         37 return $val;
138             }
139              
140             sub FETCH {
141 23     23   114 my ( $self, $key ) = @_;
142 23         22 my $res;
143 23         25 my ( $pkey, $pval ) = %{ $self->get_by_filter($key) };
  23         50  
144 23 50       72 $res = $pval->{Value} if $pval;
145 23         72 return $res;
146             }
147              
148             sub GetKeys {
149 8     8 0 62 my $self = shift;
150 8         11 return [ map { $_->{LocalName} } values %{ $self->get_by_filter } ];
  15         68  
  8         16  
151             }
152              
153             sub TIEHASH { #shift;
154 5     5   1204 return &new(@_);
155             }
156              
157             sub FIRSTKEY {
158 10     10   2040 my ($self) = @_;
159 10         14 $self->__temp_array( [ sort { $a cmp $b } @{ $self->GetKeys() } ] );
  25         70  
  10         28  
160 10         26 shift( @{ $self->__temp_array() } );
  10         21  
161             }
162              
163             sub NEXTKEY {
164 25     25   35 my ( $self, $key ) = @_;
165 25         22 shift( @{ $self->__temp_array() } );
  25         41  
166             }
167              
168             sub EXISTS {
169 23     23   253 my ( $self, $key ) = @_;
170 23         25 my ( $pkey, $pval ) = %{ $self->get_by_filter($key) };
  23         53  
171 23         86 return defined $pval;
172             }
173              
174             sub CLEAR {
175 1     1   445 my $self = shift;
176 1         3 foreach my $key ( @{ $self->GetKeys } ) {
  1         3  
177 3         7 $self->DELETE($key);
178             }
179             }
180              
181             1;
182             __END__