File Coverage

blib/lib/Catmandu/Emit.pm
Criterion Covered Total %
statement 85 102 83.3
branch 15 28 53.5
condition 2 5 40.0
subroutine 21 23 91.3
pod n/a
total 123 158 77.8


line stmt bran cond sub pod time code
1              
2             # eval context ->
3             use Catmandu::Sane;
4 147     147   77535  
  147         334  
  147         1102  
5             our $VERSION = '1.2018';
6              
7             use Catmandu::Util qw(:is :string require_package);
8 147     147   1018 use Clone qw(clone);
  147         334  
  147         40567  
9 147     147   1031 require Catmandu; # avoid circular dependencies
  147         312  
  147         12930  
10              
11             eval $_[0];
12             }
13 1100     1100   212458  
14             # <- eval context
15              
16             use B ();
17             use Moo::Role;
18 147     147   1063  
  147         337  
  147         2813  
19 147     147   764 # global state ->
  147         326  
  147         1186  
20             state $reject = {};
21             }
22              
23 955     955   2657 state $num_labels = 0;
24             my $label = "__CATMANDU__FIX__${num_labels}";
25             $num_labels++;
26             $label;
27 960     960   1391 }
28 960         1987  
29 960         1443 state $reject_label = _generate_label;
30 960         2172 }
31              
32             state $num_vars = 0;
33             my $var = "\$__catmandu__${num_vars}";
34 503     503   1428 $num_vars++;
35             $var;
36             }
37              
38 5147     5147   9003 # <- global state
39 5147         8489  
40 5147         6172 my ($self, @args) = @_;
41 5147         9131 local $@;
42             _eval_emit($self->_emit_sub(@args)) or Catmandu::Error->throw($@);
43             }
44              
45             my ($self, $body, %opts) = @_;
46             my $captures = $opts{captures} ||= {};
47 1100     1100   13196 my $perl = "sub {";
48 1100         1978 if (my $args = $opts{args}) {
49 1100 50       2545 $perl .= 'my (' . join(', ', @$args) . ') = @_;';
50             }
51             $perl .= $body;
52             $perl .= "};";
53 1100     1100   3045 my @captured_vars = map {
54 1100   100     3341 $self->_emit_declare_vars($_,
55 1100         1570 '$_[1]->{' . $self->_emit_string($_) . '}');
56 1100 50       2347 } keys %$captures;
57 1100         3235 $perl = join('', @captured_vars, $perl);
58              
59 1100         2095 return $perl, $captures;
60 1100         1803 }
61              
62 1100         2883 my ($self, $var, $val) = @_;
  1910         3541  
63             $var = "(" . join(", ", @$var) . ")" if is_array_ref($var);
64             $val = "(" . join(", ", @$val) . ")" if is_array_ref($val);
65 1100         2965 if (defined $val) {
66             return "my ${var} = ${val};";
67 1100         3592 }
68             "my ${var};";
69             }
70              
71 2592     2592   4429 my ($self, $test, $pass, $fail) = @_;
72 2592 50       5488 "if (${test}) {${pass}} else {${fail}}";
73 2592 50       4463 }
74 2592 50       4123  
75 2592         8686 my ($self, $sub_var, @args) = @_;
76             "${sub_var}->(" . join(', ', @args) . ")";
77 0         0 }
78              
79             my ($self, $var, $cb) = @_;
80             my $perl = "";
81 145     145   358 my $i = $self->_generate_var;
82 145         669  
83             # loop backwards so that deletions are safe
84             $perl .= "for (my ${i} = \@{${var}} - 1; ${i} >= 0; ${i}--) {";
85             $perl .= $cb->("${var}->[${i}]", up_var => $var, index => $i);
86 702     702   2408 $perl .= "}";
87 702         2927 $perl;
88             }
89              
90             my ($self, $var, $cb) = @_;
91 37     37   126 my $perl = "";
92 37         80 my $k = $self->generate_var;
93 37         104  
94             $perl .= "for my ${k} (keys(\%{${var}})) {";
95             $perl .= $cb->("${var}->{${k}}", up_var => $var, key => $k);
96 37         186 $perl .= "}";
97 37         270 $perl;
98 37         98 }
99 37         109  
100             my ($self, $var, $cb_var, %opts) = @_;
101             my $val_var = $self->_generate_var;
102             my $cancel_var = $self->_generate_var;
103 0     0   0 my $delete_var = $self->_generate_var;
104 0         0 my $perl = "";
105 0         0 $perl
106             .= "my (${val_var}, ${cancel_var}, ${delete_var}) = ${cb_var}->(${var});";
107 0         0 $perl .= "if (${delete_var}) {";
108 0         0 $perl .= $self->_emit_delete(%opts);
109 0         0 $perl .= "} elsif (!${cancel_var}) {";
110 0         0 $perl .= $self->_emit_assign($var, $val_var, %opts);
111             $perl .= "}";
112             $perl;
113             }
114 169     169   529  
115 169         389 my ($self, $var, $val, %opts) = @_;
116 169         387 my $l_var = $var;
117 169         340 if (my $up_var = $opts{up_var}) {
118 169         269 if (defined(my $key = $opts{key})) {
119 169         614 $l_var = "${up_var}->{${key}}";
120             }
121 169         380 elsif (defined(my $index = $opts{index})) {
122 169         543 $l_var = "${up_var}->[${index}]";
123 169         468 }
124 169         518 else {
125 169         291 Catmandu::BadArg->throw('up_var without key or index');
126 169         893 }
127             }
128             "${l_var} = ${val};";
129             }
130 726     726   1636  
131 726         1028 my ($self, %opts) = @_;
132 726 100       1707 my $up_var = $opts{up_var};
133 167 100       445 if (!defined($up_var)) {
    50          
134 155         464  
135             # TODO deleting the root object is equivalent to reject
136             $self->_emit_reject;
137 12         38 }
138             elsif (defined(my $key = $opts{key})) {
139             "delete ${up_var}->{${key}}";
140 0         0 }
141             elsif (defined(my $idx = $opts{index})) {
142             "splice(\@{${up_var}}, ${idx}, 1)";
143 726         2703 }
144             else {
145             Catmandu::BadArg->throw('up_var without key or index');
146             }
147 169     169   473 }
148 169         301  
149 169 100       628 my ($self, $val) = @_;
    100          
    50          
150              
151             ## undef
152 2         13 return 'undef' unless defined $val;
153              
154             ## numbers
155 155         593 # we don't quote ints and floats unless there are leading
156             # (and for floats trailing) zero's
157             if (is_integer($val)) {
158 12         51 return $val;
159             }
160             if (is_float($val) && $val !~ /0$/) {
161 0         0 return $val;
162             }
163              
164             ## strings
165             $self->_emit_string($val);
166 0     0   0 }
167              
168             my ($self, $str) = @_;
169 0 0       0 B::perlstring($str);
170             }
171              
172             my ($self) = @_;
173             'goto ' . $self->_reject_label . ';';
174 0 0       0 }
175 0         0  
176             1;
177 0 0 0     0  
178 0         0  
179             =pod
180              
181             =head1 NAME
182 0         0  
183             Catmandu::Emit - Role with helper methods for code emitting
184              
185             =cut