File Coverage

lib/Tie/Nested.pm
Criterion Covered Total %
statement 50 60 83.3
branch 20 30 66.6
condition 5 12 41.6
subroutine 10 11 90.9
pod 0 1 0.0
total 85 114 74.5


line stmt bran cond sub pod time code
1             # Copyrights 2010 by Mark Overmeer.
2             # For other contributors see ChangeLog.
3             # See the manual pages for details on the licensing terms.
4             # Pod stripped from pm file by OODoc 1.06.
5 2     2   4509 use warnings;
  2         4  
  2         49  
6 2     2   9 use strict;
  2         3  
  2         70  
7              
8             package Tie::Nested;
9 2     2   9 use vars '$VERSION';
  2         6  
  2         123  
10             $VERSION = '0.10';
11              
12              
13 2     2   1633 use Log::Report 'tie-nested', syntax => 'SHORT';
  2         267571  
  2         16  
14 2     2   315104 use Data::Dumper;
  2         14603  
  2         1459  
15              
16              
17             sub TIEHASH(@)
18 11     11   988 { my $class = shift;
19 11 100       40 my $add = @_ % 2 ? shift : {};
20 11         64 my $self = (bless {}, $class)->init({@_} );
21 11         40 my @a = %$add;
22 11         76 tie %$add, $self->{mine};
23 11         283 $self->{data} = $add;
24 11         49 $self->STORE(shift @a, shift @a) while @a;
25 11         71 $self;
26             }
27              
28              
29             sub TIEARRAY(@)
30 0     0   0 { my $class = shift;
31 0 0       0 my $add = @_ % 2 ? shift : [];
32 0 0       0 $add = [$add] if ref $add ne 'ARRAY';
33 0         0 my $self = (bless {}, $class)->init( {@_} );
34 0         0 tie @$add, $self->{mine};
35 0         0 $self->{data} = $add;
36 0         0 $self;
37             }
38              
39             sub init($)
40 11     11 0 17 { my ($self, $args) = @_;
41              
42 11         13 my ($mine, @nest_opts);
43 11 100       41 if(my $r = $args->{recurse})
    50          
44 6 100       18 { $r = [ $r ] if ref $r ne 'ARRAY';
45 6         9 $mine = $r->[0];
46 6         14 @nest_opts = (recurse => $r);
47             }
48             elsif(my $n = $args->{nestings})
49 5 50       25 { ($mine, my @nest) = ref $n eq 'ARRAY' ? @$n : $n;
50 5 100       24 @nest_opts = (nestings => \@nest) if @nest;
51             }
52             else
53 0         0 { error __x"tie needs either 'recurse' or 'nestings' parameter";
54             }
55              
56 11 50       49 defined $mine
57             or error __x"requires a package name for the tie on the data";
58              
59 11         33 $self->{mine} = $mine;
60 11 100       33 $self->{nest} = \@nest_opts if @nest_opts;
61 11         27 $self;
62             }
63              
64             sub STORE($$$)
65 25     25   2124 { my ($self, $k, $v) = @_;
66 25         42 my $t = $self->{mine};
67 25   33     63 my $d = $self->{data} ||= $t->($k, $v);
68              
69 25 100       51 if(my $nest = $self->{nest})
70             {
71 21 100 66     166 if(ref $v eq 'HASH' && $nest->[1][0]->can('TIEHASH'))
    50 33        
72 7         49 { tie %$v, ref $self, {%$v}, @$nest;
73 7         36 return $d->{$k} = $v;
74             }
75             elsif(ref $v eq 'ARRAY' && $nest->[1][0]->can('TIEARRAY'))
76 0         0 { tie @$v, ref $self, [@$v], @$nest;
77 0         0 return $d->{$k} = $v;
78             }
79             }
80              
81 18         113 (tied %$d)->STORE($k, $v);
82             }
83              
84             my $end;
85 2     2   1270 END { $end++ }
86              
87             our $AUTOLOAD;
88             sub AUTOLOAD(@)
89 180 50   180   15109 { return if $end;
90 180         1119 $AUTOLOAD =~ s/.*\:\://;
91 180         296 my $d = shift->{data};
92 180         201 my $obj = tied %$d;
93 180 50 33     386 return if $AUTOLOAD eq 'DESTROY' && ! $obj->can('DESTROY');
94 180         561 $obj->$AUTOLOAD(@_);
95             }
96              
97             1;