MediaWiki
REL1_31
TestFileReader.php
Go to the documentation of this file.
1
<?php
22
class
TestFileReader
{
23
private
$file
;
24
private
$fh
;
25
private
$section
=
null
;
27
private
$sectionData
= [];
28
private
$sectionLineNum
= [];
29
private
$lineNum
= 0;
30
private
$runDisabled
;
31
private
$runParsoid
;
32
private
$regex
;
33
34
private
$articles
= [];
35
private
$requirements
= [];
36
private
$tests
= [];
37
38
public
static
function
read
( $file, array
$options
= [] ) {
39
$reader =
new
self
(
$file
,
$options
);
40
$reader->execute();
41
42
$requirements
= [];
43
foreach
( $reader->requirements as
$type
=> $reqsOfType ) {
44
foreach
( $reqsOfType as $name => $unused ) {
45
$requirements
[] = [
46
'type'
=>
$type
,
47
'name'
=>
$name
48
];
49
}
50
}
51
52
return
[
53
'requirements'
=>
$requirements
,
54
'tests'
=> $reader->tests,
55
'articles'
=> $reader->articles
56
];
57
}
58
59
private
function
__construct
( $file,
$options
) {
60
$this->file =
$file
;
61
$this->fh = fopen( $this->file,
"rt"
);
62
63
if
( !$this->fh ) {
64
throw
new
MWException
(
"Couldn't open file '$file'\n"
);
65
}
66
67
$options
=
$options
+ [
68
'runDisabled'
=>
false
,
69
'runParsoid'
=>
false
,
70
'regex'
=>
'//'
,
71
];
72
$this->runDisabled =
$options
[
'runDisabled'
];
73
$this->runParsoid =
$options
[
'runParsoid'
];
74
$this->regex =
$options
[
'regex'
];
75
}
76
77
private
function
addCurrentTest
() {
78
// "input" and "result" are old section names allowed
79
// for backwards-compatibility.
80
$input
= $this->
checkSection
( [
'wikitext'
,
'input'
],
false
);
81
$nonTidySection = $this->
checkSection
(
82
[
'html/php'
,
'html/*'
,
'html'
,
'result'
],
false
);
83
// Some tests have "with tidy" and "without tidy" variants
84
$tidySection = $this->
checkSection
( [
'html/php+tidy'
,
'html+tidy'
],
false
);
85
86
// Remove trailing newline
87
$data = array_map(
'ParserTestRunner::chomp'
, $this->sectionData );
88
89
// Apply defaults
90
$data += [
91
'options'
=>
''
,
92
'config'
=>
''
93
];
94
95
if
(
$input
===
false
) {
96
throw
new
MWException
(
"Test at {$this->file}:{$this->sectionLineNum['test']} "
.
97
"lacks input section"
);
98
}
99
100
if
( preg_match(
'/\\bdisabled\\b/i'
, $data[
'options'
] ) && !$this->runDisabled ) {
101
// Disabled
102
return
;
103
}
104
105
if
( $tidySection ===
false
&& $nonTidySection ===
false
) {
106
if
( isset( $data[
'html/parsoid'
] ) || isset( $data[
'wikitext/edited'
] ) ) {
107
// Parsoid only
108
return
;
109
}
else
{
110
throw
new
MWException
(
"Test at {$this->file}:{$this->sectionLineNum['test']} "
.
111
"lacks result section"
);
112
}
113
}
114
115
if
( preg_match(
'/\\bparsoid\\b/i'
, $data[
'options'
] ) && $nonTidySection ===
'html'
116
&& !$this->runParsoid
117
) {
118
// A test which normally runs on Parsoid but can optionally be run with MW
119
return
;
120
}
121
122
if
( !preg_match( $this->regex, $data[
'test'
] ) ) {
123
// Filtered test
124
return
;
125
}
126
127
$commonInfo = [
128
'test'
=> $data[
'test'
],
129
'desc'
=> $data[
'test'
],
130
'input'
=> $data[
$input
],
131
'options'
=> $data[
'options'
],
132
'config'
=> $data[
'config'
],
133
'line'
=> $this->sectionLineNum[
'test'
],
134
'file'
=>
$this->file
135
];
136
137
if
( $nonTidySection !==
false
) {
138
// Add non-tidy test
139
$this->tests[] = [
140
'result'
=> $data[$nonTidySection],
141
'resultSection'
=> $nonTidySection
142
] + $commonInfo;
143
144
if
( $tidySection !==
false
) {
145
// Add tidy subtest
146
$this->tests[] = [
147
'desc'
=> $data[
'test'
] .
' (with tidy)'
,
148
'result'
=> $data[$tidySection],
149
'resultSection'
=> $tidySection,
150
'options'
=> $data[
'options'
] .
' tidy'
,
151
'isSubtest'
=>
true
,
152
] + $commonInfo;
153
}
154
} elseif ( $tidySection !==
false
) {
155
// No need to override desc when there is no subtest
156
$this->tests[] = [
157
'result'
=> $data[$tidySection],
158
'resultSection'
=> $tidySection,
159
'options'
=> $data[
'options'
] .
' tidy'
160
] + $commonInfo;
161
}
else
{
162
throw
new
MWException
(
"Test at {$this->file}:{$this->sectionLineNum['test']} "
.
163
"lacks result section"
);
164
}
165
}
166
167
private
function
execute
() {
168
while
(
false
!== (
$line
= fgets( $this->fh ) ) ) {
169
$this->lineNum++;
170
$matches
= [];
171
172
if
( preg_match(
'/^!!\s*(\S+)/'
,
$line
,
$matches
) ) {
173
$this->section = strtolower(
$matches
[1] );
174
175
if
( $this->section ==
'endarticle'
) {
176
$this->
checkSection
(
'text'
);
177
$this->
checkSection
(
'article'
);
178
179
$this->
addArticle
(
180
ParserTestRunner::chomp
( $this->sectionData[
'article'
] ),
181
$this->sectionData[
'text'
], $this->lineNum );
182
183
$this->
clearSection
();
184
185
continue
;
186
}
187
188
if
( $this->section ==
'endhooks'
) {
189
$this->
checkSection
(
'hooks'
);
190
191
foreach
( explode(
"\n"
, $this->sectionData[
'hooks'
] ) as
$line
) {
192
$line
= trim(
$line
);
193
194
if
(
$line
) {
195
$this->
addRequirement
(
'hook'
, $line );
196
}
197
}
198
199
$this->
clearSection
();
200
201
continue
;
202
}
203
204
if
( $this->section ==
'endfunctionhooks'
) {
205
$this->
checkSection
(
'functionhooks'
);
206
207
foreach
( explode(
"\n"
, $this->sectionData[
'functionhooks'
] ) as
$line
) {
208
$line
= trim(
$line
);
209
210
if
(
$line
) {
211
$this->
addRequirement
(
'functionHook'
, $line );
212
}
213
}
214
215
$this->
clearSection
();
216
217
continue
;
218
}
219
220
if
( $this->section ==
'endtransparenthooks'
) {
221
$this->
checkSection
(
'transparenthooks'
);
222
223
foreach
( explode(
"\n"
, $this->sectionData[
'transparenthooks'
] ) as
$line
) {
224
$line
= trim(
$line
);
225
226
if
(
$line
) {
227
$this->
addRequirement
(
'transparentHook'
, $line );
228
}
229
}
230
231
$this->
clearSection
();
232
233
continue
;
234
}
235
236
if
( $this->section ==
'end'
) {
237
$this->
checkSection
(
'test'
);
238
$this->
addCurrentTest
();
239
$this->
clearSection
();
240
continue
;
241
}
242
243
if
( isset( $this->sectionData[$this->section] ) ) {
244
throw
new
MWException
(
"duplicate section '$this->section' "
245
.
"at line {$this->lineNum} of $this->file\n"
);
246
}
247
248
$this->sectionLineNum[
$this->section
] =
$this->lineNum
;
249
$this->sectionData[
$this->section
] =
''
;
250
251
continue
;
252
}
253
254
if
( $this->section ) {
255
$this->sectionData[
$this->section
] .=
$line
;
256
}
257
}
258
}
259
263
private
function
clearSection
() {
264
$this->sectionLineNum = [];
265
$this->sectionData = [];
266
$this->section =
null
;
267
}
268
282
private
function
checkSection
(
$tokens
, $fatal =
true
) {
283
if
( is_null( $this->section ) ) {
284
throw
new
MWException
( __METHOD__ .
" can not verify a null section!\n"
);
285
}
286
if
( !is_array(
$tokens
) ) {
287
$tokens
= [
$tokens
];
288
}
289
if
( count(
$tokens
) == 0 ) {
290
throw
new
MWException
( __METHOD__ .
" can not verify zero sections!\n"
);
291
}
292
293
$data =
$this->sectionData
;
294
$tokens
= array_filter(
$tokens
,
function
( $token ) use ( $data ) {
295
return
isset( $data[$token] );
296
} );
297
298
if
( count(
$tokens
) == 0 ) {
299
if
( !$fatal ) {
300
return
false
;
301
}
302
throw
new
MWException
( sprintf(
303
"'%s' without '%s' at line %s of %s\n"
,
304
$this->section,
305
implode(
','
,
$tokens
),
306
$this->lineNum,
307
$this->file
308
) );
309
}
310
if
( count(
$tokens
) > 1 ) {
311
throw
new
MWException
( sprintf(
312
"'%s' with unexpected tokens '%s' at line %s of %s\n"
,
313
$this->section,
314
implode(
','
,
$tokens
),
315
$this->lineNum,
316
$this->file
317
) );
318
}
319
320
return
array_values(
$tokens
)[0];
321
}
322
323
private
function
addArticle
( $name, $text,
$line
) {
324
$this->articles[] = [
325
'name'
=>
$name
,
326
'text'
=> $text,
327
'line'
=>
$line
,
328
'file'
=>
$this->file
329
];
330
}
331
332
private
function
addRequirement
(
$type
, $name ) {
333
$this->requirements[
$type
][
$name
] =
true
;
334
}
335
}
$matches
$matches
Definition
NoLocalSettings.php:24
$line
$line
Definition
cdb.php:59
MWException
MediaWiki exception.
Definition
MWException.php:26
ParserTestRunner\chomp
static chomp( $s)
Remove last character if it is a newline.
Definition
ParserTestRunner.php:646
TestFileReader
Definition
TestFileReader.php:22
TestFileReader\$regex
$regex
Definition
TestFileReader.php:32
TestFileReader\addArticle
addArticle( $name, $text, $line)
Definition
TestFileReader.php:323
TestFileReader\$articles
$articles
Definition
TestFileReader.php:34
TestFileReader\$requirements
$requirements
Definition
TestFileReader.php:35
TestFileReader\clearSection
clearSection()
Clear section name and its data.
Definition
TestFileReader.php:263
TestFileReader\__construct
__construct( $file, $options)
Definition
TestFileReader.php:59
TestFileReader\$sectionLineNum
$sectionLineNum
Definition
TestFileReader.php:28
TestFileReader\$file
$file
Definition
TestFileReader.php:23
TestFileReader\$sectionData
$sectionData
String|null: current test section being analyzed.
Definition
TestFileReader.php:27
TestFileReader\$runParsoid
$runParsoid
Definition
TestFileReader.php:31
TestFileReader\$runDisabled
$runDisabled
Definition
TestFileReader.php:30
TestFileReader\$section
$section
Definition
TestFileReader.php:25
TestFileReader\addCurrentTest
addCurrentTest()
Definition
TestFileReader.php:77
TestFileReader\checkSection
checkSection( $tokens, $fatal=true)
Verify the current section data has some value for the given token name(s) (first parameter).
Definition
TestFileReader.php:282
TestFileReader\$tests
$tests
Definition
TestFileReader.php:36
TestFileReader\addRequirement
addRequirement( $type, $name)
Definition
TestFileReader.php:332
TestFileReader\execute
execute()
Definition
TestFileReader.php:167
TestFileReader\$lineNum
$lineNum
Definition
TestFileReader.php:29
TestFileReader\read
static read( $file, array $options=[])
Definition
TestFileReader.php:38
TestFileReader\$fh
$fh
Definition
TestFileReader.php:24
$options
null means default in associative array with keys and values unescaped Should be merged with default with a value of false meaning to suppress the attribute in associative array with keys and values unescaped & $options
Definition
hooks.txt:2001
$name
Allows to change the fields on the form that will be generated $name
Definition
hooks.txt:302
$tokens
$tokens
Definition
mwdoc-filter.php:47
$input
if(is_array($mode)) switch( $mode) $input
Definition
postprocess-phan.php:145
$type
$type
Definition
testCompression.php:48
tests
parser
TestFileReader.php
Generated on Mon Nov 25 2024 15:36:10 for MediaWiki by
1.10.0