File Coverage

blib/lib/Devel/Trace/Subs.pm
Criterion Covered Total %
statement 73 101 72.2
branch 26 34 76.4
condition 21 30 70.0
subroutine 14 19 73.6
pod 4 4 100.0
total 138 188 73.4


line stmt bran cond sub pod time code
1             package Devel::Trace::Subs;
2 3     3   214750 use 5.008;
  3         28  
3 3     3   16 use strict;
  3         4  
  3         55  
4 3     3   12 use warnings;
  3         5  
  3         72  
5              
6 3     3   1625 use Data::Dumper;
  3         18029  
  3         201  
7 3     3   1142 use Devel::Trace::Subs::HTML qw(html);
  3         9  
  3         204  
8 3     3   1330 use Devel::Trace::Subs::Text qw(text);
  3         8  
  3         168  
9 3     3   21 use Exporter;
  3         5  
  3         72  
10 3     3   3162 use Storable;
  3         9699  
  3         210  
11 3     3   1585 use Symbol qw(delete_package);
  3         2327  
  3         3273  
12              
13             our $VERSION = '0.24';
14              
15             our @ISA = qw(Exporter);
16             our @EXPORT_OK = qw(
17             trace
18             trace_dump
19             install_trace
20             remove_trace
21             );
22              
23             $SIG{INT} = sub { 'this ensures END runs if ^C is pressed'; };
24              
25             sub trace {
26              
27 14 100   14 1 70434 return unless $ENV{DTS_ENABLE};
28              
29 13         42 my $flush_flow = $ENV{DTS_FLUSH_FLOW};
30              
31 13         53 _env();
32              
33 13         38 my $data = _store();
34              
35 13         107 my $flow_count = ++$ENV{DTS_FLOW_COUNT};
36              
37 13   50     115 my $flow = {
38             name => $flow_count,
39             value => (caller(1))[3] || 'main()'
40             };
41              
42 13         30 push @{$data->{flow}}, $flow;
  13         50  
43              
44 13   50     25 push @{$data->{stack}}, {
  13   50     204  
      50        
      50        
      50        
45             in => (caller(1))[3] || '-',
46             package => (caller(1))[0] || '-',
47             sub => (caller(2))[3] || '-',
48             filename => (caller(1))[1] || '-',
49             line => (caller(1))[2] || '-',
50             };
51              
52 13         35 _store($data);
53              
54 13 100       3873 if ($flush_flow){
55 1         11 print "\n** $flow->{name} :: $flow->{value} **\n";
56             }
57              
58 13 100       144 if (defined wantarray){
59 1         5 return $data;
60             }
61             }
62             sub trace_dump {
63              
64 11 100   11 1 629 if (! $ENV{DTS_PID}){
65 1         9 die "\nCan't call trace_dump() without calling trace()\n\n" .
66             'Make sure to set $ENV{DTS_ENABLE} = 1;' . "\n\n";
67             }
68              
69 10         60 my %p = @_;
70              
71 10         24 my $want = $p{want};
72 10         24 my $out_type = $p{type};
73 10         23 my $file = $p{file};
74              
75 10         23 my $data = _store();
76              
77 10 100 100     61 if ($want && $want eq 'stack'){
78 3 100 100     18 if ($out_type && $out_type eq 'html') {
79             html(
80             file => $file,
81             want => $want,
82             data => $data->{stack}
83 1         9 );
84             }
85             else {
86             text(
87             want => 'stack',
88             data => $data->{stack},
89 2         17 file => $file
90             );
91             }
92             }
93 10 100 100     13808 if ($want && $want eq 'flow'){
94 3 100 100     20 if ($out_type && $out_type eq 'html') {
95             html(
96             file => $file,
97             want => $want,
98             data => $data->{flow}
99 1         10 );
100             }
101             else {
102             text(
103             want => 'flow',
104             data => $data->{flow},
105 2         16 file => $file
106             );
107             }
108             }
109 10 100       9858 if (! $want){
110 4 100 100     21 if ($out_type && $out_type eq 'html') {
111 1         10 html(
112             file => $file,
113             data => $data
114             );
115             }
116             else {
117             text(
118             data => {
119             flow => $data->{flow},
120             stack => $data->{stack}
121             },
122 3         31 file => $file
123             );
124             }
125             }
126             }
127             sub install_trace {
128              
129 0     0 1 0 eval {
130 0         0 require Devel::Examine::Subs;
131 0         0 Devel::Examine::Subs->import();
132             };
133              
134 0 0       0 $@ = 1 if $ENV{EVAL_TEST}; # for test coverage
135              
136 0 0       0 if ($@){
137 0         0 die "Devel::Examine::Subs isn't installed. Can't run install_trace(): $@";
138             }
139              
140 0         0 my %p = @_;
141              
142 0         0 my $file = $p{file};
143 0         0 my $extensions = $p{extensions};
144 0         0 my $inject = $p{inject};
145              
146 0         0 my $des_use = Devel::Examine::Subs->new(file => $file,);
147              
148 0         0 remove_trace(file => $file);
149              
150             # this is a DES pre_proc
151              
152 0         0 $des_use->inject(inject_use => _inject_use());
153              
154 0         0 my $des = Devel::Examine::Subs->new(
155             file => $file,
156             extensions => $extensions,
157             );
158              
159 0   0     0 $inject = $p{inject} || _inject_code();
160              
161 0         0 $des->inject(
162             inject_after_sub_def => $inject,
163             );
164            
165             }
166             sub remove_trace {
167            
168 0     0 1 0 eval {
169 0         0 require Devel::Examine::Subs;
170 0         0 Devel::Examine::Subs->import();
171             };
172              
173 0 0       0 $@ = 1 if $ENV{EVAL_TEST}; # for test coverage
174              
175 0 0       0 if ($@){
176 0         0 die "Devel::Examine::Subs isn't installed. Can't run remove_trace(): $@";
177             }
178            
179 0         0 my %p = @_;
180 0         0 my $file = $p{file};
181              
182 0         0 my $des = Devel::Examine::Subs->new( file => $file );
183              
184 0         0 $des->remove(delete => [qr/injected by Devel::Trace::Subs/]);
185             }
186             sub _inject_code {
187             return [
188 0     0   0 'trace() if $ENV{DTS_ENABLE}; # injected by Devel::Trace::Subs',
189             ];
190             }
191             sub _inject_use {
192             return [
193 0     0   0 'use Devel::Trace::Subs qw(trace trace_dump); ' .
194             '# injected by Devel::Trace::Subs',
195             ];
196             }
197             sub _env {
198              
199 13     13   35 my $pid = $$;
200 13         55 $ENV{DTS_PID} = $pid;
201              
202 13         29 return $pid;
203             }
204             sub _store {
205              
206 38     38   738 my ($data) = @_;
207              
208 38         163 my $store = "DTS_" . join('_', ($$ x 3)) . ".dat";
209              
210 38         128 $ENV{DTS_STORE} = $store;
211              
212 38         46 my $struct;
213              
214 38 100       575 if (-f $store){
215 34         159 $struct = retrieve($store);
216             }
217             else {
218 4         11 $struct = {};
219             }
220              
221 38 100       4492 return $struct if ! $data;
222              
223 14         66 store($data, $store);
224              
225             }
226       0     sub _fold_placeholder {};
227              
228             END {
229 3 100   3   13279 unlink $ENV{DTS_STORE} if $ENV{DTS_STORE};
230             }
231              
232             __END__