File Coverage

blib/lib/Acme/Lexical/Thief.pm
Criterion Covered Total %
statement 48 49 97.9
branch 9 12 75.0
condition 1 2 50.0
subroutine 12 13 92.3
pod n/a
total 70 76 92.1


line stmt bran cond sub pod time code
1             package Acme::Lexical::Thief;
2              
3 2     2   80438 use 5.012;
  2         7  
  2         83  
4 2     2   12 use strict;
  2         4  
  2         69  
5 2     2   12 use warnings;
  2         9  
  2         80  
6 2     2   20 no warnings qw( once void uninitialized numeric );
  2         5  
  2         140  
7              
8             BEGIN {
9 2     2   11 $Acme::Lexical::Thief::AUTHORITY = 'cpan:TOBYINK';
10 2         33 $Acme::Lexical::Thief::VERSION = '0.001';
11             }
12              
13 2     2   20 use Carp;
  2         4  
  2         179  
14 2     2   2169 use Keyword::Simple ();
  2         41465  
  2         55  
15 2     2   1527 use PadWalker ();
  2         9320  
  2         71  
16 2     2   22455 use Text::Balanced ();
  2         77340  
  2         1812  
17              
18             my $KEYWORD = 'steal';
19             my $CLASS = __PACKAGE__;
20              
21             sub import
22             {
23             Keyword::Simple::define $KEYWORD, sub
24             {
25 6     6   97 my $ref = shift;
26 6         23 $$ref =~ s/^\s+//;
27              
28 6         9 my $depth = 0;
29 6 100       27 if ($$ref =~ /^((?: 0x[0-9A-F]+ | 0b[0-1]+ | 0[0-7]* | [1-9][0-9]* )\s*)/ixs)
30             {
31 2         107 $depth = eval $1;
32 2         12 substr($$ref, 0, length $1) = '';
33             }
34              
35 6         7 my $extracted;
36 6 100       13 if ($$ref =~ /^\(/)
37             {
38 2 50       7 $extracted = Text::Balanced::extract_bracketed($$ref)
39             or croak "usage: $KEYWORD (VARIABLES);";
40 2         301 $extracted =~ s/(^\(|\)$)//gs;
41             }
42             else
43             {
44 4 50       31 ($extracted, $$ref) = ($$ref =~ /^([^;]+)(;.*)$/s)
45             or croak "usage: $KEYWORD VARIABLES;";
46             }
47 6         37 (my $globs = $extracted) =~ s/[\$\%\@]/*/gs;
48 6         736 $$ref = "our($extracted); local($globs) = $CLASS\::_callback(q($extracted), $depth);$$ref";
49             }
50 2     2   45 }
51              
52             sub unimport
53             {
54 0     0   0 Keyword::Simple::undefine $KEYWORD;
55             }
56              
57             sub _callback
58             {
59 7     7   2615 my $vars = shift;
60 7   50     19 my $depth = shift // 0;
61            
62 7         57 $vars =~ s/(^\s*|\s*$)//g;
63 7         34 my @vars = split /\s*,\s*/, $vars;
64            
65 7         58 my $MY = PadWalker::peek_my($depth + 2);
66 7         43 my $OUR = PadWalker::peek_our($depth + 2);
67 8 50       262 return map {
    100          
68 7         13 exists $MY->{$_} ? $MY->{$_} :
69             exists $OUR->{$_} ? $OUR->{$_} :
70             croak "$KEYWORD($_) failed; caller has no $_ defined";
71             } @vars;
72             }
73              
74             1;
75              
76             __END__