File Coverage

blib/lib/dan.pm
Criterion Covered Total %
statement 65 70 92.8
branch 16 20 80.0
condition 14 20 70.0
subroutine 12 14 85.7
pod 1 6 16.6
total 108 130 83.0


line stmt bran cond sub pod time code
1             package dan;
2              
3 7     7   7700 use 5.009005;
  7         21  
  7         248  
4 7     7   34 use strict;
  7         22  
  7         301  
5 7     7   32 use warnings;
  7         11  
  7         228  
6              
7 7     7   91635 use Encode qw(find_encoding);
  7         217512  
  7         5910  
8              
9             our $VERSION = '0.551.2';
10              
11             our $SINGLETON = bless { code => {} }, __PACKAGE__;
12              
13             sub croak {
14 0     0 0 0 require Carp;
15 0         0 Carp::croak(__PACKAGE__ . ": @_");
16             }
17              
18             my $LATIN1 = find_encoding('iso-8859-1')
19             or croak("Can't load latin-1");
20              
21             my $DEFAULT_ENCODING;
22             my $DEFAULT_UTF8HINTBITS;
23             my $utf8_hint_bits = 0x00800000;
24             my $is_DanThe;
25              
26             sub import {
27 12     12   104 my($class, %opts) = @_;
28              
29 12 100 66     54 if (exists $opts{the} && !$is_DanThe) {
30 1 50   1   61 eval "package the; sub Dan { shift; return wantarray ? \@_ : \$_[0] } 1;";
  1         568  
  1         34  
31 1         2 $is_DanThe++;
32 1         1628 return;
33             }
34              
35 11 100 100     76 if (ref($opts{cat_decode} || '') eq 'CODE' && ! exists $opts{decode}) {
      66        
36 2     1   7 $opts{decode} = sub { shift };
  1         58  
37             }
38              
39             # set hinthash
40 11         43 $^H{$class} = 'dan';
41              
42             # set option
43 11         20 my $pkg = caller;
44 11         48 $SINGLETON->{code}->{$pkg} = \%opts;
45              
46             # swapping to utf8 hint bits
47 11         15 $DEFAULT_UTF8HINTBITS = 0;
48 11 100 66     36 if ($opts{force} && $^H & $utf8_hint_bits) {
49 1         1 $DEFAULT_UTF8HINTBITS = 1;
50 1         3 $^H &= ~$utf8_hint_bits;
51             }
52              
53             # swapping to encoding
54 11         19 $DEFAULT_ENCODING = ${^ENCODING};
55 11         175 ${^ENCODING} = $SINGLETON;
56             }
57              
58             sub unimport {
59 6     6   30 my $class = shift;
60 6         16 undef $^H{$class};
61 6         10 my $pkg = caller;
62 6         18 delete $SINGLETON->{code}->{$pkg};
63              
64 6 50       16 if ($DEFAULT_UTF8HINTBITS) {
65 0         0 $DEFAULT_UTF8HINTBITS = 0;
66 0         0 $^H |= $utf8_hint_bits;
67             }
68 6   66     86 ${^ENCODING} = $DEFAULT_ENCODING || ${^ENCODING};
69             }
70              
71              
72             sub is_dan {
73 2499   50 2499 0 8518 my $level = $_[1] // 1;
74 2499         17271 my $hinthash = (caller($level))[10];
75 2499         6595 $hinthash->{"" . __PACKAGE__};
76             }
77              
78             sub run {
79 24     24 0 50 my($self, $mode, $str, %opts) = @_;
80 24   50     82 my $level = $opts{level} // 1;
81 24         100 my $pkg = (caller($level))[0];
82 24   100     132 my $code = ($SINGLETON->{code}->{$pkg} || {})->{$mode} || '';
83 24 50       56 return $code if $opts{wantcode};
84              
85 24 100       73 return '' unless ref($code) eq 'CODE';
86 8         34 return $code->($str);
87             }
88              
89             # for DATA / END section
90 0     0 0 0 sub name { $LATIN1->name }
91              
92             sub decode {
93 2460     2460 0 40157 my $self = shift;
94 2460 100       3634 if ($self->is_dan) {
95 1         2 my($str) = @_;
96 1         3 $self->run( decode => $str );
97             } else {
98 2459         8772 $LATIN1->decode(@_);
99             }
100             }
101              
102             sub cat_decode {
103 39     39 1 67 my $self = shift;
104              
105 39 100       68 if ($self->is_dan) {
106 23         43 my(undef, undef, $idx, $quot) = @_;
107 23         41 my ( $rdst, $rsrc, $rpos ) = \@_[ 0, 1, 2 ];
108 23         32 my $pos = $idx;
109 23         91 while ((my $tmp = index $$rsrc, $quot, $pos) > 0) {
110 23         26 $pos = $tmp + 1;
111 23 50       84 last unless substr($$rsrc, $tmp - 1, 1) eq "\\";
112             }
113 23         33 $$rpos = $pos;
114              
115 23         35 my $capt = substr($$rsrc, $idx, ($pos - $idx) - 1);
116 23         47 $$rdst = $self->run( cat_decode => $capt ) . $quot;
117 23         3516 1;
118             } else {
119 16         5702 $LATIN1->cat_decode(@_);
120             }
121             }
122              
123             1;
124             __END__