File Coverage

blib/lib/YATT/Lite/Test/XHFTest.pm
Criterion Covered Total %
statement 120 125 96.0
branch 25 32 78.1
condition 16 28 57.1
subroutine 24 24 100.0
pod 1 10 10.0
total 186 219 84.9


line stmt bran cond sub pod time code
1             package YATT::Lite::Test::XHFTest;
2 2     2   4751 use strict;
  2         4  
  2         60  
3 2     2   11 use warnings qw(FATAL all NONFATAL misc);
  2         6  
  2         91  
4 2     2   11 use parent qw(YATT::Lite::Object);
  2         4  
  2         14  
5 2         14 use YATT::Lite::MFields qw/tests numtests yatt global file_list file_dict
6             cf_filename cf_ext cf_parser cf_encoding
7 2     2   137 prev_item builder/;
  2         4  
8 2     2   13 use Exporter 'import';
  2         4  
  2         124  
9             sub MY () {__PACKAGE__}
10 2     2   10 use YATT::Lite::Util qw(default dict_sort);
  2         5  
  2         176  
11 10     10 0 34 sub default_ext {'yatt'}
12             our @EXPORT_OK = qw(Item);
13              
14 2     2   12 use Encode;
  2         4  
  2         270  
15              
16             {
17             sub Item () {'YATT::Lite::Test::XHFTest::Item'}
18             package YATT::Lite::Test::XHFTest::Item;
19 2     2   16 use parent qw(YATT::Lite::Object);
  2         4  
  2         10  
20 2     2   111 use YATT::Lite::Util qw(lexpand);
  2         5  
  2         116  
21 2         10 use YATT::Lite::MFields qw/cf_global
22             cf_parser
23              
24             num
25             realfile
26              
27             cf_FILE
28             cf_TITLE
29             cf_BREAK
30             cf_SKIP
31             cf_TODO
32             cf_PERL_MINVER
33              
34             cf_WIDGET
35             cf_RANDOM
36             cf_IN
37             cf_PARAM
38             cf_OUT
39             cf_ERROR
40              
41             cf_REQUIRE
42              
43             cf_TAG
44 2     2   20 /;
  2         4  
45              
46 165     165   99281 sub is_runnable { shift->ntests }
47             sub ntests {
48 339     339   1114 my __PACKAGE__ $item = shift;
49 339 100       957 if ($item->{cf_OUT}) {
    100          
50 242         1547 2;
51             } elsif ($item->{cf_ERROR}) {
52 87         565 1;
53             } else {
54 10         59 0;
55             }
56             }
57             sub test_require {
58 1     1   3 my ($self, $reqlist) = @_;
59 1         5 grep {not eval qq{require $_}} lexpand($reqlist);
  1         74  
60             }
61              
62             }
63              
64             require YATT::Lite::XHF;
65             sub Parser () {'YATT::Lite::XHF'}
66              
67             sub list_files {
68 1     1 0 406 my $pack = shift;
69             map {
70 1 50       3 ! -d $_ ? $_ : dict_sort <$_/*.xhf>;
  10         266  
71             } @_;
72             }
73              
74             sub after_new {
75 10     10 1 16 my MY $self = shift;
76 10         20 $self->{numtests} = 0;
77 10         20 $self->{tests} = [];
78 10   33     48 $self->{cf_ext} //= $self->default_ext;
79 10         24 $self;
80             }
81             sub load {
82 10     10 0 192 my $pack = shift;
83 10         86 my Parser $parser = $pack->Parser->new(@_);
84 10         40 my MY $self = $pack->new($parser->cf_delegate(qw(filename))
85             , parser => $parser);
86 10 100       43 if (my @global = $parser->read(skip_comment => 0)) {
87 3         14 $self->configure(@global);
88 3         16 $parser->configure($self->cf_delegate_defined(qw(encoding)));
89             }
90 10         64 while (my @config = $parser->read) {
91 165         764 $self->add_item($self->Item->new(@config));
92             }
93 10         58 $self;
94             }
95              
96             sub convert_enc_array {
97 2     2 0 17 my ($self, $enc, $array) = @_;
98 2         6 foreach (@$array) {
99 5 100       117 unless (ref $_) {
    50          
100 4         32 $_ = decode($enc, $_)
101             } elsif (ref $_ eq 'ARRAY') {
102 1         5 $_ = $self->convert_enc_array($enc, $_);
103             } else {
104             # nop.
105             }
106             }
107 2         36 $array;
108             }
109              
110             sub ntests {
111 10     10 0 52 my MY $self = shift; $self->{numtests}
112 10         34 }
113             sub add_item {
114 165     165 0 253 (my MY $self, my Item $item) = @_;
115 165 50       389 if ($item->{cf_global}) {
116 0         0 $self->{global} = $item->{cf_global};
117 0         0 next;
118             }
119 165         174 push @{$self->{tests}}, $self->fixup_item($item);
  165         423  
120 165         412 $self->{numtests} += $item->ntests;
121             }
122              
123             sub fixup_item {
124 165     165 0 258 (my MY $self, my Item $test) = @_;
125 165         231 my Item $prev = $self->{prev_item};
126 165   66     420 $test->{cf_FILE} ||= do {
127 159 100 100     783 if ($prev && $prev->{cf_FILE} =~ m{%d}) {
128             $prev->{cf_FILE}
129 148         485 } else {
130 11         41 "f%d.$self->{cf_ext}"
131             }
132             };
133              
134 165         235 $test->{realfile} = do {
135 165 100       291 if ($test->{cf_IN}) {
136 2     2   14 no if $] >= 5.021002, warnings => qw/redundant/;
  2         4  
  2         19  
137 142   100     212 sprintf($test->{cf_FILE}, 1+@{$self->{file_list} //= []})
  142         769  
138             } else {
139             $prev->{realfile}
140 23         50 }
141             };
142              
143 165   33     448 $test->{cf_WIDGET} ||= do {
144 165         268 my $widget = $test->{realfile};
145 165         603 $widget =~ s{\.\w+$}{};
146 165         272 $widget =~ s{/}{:}g;
147 165         517 $widget;
148             };
149              
150 165 100       406 if ($test->{cf_IN}) {
151 142 50       413 if (my $conflict = $self->{file_dict}{$test->{realfile}}) {
152 0         0 die "FILE name confliction in test $test";
153             }
154 142         362 $self->{file_dict}{$test->{realfile}} = $test;
155 142         165 push @{$self->{file_list}}, $test->{realfile};
  142         354  
156             }
157              
158 165 100 66     622 if ($test->{cf_OUT} || $test->{cf_ERROR}) {
159 160   0     342 $test->{cf_WIDGET} ||= $prev && $prev->{cf_WIDGET};
      33        
160 160 100 100     467 if (not $test->{cf_TITLE} and $prev) {
161 19         71 $test->{num} = default($prev->{num}, 0) + 1;
162 19         48 $test->{cf_TITLE} = $prev->{cf_TITLE};
163             }
164 160         267 $self->{prev_item} = $test;
165             }
166              
167 165         334 $test;
168             }
169              
170             sub as_vfs_data {
171 10     10 0 10164 my MY $self = shift;
172 10         22 my (%result);
173             # 記述の順番どおりに作成
174 10         18 foreach my $fn (@{$self->{file_list}}) {
  10         36  
175 142         317 my Item $item = $self->{file_dict}{$fn};
176 142         278 my @path = split m|/|, $fn;
177 142         353 my $path_cursor = path_cursor(\%result, \@path);
178 142 50       660 $path[0] =~ s|\.(\w+)$||
179             or die "Can't handle filename as vfs key: $fn";
180 142         276 my $ext = $1;
181 142 50       526 if (my $sub = $self->can("convert_$ext")) {
182 0         0 $sub->($self, $path_cursor, $item)
183             } else {
184             # XXX: 既に配列になってると困るよね。 rc 系を後回しにすれば大丈夫?
185 142 50       373 unless (defined $item->{cf_IN}) {
186 0         0 die "undef IN"
187             }
188 142         598 $path_cursor->[0]{$path[0]} = $item->{cf_IN};
189             }
190             }
191 10         38 \%result;
192             }
193              
194             sub path_cursor {
195 142     142 0 208 my ($top, $path) = @_;
196             # path を一個残して、vivify する。
197             # そこにいたる経路を cursor として返す。
198 142         239 my $cursor = [$top];
199 142         354 while (@$path > 1) {
200 1         3 my $nm = shift @$path;
201 1   50     11 $cursor = [$cursor->[0]{$nm} ||= {}, $cursor];
202             }
203 142         240 $cursor;
204             }
205              
206             1;