File Coverage

blib/lib/Pad/Tie.pm
Criterion Covered Total %
statement 46 51 90.2
branch 4 6 66.6
condition 5 10 50.0
subroutine 10 13 76.9
pod 1 6 16.6
total 66 86 76.7


line stmt bran cond sub pod time code
1 2     2   27080 use strict;
  2         3  
  2         46  
2 2     2   5 use warnings;
  2         2  
  2         59  
3              
4             package Pad::Tie;
5              
6 2     2   527 use Pad::Tie::LP;
  2         4  
  2         39  
7 2     2   716 use Data::OptList;
  2         11856  
  2         9  
8 2     2   825 use Module::Pluggable require => 1;
  2         16158  
  2         9  
9 2     2   106 use Carp ();
  2         2  
  2         670  
10              
11             our $VERSION = '0.002_02';
12             my %METHOD;
13              
14             sub new {
15 1     1 1 21 my $class = shift;
16 1         2 my ($invocant, $methods) = @_;
17 1         6 $methods = Data::OptList::mkopt($methods);
18 1         66 my $self = bless {
19             invocant => $invocant,
20             methods => $methods,
21             persist => Pad::Tie::LP->new,
22             pre_call => [],
23             } => $class;
24 1         26 $self->build_context;
25             #tie %{ $self->{context} }, 'Pad::Tie::Context', $self;
26 1         4 $self->{persist}->set_context(_ => $self->{context});
27 1         5 return $self;
28             }
29              
30             sub build_methods {
31 1   33 1 0 4 my $class = ref($_[0]) || $_[0];
32 1         5 for my $plugin ($class->plugins) {
33 6         2027 for my $provided ($plugin->provides) {
34             #warn "$plugin provides $provided\n";
35 6         8 $METHOD{$provided} = $plugin;
36             }
37             }
38             }
39              
40             sub build_context {
41 1     1 0 2 my $self = shift;
42 1   33     5 my $methods = shift || $self->{methods};
43 1   50     6 $self->{context} ||= {};
44 1 50       6 $self->build_methods unless %METHOD;
45 1         2 for (@$methods) {
46 6         8 my ($method_personality, $plugin_arg) = @$_;
47             Carp::confess "unhandled method personality: $method_personality"
48 6 50       10 unless $METHOD{$method_personality};
49 6         6 my $plugin = $METHOD{$method_personality};
50             my $rv = $plugin->$method_personality(
51             $self->{context},
52 6   100     14 $self->{invocant}, $plugin_arg,
53             ) || {};
54             # XXX I hate this but I can't think of a better way to do it offhand.
55             # if you aren't me, don't use this; talk to me about it instead. -- hdp,
56             # 2007-04-24
57 6 100       30 if ($rv->{pre_call}) {
58 1         1 push @{ $self->{pre_call} }, @{ $rv->{pre_call} };
  1         3  
  1         2  
59             }
60             }
61             }
62              
63             sub clone {
64 0     0 0 0 my ($self, $invocant) = @_;
65             # XXX validate $invocant?
66             # XXX does 'persist' need to be duplicated also?
67             # I don't think it has any permanent state that is interesting
68 0         0 return bless {
69             %$self,
70             invocant => $invocant,
71             } => ref($self),
72             }
73              
74             sub call {
75 6     6 0 5234 my ($self, $code, @args) = @_;
76 6         6 $_->($self, $code, \@args) for @{ $self->{pre_call} };
  6         23  
77 6         49 return $self->{persist}->call($code, @args);
78             }
79              
80             sub wrap {
81 0     0 0   my ($self, $code) = @_;
82 0     0     return sub { $self->call($code, @_) };
  0            
83             }
84              
85             1;
86              
87             __END__