line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
=head1 NAME |
2
|
|
|
|
|
|
|
|
3
|
|
|
|
|
|
|
Devel::PerlySense::Project - A Project root |
4
|
|
|
|
|
|
|
|
5
|
|
|
|
|
|
|
=head1 SYNOPSIS |
6
|
|
|
|
|
|
|
|
7
|
|
|
|
|
|
|
|
8
|
|
|
|
|
|
|
|
9
|
|
|
|
|
|
|
|
10
|
|
|
|
|
|
|
=head1 DESCRIPTION |
11
|
|
|
|
|
|
|
|
12
|
|
|
|
|
|
|
A Project describes the root directory of a source tree. |
13
|
|
|
|
|
|
|
|
14
|
|
|
|
|
|
|
A Project has configuration settings. |
15
|
|
|
|
|
|
|
|
16
|
|
|
|
|
|
|
=cut |
17
|
|
|
|
|
|
|
|
18
|
|
|
|
|
|
|
|
19
|
|
|
|
|
|
|
|
20
|
|
|
|
|
|
|
|
21
|
|
|
|
|
|
|
|
22
|
68
|
|
|
68
|
|
2958
|
use strict; |
|
68
|
|
|
|
|
78
|
|
|
68
|
|
|
|
|
1559
|
|
23
|
68
|
|
|
68
|
|
287
|
use warnings; |
|
68
|
|
|
|
|
67
|
|
|
68
|
|
|
|
|
2327
|
|
24
|
68
|
|
|
68
|
|
1901
|
use utf8; |
|
68
|
|
|
|
|
92
|
|
|
68
|
|
|
|
|
2550
|
|
25
|
|
|
|
|
|
|
|
26
|
|
|
|
|
|
|
package Devel::PerlySense::Project; |
27
|
|
|
|
|
|
|
$Devel::PerlySense::Project::VERSION = '0.0218'; |
28
|
|
|
|
|
|
|
|
29
|
|
|
|
|
|
|
|
30
|
68
|
|
|
68
|
|
3217
|
use Spiffy -Base; |
|
68
|
|
|
|
|
8302
|
|
|
68
|
|
|
|
|
301
|
|
31
|
68
|
|
|
68
|
|
135585
|
use Carp; |
|
68
|
|
|
68
|
|
81
|
|
|
68
|
|
|
68
|
|
1060
|
|
|
68
|
|
|
|
|
191
|
|
|
68
|
|
|
|
|
71
|
|
|
68
|
|
|
|
|
1261
|
|
|
68
|
|
|
|
|
193
|
|
|
68
|
|
|
|
|
69
|
|
|
68
|
|
|
|
|
2755
|
|
32
|
68
|
|
|
68
|
|
213
|
use Data::Dumper; |
|
68
|
|
|
|
|
67
|
|
|
68
|
|
|
|
|
1867
|
|
33
|
68
|
|
|
68
|
|
207
|
use File::Basename; |
|
68
|
|
|
|
|
68
|
|
|
68
|
|
|
|
|
2312
|
|
34
|
68
|
|
|
68
|
|
881
|
use Path::Class; |
|
68
|
|
|
|
|
52876
|
|
|
68
|
|
|
|
|
2095
|
|
35
|
68
|
|
|
68
|
|
28452
|
use File::Slurp; |
|
68
|
|
|
|
|
462721
|
|
|
68
|
|
|
|
|
3835
|
|
36
|
68
|
|
|
68
|
|
27601
|
use File::chdir; |
|
68
|
|
|
|
|
84538
|
|
|
68
|
|
|
|
|
5244
|
|
37
|
68
|
|
|
68
|
|
2066
|
use File::Find::Rule; |
|
68
|
|
|
|
|
21651
|
|
|
68
|
|
|
|
|
567
|
|
38
|
68
|
|
|
68
|
|
34538
|
use Perl::Critic 1.105; |
|
68
|
|
|
|
|
40890690
|
|
|
68
|
|
|
|
|
3233
|
|
39
|
68
|
|
|
68
|
|
504
|
use List::MoreUtils qw/ uniq /; |
|
68
|
|
|
|
|
93
|
|
|
68
|
|
|
|
|
599
|
|
40
|
|
|
|
|
|
|
|
41
|
68
|
|
|
68
|
|
25511
|
use Devel::PerlySense; |
|
68
|
|
|
|
|
100
|
|
|
68
|
|
|
|
|
676
|
|
42
|
68
|
|
|
68
|
|
15787
|
use Devel::PerlySense::Util; |
|
68
|
|
|
|
|
96
|
|
|
68
|
|
|
|
|
3684
|
|
43
|
68
|
|
|
68
|
|
277
|
use Devel::PerlySense::Util::Log; |
|
68
|
|
|
|
|
88
|
|
|
68
|
|
|
|
|
2518
|
|
44
|
68
|
|
|
68
|
|
24708
|
use Devel::PerlySense::Config::Project::Default; |
|
68
|
|
|
|
|
124
|
|
|
68
|
|
|
|
|
407
|
|
45
|
|
|
|
|
|
|
|
46
|
|
|
|
|
|
|
|
47
|
|
|
|
|
|
|
|
48
|
|
|
|
|
|
|
|
49
|
|
|
|
|
|
|
|
50
|
|
|
|
|
|
|
=head1 PROPERTIES |
51
|
|
|
|
|
|
|
|
52
|
|
|
|
|
|
|
=head2 dirProject |
53
|
|
|
|
|
|
|
|
54
|
|
|
|
|
|
|
The effective project root dir. |
55
|
|
|
|
|
|
|
|
56
|
|
|
|
|
|
|
Readonly. |
57
|
|
|
|
|
|
|
|
58
|
|
|
|
|
|
|
=cut |
59
|
1995
|
|
|
1995
|
1
|
7771
|
sub dirProject { |
60
|
|
|
|
|
|
|
return |
61
|
1995
|
|
66
|
|
|
27386
|
$self->dirProjectExplicitDir || |
62
|
|
|
|
|
|
|
$self->dirProjectImplicitUse || |
63
|
|
|
|
|
|
|
$self->dirProjectImplicitDir; |
64
|
|
|
|
|
|
|
} |
65
|
|
|
|
|
|
|
|
66
|
|
|
|
|
|
|
|
67
|
|
|
|
|
|
|
|
68
|
|
|
|
|
|
|
|
69
|
|
|
|
|
|
|
|
70
|
|
|
|
|
|
|
=head2 dirProjectExplicitDir |
71
|
|
|
|
|
|
|
|
72
|
|
|
|
|
|
|
If known, the root dir made explicit by the existence of a project |
73
|
|
|
|
|
|
|
directory and config, else "" |
74
|
|
|
|
|
|
|
|
75
|
|
|
|
|
|
|
Default: "" |
76
|
|
|
|
|
|
|
|
77
|
|
|
|
|
|
|
=cut |
78
|
|
|
|
|
|
|
field "dirProjectExplicitDir" => ""; |
79
|
|
|
|
|
|
|
|
80
|
|
|
|
|
|
|
|
81
|
|
|
|
|
|
|
|
82
|
|
|
|
|
|
|
|
83
|
|
|
|
|
|
|
|
84
|
|
|
|
|
|
|
=head2 dirProjectImplicitUse |
85
|
|
|
|
|
|
|
|
86
|
|
|
|
|
|
|
If known, the root dir indicated by a found used module, else "". |
87
|
|
|
|
|
|
|
|
88
|
|
|
|
|
|
|
Default: "" |
89
|
|
|
|
|
|
|
|
90
|
|
|
|
|
|
|
=cut |
91
|
|
|
|
|
|
|
field "dirProjectImplicitUse" => ""; |
92
|
|
|
|
|
|
|
|
93
|
|
|
|
|
|
|
|
94
|
|
|
|
|
|
|
|
95
|
|
|
|
|
|
|
|
96
|
|
|
|
|
|
|
|
97
|
|
|
|
|
|
|
=head2 dirProjectImplicitDir |
98
|
|
|
|
|
|
|
|
99
|
|
|
|
|
|
|
If known, the root dir indicated by the presence of "lib" or "t", else "". |
100
|
|
|
|
|
|
|
|
101
|
|
|
|
|
|
|
Default: "" |
102
|
|
|
|
|
|
|
|
103
|
|
|
|
|
|
|
=cut |
104
|
|
|
|
|
|
|
field "dirProjectImplicitDir" => ""; |
105
|
|
|
|
|
|
|
|
106
|
|
|
|
|
|
|
|
107
|
|
|
|
|
|
|
|
108
|
|
|
|
|
|
|
|
109
|
|
|
|
|
|
|
|
110
|
|
|
|
|
|
|
=head2 oConfig |
111
|
|
|
|
|
|
|
|
112
|
|
|
|
|
|
|
A Config::Project object with the current Project Config. This gets |
113
|
|
|
|
|
|
|
loaded if there is a config file available when the Project is |
114
|
|
|
|
|
|
|
identified. |
115
|
|
|
|
|
|
|
|
116
|
|
|
|
|
|
|
Default: An Config::Project::Default object |
117
|
|
|
|
|
|
|
|
118
|
|
|
|
|
|
|
=cut |
119
|
|
|
|
|
|
|
field "oConfig" => Devel::PerlySense::Config::Project::Default->new(); |
120
|
|
|
|
|
|
|
|
121
|
|
|
|
|
|
|
|
122
|
|
|
|
|
|
|
|
123
|
|
|
|
|
|
|
|
124
|
|
|
|
|
|
|
|
125
|
|
|
|
|
|
|
=head2 rhConfig |
126
|
|
|
|
|
|
|
|
127
|
|
|
|
|
|
|
The actual hashref with config values. |
128
|
|
|
|
|
|
|
|
129
|
|
|
|
|
|
|
Readonly (that includes the entire data structure). |
130
|
|
|
|
|
|
|
|
131
|
|
|
|
|
|
|
=cut |
132
|
1366
|
|
|
1366
|
1
|
7408
|
sub rhConfig { |
133
|
1366
|
|
|
|
|
18145
|
return $self->oConfig->rhConfig; |
134
|
|
|
|
|
|
|
} |
135
|
|
|
|
|
|
|
|
136
|
|
|
|
|
|
|
|
137
|
|
|
|
|
|
|
|
138
|
|
|
|
|
|
|
|
139
|
|
|
|
|
|
|
|
140
|
|
|
|
|
|
|
=head2 oPerlySense |
141
|
|
|
|
|
|
|
|
142
|
|
|
|
|
|
|
Devel::PerlySense object. |
143
|
|
|
|
|
|
|
|
144
|
|
|
|
|
|
|
=cut |
145
|
|
|
|
|
|
|
field "oPerlySense" => undef; |
146
|
|
|
|
|
|
|
|
147
|
|
|
|
|
|
|
|
148
|
|
|
|
|
|
|
|
149
|
|
|
|
|
|
|
|
150
|
|
|
|
|
|
|
|
151
|
|
|
|
|
|
|
=head2 nameVcs |
152
|
|
|
|
|
|
|
|
153
|
|
|
|
|
|
|
The name of the Version Control system for the project. |
154
|
|
|
|
|
|
|
|
155
|
|
|
|
|
|
|
Readonly. Currently supported: |
156
|
|
|
|
|
|
|
|
157
|
|
|
|
|
|
|
git |
158
|
|
|
|
|
|
|
svn |
159
|
|
|
|
|
|
|
none |
160
|
|
|
|
|
|
|
|
161
|
|
|
|
|
|
|
In that order, so that if there's a Git repo on top of a SVN repo, git |
162
|
|
|
|
|
|
|
is found. |
163
|
|
|
|
|
|
|
|
164
|
|
|
|
|
|
|
=cut |
165
|
1
|
|
|
1
|
1
|
9
|
sub nameVcs { |
166
|
|
|
|
|
|
|
|
167
|
|
|
|
|
|
|
#Git |
168
|
1
|
50
|
|
|
|
14
|
$self->oPerlySense->dirFindLookingAround( |
169
|
|
|
|
|
|
|
".git", |
170
|
|
|
|
|
|
|
$self->dirProject, |
171
|
|
|
|
|
|
|
["."], |
172
|
|
|
|
|
|
|
) and return("git"); |
173
|
|
|
|
|
|
|
|
174
|
|
|
|
|
|
|
#Subversion |
175
|
1
|
50
|
|
|
|
4
|
-d dir($self->dirProject, ".svn") and return("svn"); |
176
|
|
|
|
|
|
|
|
177
|
1
|
|
|
|
|
115
|
return("none"); |
178
|
|
|
|
|
|
|
} |
179
|
|
|
|
|
|
|
|
180
|
|
|
|
|
|
|
|
181
|
|
|
|
|
|
|
|
182
|
|
|
|
|
|
|
|
183
|
|
|
|
|
|
|
|
184
|
|
|
|
|
|
|
=head1 CLASS METHODS |
185
|
|
|
|
|
|
|
|
186
|
|
|
|
|
|
|
=head2 newFromLocation(file => $file, dir => $dir, oPerlySense => $oPs) |
187
|
|
|
|
|
|
|
|
188
|
|
|
|
|
|
|
Create new Project given either $file, or $dir. |
189
|
|
|
|
|
|
|
|
190
|
|
|
|
|
|
|
First, search for an explicit project root directory, then try to find |
191
|
|
|
|
|
|
|
any modules used in $file (if passed), then try to find any "lib" or |
192
|
|
|
|
|
|
|
"t" directory upwards of $file or $dir. |
193
|
|
|
|
|
|
|
|
194
|
|
|
|
|
|
|
$file takes precedence over $dir if both are specified. |
195
|
|
|
|
|
|
|
|
196
|
|
|
|
|
|
|
If none if this works out, no Project can be created and undef is |
197
|
|
|
|
|
|
|
returned. |
198
|
|
|
|
|
|
|
|
199
|
|
|
|
|
|
|
Return the new object, or undef if no project could be found. |
200
|
|
|
|
|
|
|
|
201
|
|
|
|
|
|
|
=cut |
202
|
|
|
|
|
|
|
sub newFromLocation(@) { |
203
|
61
|
|
|
61
|
1
|
2555
|
my $pkg = shift; |
204
|
61
|
|
|
|
|
237
|
my ($oPerlySense) = Devel::PerlySense::Util::aNamedArg(["oPerlySense"], @_); |
205
|
61
|
|
|
|
|
150
|
my %p = @_; |
206
|
61
|
|
|
|
|
126
|
my $file = $p{file}; |
207
|
61
|
|
|
|
|
107
|
my $dir = $p{dir}; |
208
|
61
|
100
|
|
|
|
677
|
$file and $dir = dirname($file); |
209
|
61
|
50
|
|
|
|
465
|
$dir and $dir = dir($dir)->absolute; |
210
|
|
|
|
|
|
|
|
211
|
61
|
|
|
|
|
11565
|
my $oProject; |
212
|
|
|
|
|
|
|
|
213
|
61
|
100
|
66
|
|
|
193
|
$dir and $oProject = $pkg->newFindExplicit( |
214
|
|
|
|
|
|
|
dir => $dir, |
215
|
|
|
|
|
|
|
oPerlySense => $oPerlySense, |
216
|
|
|
|
|
|
|
) and return $oProject; |
217
|
|
|
|
|
|
|
|
218
|
|
|
|
|
|
|
|
219
|
|
|
|
|
|
|
#If file, look for the dir from where any package in the file can |
220
|
|
|
|
|
|
|
#be used |
221
|
53
|
100
|
66
|
|
|
291
|
if($file and my $oDocument = $oPerlySense->oDocumentParseFile($file)) { |
222
|
5
|
|
|
|
|
24
|
for my $package ($oDocument->aNamePackage) { |
223
|
2
|
|
|
|
|
66
|
my $filePackage = $oPerlySense->fileFromModule($package); |
224
|
2
|
|
|
|
|
346
|
my $dirFound = $oPerlySense->dirFindLookingAround($filePackage, $dir); |
225
|
|
|
|
|
|
|
|
226
|
2
|
50
|
|
|
|
67
|
if($dirFound) { |
227
|
2
|
|
|
|
|
6
|
my $dirProject = dir($dirFound)->parent . ""; ###TODO: if lib or bin |
228
|
2
|
|
|
|
|
176
|
return $pkg->new( |
229
|
|
|
|
|
|
|
oPerlySense => $oPerlySense, |
230
|
|
|
|
|
|
|
dirProjectImplicitUse => $dirProject, |
231
|
|
|
|
|
|
|
); |
232
|
|
|
|
|
|
|
} |
233
|
|
|
|
|
|
|
} |
234
|
|
|
|
|
|
|
} |
235
|
|
|
|
|
|
|
|
236
|
|
|
|
|
|
|
#If dir, look for dirs |
237
|
51
|
50
|
|
|
|
192
|
if($dir) { |
238
|
51
|
|
33
|
|
|
373
|
my $dirFound = |
239
|
|
|
|
|
|
|
$oPerlySense->fileFindLookingAround("lib", $dir) || |
240
|
|
|
|
|
|
|
$oPerlySense->fileFindLookingAround("t", $dir); |
241
|
|
|
|
|
|
|
|
242
|
51
|
50
|
|
|
|
5117
|
if($dirFound) { |
243
|
51
|
|
|
|
|
150
|
my $dirProject = dir($dirFound)->parent . ""; ###TODO: if lib or bin |
244
|
|
|
|
|
|
|
|
245
|
|
|
|
|
|
|
#Special case the Unix style root dir. It's never a |
246
|
|
|
|
|
|
|
#Project dir, but if often contains a lib dir and so will |
247
|
|
|
|
|
|
|
#get identified as a Project. |
248
|
|
|
|
|
|
|
# |
249
|
|
|
|
|
|
|
#If it _is_ a root dir, this can be overriden with an |
250
|
|
|
|
|
|
|
#explicit .PerlySenseProject dir. |
251
|
|
|
|
|
|
|
# |
252
|
|
|
|
|
|
|
#On Windows, the root looks like X:\, and it's not |
253
|
|
|
|
|
|
|
#entirely unlikely that a secondary drive or a SUBST drive |
254
|
|
|
|
|
|
|
#letter contains the project root. |
255
|
51
|
100
|
|
|
|
3833
|
$dirProject eq "/" and return undef; |
256
|
|
|
|
|
|
|
|
257
|
49
|
|
|
|
|
831
|
return $pkg->new( |
258
|
|
|
|
|
|
|
oPerlySense => $oPerlySense, |
259
|
|
|
|
|
|
|
dirProjectImplicitDir => $dirProject, |
260
|
|
|
|
|
|
|
); |
261
|
|
|
|
|
|
|
} |
262
|
|
|
|
|
|
|
} |
263
|
|
|
|
|
|
|
|
264
|
0
|
|
|
|
|
0
|
return(undef); |
265
|
|
|
|
|
|
|
} |
266
|
|
|
|
|
|
|
|
267
|
|
|
|
|
|
|
|
268
|
|
|
|
|
|
|
|
269
|
|
|
|
|
|
|
|
270
|
|
|
|
|
|
|
|
271
|
|
|
|
|
|
|
=head2 newFindExplicit(dir => $dir, oPerlySense => $oPs) |
272
|
|
|
|
|
|
|
|
273
|
|
|
|
|
|
|
Create new Project if there is an explicit .PerlySenseProject |
274
|
|
|
|
|
|
|
directory in the path above $dir. |
275
|
|
|
|
|
|
|
|
276
|
|
|
|
|
|
|
Return the new object, or undef if no project could be found. |
277
|
|
|
|
|
|
|
|
278
|
|
|
|
|
|
|
=cut |
279
|
|
|
|
|
|
|
sub newFindExplicit(@) { |
280
|
56
|
|
|
56
|
1
|
512
|
my $pkg = shift; |
281
|
56
|
|
|
|
|
234
|
my ($oPerlySense, $dir) = Devel::PerlySense::Util::aNamedArg(["oPerlySense", "dir"], @_); |
282
|
|
|
|
|
|
|
|
283
|
56
|
100
|
|
|
|
324
|
if(my $dirProject = $oPerlySense->dirFindLookingAround( |
284
|
|
|
|
|
|
|
".PerlySenseProject", |
285
|
|
|
|
|
|
|
$dir, |
286
|
|
|
|
|
|
|
["."], |
287
|
|
|
|
|
|
|
)) { |
288
|
8
|
|
|
|
|
280
|
return $pkg->new( |
289
|
|
|
|
|
|
|
oPerlySense => $oPerlySense, |
290
|
|
|
|
|
|
|
dirProjectExplicitDir => $dirProject, |
291
|
|
|
|
|
|
|
oConfig => Devel::PerlySense::Config::Project->new(dirRoot => $dirProject), |
292
|
|
|
|
|
|
|
); |
293
|
|
|
|
|
|
|
} |
294
|
|
|
|
|
|
|
|
295
|
48
|
|
|
|
|
400
|
return undef; |
296
|
|
|
|
|
|
|
} |
297
|
|
|
|
|
|
|
|
298
|
|
|
|
|
|
|
|
299
|
|
|
|
|
|
|
|
300
|
|
|
|
|
|
|
|
301
|
|
|
|
|
|
|
|
302
|
|
|
|
|
|
|
=head1 MEHTODS |
303
|
|
|
|
|
|
|
|
304
|
|
|
|
|
|
|
=head2 rhRunFile(file => $fileSource, [rhConfigType = DEDUCED_FROM_FILE], [ keyConfigCommand = "command" ]) |
305
|
|
|
|
|
|
|
|
306
|
|
|
|
|
|
|
Like rhRunFile0, but with what => "run". |
307
|
|
|
|
|
|
|
|
308
|
|
|
|
|
|
|
=cut |
309
|
4
|
|
|
4
|
1
|
14
|
sub rhRunFile { |
310
|
4
|
|
|
|
|
12
|
my ($file) = Devel::PerlySense::Util::aNamedArg(["file"], @_); |
311
|
4
|
|
|
|
|
9
|
my %p = @_; |
312
|
4
|
|
|
|
|
10
|
return( $self->rhRunFile0(%p, what => "run") ); |
313
|
|
|
|
|
|
|
} |
314
|
|
|
|
|
|
|
|
315
|
|
|
|
|
|
|
|
316
|
|
|
|
|
|
|
|
317
|
|
|
|
|
|
|
|
318
|
|
|
|
|
|
|
|
319
|
|
|
|
|
|
|
=head2 rhDebugFile(file => $fileSource, [rhConfigType = DEDUCED_FROM_FILE], [ keyConfigCommand = "command" ]) |
320
|
|
|
|
|
|
|
|
321
|
|
|
|
|
|
|
Like rhRunFile0, but with what => "debug". |
322
|
|
|
|
|
|
|
|
323
|
|
|
|
|
|
|
=cut |
324
|
|
|
|
|
|
|
### XXX refactor, DRY with rhRunFile |
325
|
1
|
|
|
1
|
1
|
5
|
sub rhDebugFile { |
326
|
1
|
|
|
|
|
4
|
my ($file) = Devel::PerlySense::Util::aNamedArg(["file"], @_); |
327
|
1
|
|
|
|
|
2
|
my %p = @_; |
328
|
1
|
|
|
|
|
6
|
return( $self->rhRunFile0(%p, what => "debug") ); |
329
|
|
|
|
|
|
|
} |
330
|
|
|
|
|
|
|
|
331
|
|
|
|
|
|
|
|
332
|
|
|
|
|
|
|
|
333
|
|
|
|
|
|
|
|
334
|
|
|
|
|
|
|
|
335
|
|
|
|
|
|
|
=head2 rhRunFile0(file => $fileSource, what => "run" | "debug", [rhConfigType = DEDUCED_FROM_FILE], [ keyConfigCommand = "command" ]) |
336
|
|
|
|
|
|
|
|
337
|
|
|
|
|
|
|
Figure out what type of source file $fileSource is, and how it should |
338
|
|
|
|
|
|
|
be run/debugged. |
339
|
|
|
|
|
|
|
|
340
|
|
|
|
|
|
|
The settings in the global config->{$what_file} is used to determine |
341
|
|
|
|
|
|
|
the details. |
342
|
|
|
|
|
|
|
|
343
|
|
|
|
|
|
|
The command to use is taken from |
344
|
|
|
|
|
|
|
config->{$what_file}->{$keyConfigCommand}, if that is specified, |
345
|
|
|
|
|
|
|
otherwise for "command". |
346
|
|
|
|
|
|
|
|
347
|
|
|
|
|
|
|
Return hash ref with (keys: "dir_$what_from", "command_$what", |
348
|
|
|
|
|
|
|
"type_source_file"), or die on errors (like if no Project could be |
349
|
|
|
|
|
|
|
found). |
350
|
|
|
|
|
|
|
|
351
|
|
|
|
|
|
|
dir_$what_from is an absolute directory name which should be the cwd |
352
|
|
|
|
|
|
|
when command_$what is executed. |
353
|
|
|
|
|
|
|
|
354
|
|
|
|
|
|
|
type_source_file is something like "Test", "Module". |
355
|
|
|
|
|
|
|
|
356
|
|
|
|
|
|
|
=cut |
357
|
5
|
|
|
5
|
1
|
6
|
sub rhRunFile0 { |
358
|
5
|
|
|
|
|
12
|
my ($file) = Devel::PerlySense::Util::aNamedArg(["file"], @_); |
359
|
5
|
|
|
|
|
8
|
my %p = @_; |
360
|
5
|
|
|
|
|
7
|
my $rhConfigType = $p{rhConfigType}; |
361
|
5
|
|
|
|
|
6
|
my $what = $p{what}; |
362
|
5
|
|
100
|
|
|
17
|
my $keyConfigCommand = $p{keyConfigCommand} || "command"; |
363
|
|
|
|
|
|
|
|
364
|
5
|
|
|
|
|
13
|
$file = file($file)->absolute; |
365
|
5
|
|
33
|
|
|
771
|
$rhConfigType ||= $self->rhConfigTypeForFile( |
366
|
|
|
|
|
|
|
file => $file, |
367
|
|
|
|
|
|
|
keyConfig => "${what}_file", |
368
|
|
|
|
|
|
|
); |
369
|
|
|
|
|
|
|
|
370
|
5
|
|
|
|
|
140
|
my $dirProject = dir($self->dirProject)->absolute; |
371
|
|
|
|
|
|
|
my %hTypeDirRunFrom = ( |
372
|
3
|
|
|
3
|
|
3
|
source_root_directory => sub { $dirProject }, |
373
|
2
|
|
|
2
|
|
6
|
file_directory => sub { $file->dir }, |
374
|
5
|
|
|
|
|
359
|
); |
375
|
5
|
|
|
|
|
11
|
my $typeRunFrom = $rhConfigType->{"${what}_from"}; |
376
|
5
|
50
|
|
|
|
16
|
my $rsDirRunFrom = $hTypeDirRunFrom{$typeRunFrom} or die("Invalid ${what}_from value ($typeRunFrom)\n" . Dumper($rhConfigType) . "Allowed values: (" . join(", ", (sort keys %hTypeDirRunFrom)) . ")\n"); |
377
|
5
|
|
|
|
|
8
|
my $dirRunFrom = $rsDirRunFrom->(); |
378
|
|
|
|
|
|
|
|
379
|
5
|
|
|
|
|
15
|
my @aDirIncProject = $self->aDirIncProject(dirRelativeTo => $dirRunFrom); |
380
|
5
|
|
|
|
|
9
|
my $optionInc = join(" ", map { qq|"-I$_"| } @aDirIncProject); |
|
19
|
|
|
|
|
33
|
|
381
|
|
|
|
|
|
|
|
382
|
5
|
|
|
|
|
20
|
my $fileSource = $file->relative($dirRunFrom); |
383
|
|
|
|
|
|
|
my $command |
384
|
|
|
|
|
|
|
= $rhConfigType->{ $keyConfigCommand } |
385
|
|
|
|
|
|
|
|| $rhConfigType->{command} |
386
|
5
|
50
|
33
|
|
|
592
|
or die("Could not find a config value for which 'command' to run\n"); |
387
|
5
|
|
|
|
|
13
|
my $commandRun = textRenderTemplate( |
388
|
|
|
|
|
|
|
$command, |
389
|
|
|
|
|
|
|
{ |
390
|
|
|
|
|
|
|
INC => $optionInc, |
391
|
|
|
|
|
|
|
SOURCE_FILE => $fileSource . "", |
392
|
|
|
|
|
|
|
}, |
393
|
|
|
|
|
|
|
); |
394
|
|
|
|
|
|
|
|
395
|
|
|
|
|
|
|
my $rhConfigRun = { |
396
|
|
|
|
|
|
|
"dir_${what}_from" => $dirRunFrom . "", |
397
|
|
|
|
|
|
|
"command_${what}" => $commandRun, |
398
|
|
|
|
|
|
|
type_source_file => $rhConfigType->{moniker}, |
399
|
5
|
|
|
|
|
23
|
}; |
400
|
5
|
|
|
|
|
130
|
return($rhConfigRun); |
401
|
|
|
|
|
|
|
} |
402
|
|
|
|
|
|
|
|
403
|
|
|
|
|
|
|
|
404
|
|
|
|
|
|
|
|
405
|
|
|
|
|
|
|
|
406
|
|
|
|
|
|
|
|
407
|
|
|
|
|
|
|
=head2 rhConfigTypeForFile(file => $fileSource, keyConfig => CONFIG_KEY) |
408
|
|
|
|
|
|
|
|
409
|
|
|
|
|
|
|
Return the config type hash ref (keys: command, moniker) from the ones |
410
|
|
|
|
|
|
|
available in the config. Match the $fileSource name against each rex |
411
|
|
|
|
|
|
|
in the config. |
412
|
|
|
|
|
|
|
|
413
|
|
|
|
|
|
|
Die if no configType could be identified. |
414
|
|
|
|
|
|
|
|
415
|
|
|
|
|
|
|
=cut |
416
|
19
|
|
|
19
|
1
|
891
|
sub rhConfigTypeForFile { |
417
|
19
|
|
|
|
|
56
|
my ($file, $keyConfig) = Devel::PerlySense::Util::aNamedArg(["file", "keyConfig"], @_); |
418
|
|
|
|
|
|
|
|
419
|
19
|
|
|
|
|
335
|
my $rhConfig = $self->oPerlySense->rhConfig; |
420
|
19
|
|
|
|
|
351
|
for my $rhConfigType (@{ $rhConfig->{ $keyConfig } }) { |
|
19
|
|
|
|
|
39
|
|
421
|
|
|
|
|
|
|
my $rex = $rhConfigType->{rex} |
422
|
33
|
100
|
|
|
|
66
|
or die("Missing rex key in config chunk: " . Dumper($rhConfigType)); |
423
|
|
|
|
|
|
|
|
424
|
31
|
100
|
|
|
|
25
|
eval { $file =~ /$rex/ } and return $rhConfigType; |
|
31
|
|
|
|
|
325
|
|
425
|
18
|
100
|
|
|
|
128
|
$@ and die("Invalid rex value in config chunk.\nError: $@\n" . Dumper($rhConfigType)); |
426
|
|
|
|
|
|
|
} |
427
|
|
|
|
|
|
|
|
428
|
2
|
|
|
|
|
15
|
die("No run_perl rex matched the file ($file). Please check your config\n"); |
429
|
|
|
|
|
|
|
} |
430
|
|
|
|
|
|
|
|
431
|
|
|
|
|
|
|
|
432
|
|
|
|
|
|
|
|
433
|
|
|
|
|
|
|
|
434
|
|
|
|
|
|
|
|
435
|
|
|
|
|
|
|
=head2 aDirIncProject(dirRelativeTo => $dirRelativeTo) |
436
|
|
|
|
|
|
|
|
437
|
|
|
|
|
|
|
Return array with dir objects which are the inc_dir directories in the |
438
|
|
|
|
|
|
|
config, plus the usual inc directories. They are all relative to |
439
|
|
|
|
|
|
|
$dirRelativeTo. |
440
|
|
|
|
|
|
|
|
441
|
|
|
|
|
|
|
=cut |
442
|
771
|
|
|
771
|
1
|
30373
|
sub aDirIncProject { |
443
|
771
|
|
|
|
|
2439
|
my ($dirRelativeTo) = Devel::PerlySense::Util::aNamedArg(["dirRelativeTo"], @_); |
444
|
|
|
|
|
|
|
|
445
|
771
|
|
|
|
|
1781
|
my $dirProject = dir($self->dirProject)->absolute; |
446
|
771
|
|
|
|
|
60769
|
my $dirProjectRelativeTo = $dirProject->relative( $dirRelativeTo ); |
447
|
|
|
|
|
|
|
|
448
|
|
|
|
|
|
|
###TODO: extract method for the inc_dir config entry aIncDirConfig |
449
|
771
|
50
|
|
|
|
63125
|
my @aDirIncProject = @{ $self->oPerlySense->rhConfig->{project}->{inc_dir} || [] }; |
|
771
|
|
|
|
|
13797
|
|
450
|
771
|
|
|
|
|
21916
|
my @aDirInc = (@aDirIncProject, ".", "lib"); |
451
|
|
|
|
|
|
|
|
452
|
|
|
|
|
|
|
my @aDirIncRelative = |
453
|
771
|
|
|
|
|
1119
|
map { dir($dirProjectRelativeTo, $_) . "" } |
|
1551
|
|
|
|
|
33069
|
|
454
|
|
|
|
|
|
|
@aDirInc; |
455
|
|
|
|
|
|
|
|
456
|
771
|
|
|
|
|
25405
|
return @aDirIncRelative; |
457
|
|
|
|
|
|
|
} |
458
|
|
|
|
|
|
|
|
459
|
|
|
|
|
|
|
|
460
|
|
|
|
|
|
|
|
461
|
|
|
|
|
|
|
|
462
|
|
|
|
|
|
|
|
463
|
|
|
|
|
|
|
=head2 aDirIncAbsolute() |
464
|
|
|
|
|
|
|
|
465
|
|
|
|
|
|
|
Return array with absolute dir objects which are the inc_dir |
466
|
|
|
|
|
|
|
directories in the config, plus the usual inc directories. |
467
|
|
|
|
|
|
|
|
468
|
|
|
|
|
|
|
=cut |
469
|
544
|
|
|
544
|
1
|
3048
|
sub aDirIncAbsolute { |
470
|
544
|
|
|
|
|
1269
|
my $dirProject = dir($self->dirProject)->absolute; |
471
|
|
|
|
|
|
|
|
472
|
|
|
|
|
|
|
###TODO: extract method for the inc_dir config entry aIncDirConfig |
473
|
|
|
|
|
|
|
my @aDirIncProject = @{ |
474
|
544
|
50
|
|
|
|
45081
|
$self->oPerlySense->rhConfig->{project}->{inc_dir} || [] |
|
544
|
|
|
|
|
8549
|
|
475
|
|
|
|
|
|
|
}; |
476
|
544
|
|
|
|
|
11375
|
my @aDirInc = (@aDirIncProject, ".", "lib"); |
477
|
|
|
|
|
|
|
|
478
|
|
|
|
|
|
|
my @aDirIncAbsolute = |
479
|
544
|
|
|
|
|
877
|
map { dir($dirProject, $_)->absolute . "" } |
|
1091
|
|
|
|
|
29867
|
|
480
|
|
|
|
|
|
|
@aDirInc; |
481
|
544
|
|
|
|
|
33897
|
return @aDirIncAbsolute; |
482
|
|
|
|
|
|
|
} |
483
|
|
|
|
|
|
|
|
484
|
|
|
|
|
|
|
|
485
|
|
|
|
|
|
|
|
486
|
|
|
|
|
|
|
|
487
|
|
|
|
|
|
|
|
488
|
|
|
|
|
|
|
=head2 isFileInProject(file => $file) |
489
|
|
|
|
|
|
|
|
490
|
|
|
|
|
|
|
Return true if $file is within the project root, or in any of the INC |
491
|
|
|
|
|
|
|
directories, else false. Die on errors. |
492
|
|
|
|
|
|
|
|
493
|
|
|
|
|
|
|
Test logically/structurally, not whether the file actually exists. |
494
|
|
|
|
|
|
|
|
495
|
|
|
|
|
|
|
=cut |
496
|
7
|
|
|
7
|
1
|
806
|
sub isFileInProject { |
497
|
7
|
|
|
|
|
33
|
my ($file) = Devel::PerlySense::Util::aNamedArg(["file"], @_); |
498
|
|
|
|
|
|
|
|
499
|
|
|
|
|
|
|
my @aDirInc = |
500
|
15
|
|
|
|
|
833
|
map { dir($self->dirProject, $_) } |
501
|
7
|
50
|
|
|
|
12
|
@{ $self->oPerlySense->rhConfig->{project}->{inc_dir} || [] }; |
|
7
|
|
|
|
|
175
|
|
502
|
|
|
|
|
|
|
my @aDirSourceAbsolute = |
503
|
7
|
|
|
|
|
353
|
map { dir($_)->absolute } |
|
22
|
|
|
|
|
1143
|
|
504
|
|
|
|
|
|
|
($self->dirProject, @aDirInc); |
505
|
|
|
|
|
|
|
|
506
|
|
|
|
|
|
|
###TODO: Comment out debug statements when that failing test in t/PerlySense-Project-file-in-project.t is fixed |
507
|
7
|
|
|
|
|
576
|
debug("\nTESTING WHETHER FILE\n($file) IS IN PROJECT\n(" . $self->dirProject . "),\ni.e.\n(" . join(")\n(", @aDirSourceAbsolute) . ")\n"); |
508
|
7
|
|
|
|
|
26
|
my @aDirProjectRegex = map { qr/^ \Q$_\E /x } @aDirSourceAbsolute; |
|
22
|
|
|
|
|
707
|
|
509
|
|
|
|
|
|
|
|
510
|
7
|
|
|
|
|
354
|
my $dirFileAbsolute = dir( filePathNormalize( file($file)->absolute->dir ) ); |
511
|
7
|
|
|
|
|
1158
|
debug("DIR ABSOLUTE ($dirFileAbsolute)\n"); |
512
|
|
|
|
|
|
|
|
513
|
7
|
|
|
|
|
18
|
for my $dirProject (map { dir(filePathNormalize($_)) } @aDirSourceAbsolute) { |
|
22
|
|
|
|
|
2813
|
|
514
|
16
|
|
|
|
|
3898
|
debug("Checking whether\n($dirFileAbsolute) is within\n($dirProject)\n"); |
515
|
16
|
100
|
|
|
|
78
|
$dirProject->subsumes($dirFileAbsolute) and debug("Found it"), return 1; |
516
|
|
|
|
|
|
|
} |
517
|
|
|
|
|
|
|
|
518
|
3
|
|
|
|
|
822
|
debug("FILE ($file) is NOT in the Project (" . $self->dirProject . ")\n"); |
519
|
3
|
|
|
|
|
56
|
return 0; |
520
|
|
|
|
|
|
|
} |
521
|
|
|
|
|
|
|
|
522
|
|
|
|
|
|
|
|
523
|
|
|
|
|
|
|
|
524
|
|
|
|
|
|
|
|
525
|
|
|
|
|
|
|
|
526
|
|
|
|
|
|
|
=head2 flymakeFile(file => $fileSource) |
527
|
|
|
|
|
|
|
|
528
|
|
|
|
|
|
|
Do a flymake run with $fileSource according to the flymake config and |
529
|
|
|
|
|
|
|
output the result to STDOUT and STDERR. |
530
|
|
|
|
|
|
|
|
531
|
|
|
|
|
|
|
Return 1 or die on errors (but that will look like the result of a |
532
|
|
|
|
|
|
|
failed flymake run). |
533
|
|
|
|
|
|
|
|
534
|
|
|
|
|
|
|
=cut |
535
|
|
|
|
|
|
|
|
536
|
0
|
|
|
0
|
1
|
|
sub flymakeFile { |
537
|
0
|
|
|
|
|
|
my ($file) = Devel::PerlySense::Util::aNamedArg(["file"], @_); |
538
|
|
|
|
|
|
|
|
539
|
0
|
0
|
|
|
|
|
if($self->oPerlySense->rhConfig->{external}{editor}{emacs}{flymake}{syntax}) { |
540
|
0
|
|
|
|
|
|
my $rhConfigRun = $self->rhRunFile( |
541
|
|
|
|
|
|
|
file => $file, |
542
|
|
|
|
|
|
|
rhConfigType => { |
543
|
|
|
|
|
|
|
command => q{perl -c ${INC} "${SOURCE_FILE}" 2>&1 | perl -ne " /Subroutine [\\w:]+ redefined at/ or print"}, |
544
|
|
|
|
|
|
|
moniker => "Flymake", |
545
|
|
|
|
|
|
|
rex => "", |
546
|
|
|
|
|
|
|
run_from => "file_directory", |
547
|
|
|
|
|
|
|
}, |
548
|
|
|
|
|
|
|
); |
549
|
|
|
|
|
|
|
|
550
|
0
|
|
|
|
|
|
local $CWD = $rhConfigRun->{dir_run_from}; |
551
|
0
|
|
|
|
|
|
system( $rhConfigRun->{command_run} ); |
552
|
|
|
|
|
|
|
} |
553
|
|
|
|
|
|
|
|
554
|
0
|
0
|
|
|
|
|
if($self->oPerlySense->rhConfig->{external}{editor}{emacs}{flymake}{critic}) { |
555
|
|
|
|
|
|
|
###TODO: don't run if syntax errors found |
556
|
|
|
|
|
|
|
|
557
|
0
|
|
|
|
|
|
my $fileConfigCritic = file( |
558
|
|
|
|
|
|
|
dir($self->dirProject)->absolute, ".PerlySenseProject", ".perlcritic", |
559
|
|
|
|
|
|
|
); |
560
|
|
|
|
|
|
|
|
561
|
0
|
|
|
|
|
|
my @aOption = (-profile => $fileConfigCritic . ""); |
562
|
0
|
0
|
|
|
|
|
-e $fileConfigCritic or @aOption = (); |
563
|
|
|
|
|
|
|
|
564
|
0
|
|
|
|
|
|
my $oCritic = Perl::Critic->new(@aOption); |
565
|
|
|
|
|
|
|
|
566
|
0
|
|
|
|
|
|
my @aViolation = $oCritic->critique($file); |
567
|
|
|
|
|
|
|
|
568
|
0
|
|
|
|
|
|
Perl::Critic::Violation::set_format( "%m near '%r' (%e, %p) at %f line %l.\n" ); |
569
|
0
|
|
|
|
|
|
for my $violation (@aViolation) { |
570
|
0
|
|
|
|
|
|
print STDERR "Warning: $violation"; |
571
|
|
|
|
|
|
|
} |
572
|
|
|
|
|
|
|
} |
573
|
|
|
|
|
|
|
|
574
|
0
|
|
|
|
|
|
return 1; |
575
|
|
|
|
|
|
|
} |
576
|
|
|
|
|
|
|
|
577
|
|
|
|
|
|
|
|
578
|
|
|
|
|
|
|
|
579
|
|
|
|
|
|
|
|
580
|
|
|
|
|
|
|
|
581
|
|
|
|
|
|
|
=head2 rhSubCovered(file => $fileSource) |
582
|
|
|
|
|
|
|
|
583
|
|
|
|
|
|
|
Do a "covered subs" call with $fileSource. |
584
|
|
|
|
|
|
|
|
585
|
|
|
|
|
|
|
Die if Devel::CoverX::Covered isn't installed. |
586
|
|
|
|
|
|
|
|
587
|
|
|
|
|
|
|
Return hash ref with (keys: sub name; values: quality)), or an empty |
588
|
|
|
|
|
|
|
hash ref if no coverage info was found for $fileSource. |
589
|
|
|
|
|
|
|
|
590
|
|
|
|
|
|
|
Any subs with the same name will have their qualities combined. |
591
|
|
|
|
|
|
|
|
592
|
|
|
|
|
|
|
=cut |
593
|
0
|
|
|
0
|
1
|
|
sub rhSubCovered { |
594
|
0
|
|
|
|
|
|
my ($file) = Devel::PerlySense::Util::aNamedArg(["file"], @_); |
595
|
|
|
|
|
|
|
|
596
|
0
|
|
|
|
|
|
local $CWD = $self->dirProject; |
597
|
|
|
|
|
|
|
|
598
|
0
|
|
|
|
|
|
eval { |
599
|
0
|
|
|
|
|
|
require Devel::CoverX::Covered; |
600
|
0
|
|
|
|
|
|
require Devel::CoverX::Covered::Db; |
601
|
|
|
|
|
|
|
}; |
602
|
0
|
0
|
|
|
|
|
$@ and die("Devel::CoverX::Covered isn't installed\n"); |
603
|
|
|
|
|
|
|
|
604
|
|
|
|
|
|
|
###TODO: use dir specified in config and/or on command line |
605
|
0
|
|
|
|
|
|
local $CWD = $self->dirProject . ""; |
606
|
|
|
|
|
|
|
|
607
|
|
|
|
|
|
|
###TODO: Change Devel::CoverX::Covered to expose this dir properly |
608
|
|
|
|
|
|
|
###and get it from there. |
609
|
0
|
|
|
|
|
|
my $dirDb = "covered"; |
610
|
0
|
0
|
|
|
|
|
-d $dirDb or return( {} ); |
611
|
|
|
|
|
|
|
|
612
|
0
|
|
|
|
|
|
my $db = Devel::CoverX::Covered::Db->new(); |
613
|
0
|
|
|
|
|
|
my $fileRelative = file($file)->relative( $self->dirProject ); |
614
|
0
|
|
|
|
|
|
my %hSubQuality; |
615
|
0
|
|
|
|
|
|
for my $raSubQuality ( $db->covered_subs($fileRelative) ) { |
616
|
0
|
|
|
|
|
|
my ($sub, $quality) = @$raSubQuality; |
617
|
0
|
|
|
|
|
|
$hSubQuality{$sub} += $quality; |
618
|
|
|
|
|
|
|
} |
619
|
|
|
|
|
|
|
|
620
|
0
|
|
|
|
|
|
return(\%hSubQuality); |
621
|
|
|
|
|
|
|
} |
622
|
|
|
|
|
|
|
|
623
|
|
|
|
|
|
|
|
624
|
|
|
|
|
|
|
|
625
|
|
|
|
|
|
|
|
626
|
|
|
|
|
|
|
|
627
|
|
|
|
|
|
|
=head2 raFileTestOther(file => $fileSource, [sub => $sub]) |
628
|
|
|
|
|
|
|
|
629
|
|
|
|
|
|
|
Return array ref with file names of files related to $file and |
630
|
|
|
|
|
|
|
possibly $sub, i.e. the "other" files related $file. |
631
|
|
|
|
|
|
|
|
632
|
|
|
|
|
|
|
If $file is a source file, return test files, and vice verca. |
633
|
|
|
|
|
|
|
|
634
|
|
|
|
|
|
|
$sub is only ever active when $fileSource is a source file. |
635
|
|
|
|
|
|
|
|
636
|
|
|
|
|
|
|
Die if Devel::CoverX::Covered isn't installed. |
637
|
|
|
|
|
|
|
|
638
|
|
|
|
|
|
|
=cut |
639
|
0
|
|
|
0
|
1
|
|
sub raFileTestOther { |
640
|
0
|
|
|
|
|
|
my ($file, $sub) = Devel::PerlySense::Util::aNamedArg(["file", "sub"], @_); |
641
|
|
|
|
|
|
|
|
642
|
0
|
|
|
|
|
|
eval { |
643
|
0
|
|
|
|
|
|
require Devel::CoverX::Covered; |
644
|
0
|
|
|
|
|
|
require Devel::CoverX::Covered::Db; |
645
|
|
|
|
|
|
|
}; |
646
|
0
|
0
|
|
|
|
|
$@ and die("Devel::CoverX::Covered isn't installed\n"); |
647
|
|
|
|
|
|
|
|
648
|
|
|
|
|
|
|
###TODO: verify there is a cover_db database present |
649
|
|
|
|
|
|
|
|
650
|
0
|
|
|
|
|
|
local $CWD = $self->dirProject . ""; |
651
|
|
|
|
|
|
|
|
652
|
0
|
|
|
|
|
|
my $db = Devel::CoverX::Covered::Db->new(); |
653
|
|
|
|
|
|
|
|
654
|
0
|
|
|
|
|
|
my $method = "source_files_covered_by"; # Default to test file |
655
|
0
|
0
|
|
|
|
|
$file =~ m|\.pm$| and $method = "test_files_covering"; # If a module, it's source |
656
|
0
|
0
|
|
|
|
|
$file =~ m|/t/| and $method = "source_files_covered_by"; # If it's in /t/, it's a test |
657
|
0
|
0
|
|
|
|
|
$file =~ m|\.t$| and $method = "source_files_covered_by"; # If it's a .t file, it's a test |
658
|
|
|
|
|
|
|
### TODO: config with list of lib dirs and list of test dirs |
659
|
0
|
|
|
|
|
|
debug("raFileTestOther with method ($method)"); |
660
|
|
|
|
|
|
|
|
661
|
0
|
|
|
|
|
|
my $fileRelative = file($file)->relative( $self->dirProject ); |
662
|
0
|
|
|
|
|
|
my $raFileTestOther = [ $db->$method($fileRelative, $sub) ]; |
663
|
|
|
|
|
|
|
|
664
|
0
|
|
|
|
|
|
return($raFileTestOther); |
665
|
|
|
|
|
|
|
} |
666
|
|
|
|
|
|
|
|
667
|
|
|
|
|
|
|
|
668
|
|
|
|
|
|
|
|
669
|
|
|
|
|
|
|
|
670
|
|
|
|
|
|
|
|
671
|
|
|
|
|
|
|
=head2 raFileProjectOther(file => $fileSource, [sub => $sub]) |
672
|
|
|
|
|
|
|
|
673
|
|
|
|
|
|
|
Return array ref with file names of files corresponding to $file. |
674
|
|
|
|
|
|
|
|
675
|
|
|
|
|
|
|
Die if there is no config file. |
676
|
|
|
|
|
|
|
|
677
|
|
|
|
|
|
|
=cut |
678
|
0
|
|
|
0
|
1
|
|
sub raFileProjectOther { |
679
|
0
|
|
|
|
|
|
my ($file, $sub) = Devel::PerlySense::Util::aNamedArg(["file"], @_); |
680
|
|
|
|
|
|
|
|
681
|
0
|
|
|
|
|
|
eval { |
682
|
0
|
|
|
|
|
|
require File::Corresponding; |
683
|
0
|
|
|
|
|
|
require File::Corresponding::Config::Find; |
684
|
|
|
|
|
|
|
}; |
685
|
0
|
0
|
|
|
|
|
$@ and die("File::Corresponding isn't installed\n"); |
686
|
|
|
|
|
|
|
|
687
|
|
|
|
|
|
|
|
688
|
|
|
|
|
|
|
# Work from the project dir, so the rest of the paths will just work out |
689
|
0
|
|
|
|
|
|
local $CWD = $self->dirProject . ""; |
690
|
|
|
|
|
|
|
|
691
|
0
|
0
|
|
|
|
|
my $fileConfig = File::Corresponding::Config::Find->new( |
692
|
|
|
|
|
|
|
preferred_dirs => [ dir(".PerlySenseProject"), dir(".") ], |
693
|
|
|
|
|
|
|
)->user_config(".corresponding_file") |
694
|
|
|
|
|
|
|
or die("Could not find a '.corresponding_file' config file in either 1) the .PerlySenseProject; b) the current directory; c) your home directory. See perldoc File::Corresponding for information on how to create one.\n"); |
695
|
|
|
|
|
|
|
|
696
|
0
|
|
|
|
|
|
my $corresponding = File::Corresponding->new(); |
697
|
0
|
0
|
|
|
|
|
eval { $corresponding->load_config_file($fileConfig) } |
|
0
|
|
|
|
|
|
|
698
|
|
|
|
|
|
|
or die("Could not read config file ($fileConfig): $@\n"); |
699
|
|
|
|
|
|
|
|
700
|
0
|
|
|
|
|
|
my $fileRelative = file($file)->relative( $self->dirProject ); |
701
|
|
|
|
|
|
|
my @aFileProjectOther = uniq( |
702
|
0
|
|
|
|
|
|
map { $_->file } |
703
|
0
|
|
|
|
|
|
@{$corresponding->corresponding( $fileRelative )} |
|
0
|
|
|
|
|
|
|
704
|
|
|
|
|
|
|
); |
705
|
|
|
|
|
|
|
|
706
|
0
|
|
|
|
|
|
return(\@aFileProjectOther); |
707
|
|
|
|
|
|
|
} |
708
|
|
|
|
|
|
|
|
709
|
|
|
|
|
|
|
|
710
|
|
|
|
|
|
|
|
711
|
|
|
|
|
|
|
|
712
|
|
|
|
|
|
|
|
713
|
|
|
|
|
|
|
=head2 aFileSourceCode() |
714
|
|
|
|
|
|
|
|
715
|
|
|
|
|
|
|
Return array with file names with perl source code in the project. |
716
|
|
|
|
|
|
|
|
717
|
|
|
|
|
|
|
# TODO: also look inside files without extension and check for perlyness |
718
|
|
|
|
|
|
|
|
719
|
|
|
|
|
|
|
=cut |
720
|
0
|
|
|
0
|
1
|
|
sub aFileSourceCode { |
721
|
0
|
|
|
|
|
|
return File::Find::Rule |
722
|
|
|
|
|
|
|
->name("*.pm", "*.pl") |
723
|
|
|
|
|
|
|
->in( $self->aDirIncAbsolute ); |
724
|
|
|
|
|
|
|
} |
725
|
|
|
|
|
|
|
|
726
|
|
|
|
|
|
|
|
727
|
|
|
|
|
|
|
|
728
|
|
|
|
|
|
|
|
729
|
|
|
|
|
|
|
|
730
|
|
|
|
|
|
|
|
731
|
|
|
|
|
|
|
1; |
732
|
|
|
|
|
|
|
|
733
|
|
|
|
|
|
|
|
734
|
|
|
|
|
|
|
|
735
|
|
|
|
|
|
|
|
736
|
|
|
|
|
|
|
|
737
|
|
|
|
|
|
|
__END__ |
738
|
|
|
|
|
|
|
|
739
|
|
|
|
|
|
|
=encoding utf8 |
740
|
|
|
|
|
|
|
|
741
|
|
|
|
|
|
|
=head1 AUTHOR |
742
|
|
|
|
|
|
|
|
743
|
|
|
|
|
|
|
Johan Lindstrom, C<< <johanl@cpan.org> >> |
744
|
|
|
|
|
|
|
|
745
|
|
|
|
|
|
|
=head1 BUGS |
746
|
|
|
|
|
|
|
|
747
|
|
|
|
|
|
|
Please report any bugs or feature requests to |
748
|
|
|
|
|
|
|
C<bug-devel-perlysense@rt.cpan.org>, or through the web interface at |
749
|
|
|
|
|
|
|
L<http://rt.cpan.org/NoAuth/ReportBug.html?Queue=Devel-PerlySense>. |
750
|
|
|
|
|
|
|
I will be notified, and then you'll automatically be notified of progress on |
751
|
|
|
|
|
|
|
your bug as I make changes. |
752
|
|
|
|
|
|
|
|
753
|
|
|
|
|
|
|
=head1 ACKNOWLEDGEMENTS |
754
|
|
|
|
|
|
|
|
755
|
|
|
|
|
|
|
=head1 COPYRIGHT & LICENSE |
756
|
|
|
|
|
|
|
|
757
|
|
|
|
|
|
|
Copyright 2005 Johan Lindstrom, All Rights Reserved. |
758
|
|
|
|
|
|
|
|
759
|
|
|
|
|
|
|
This program is free software; you can redistribute it and/or modify it |
760
|
|
|
|
|
|
|
under the same terms as Perl itself. |
761
|
|
|
|
|
|
|
|
762
|
|
|
|
|
|
|
=cut |