Clean up spacing of doc comments
[lhc/web/wiklou.git] / tests / phpunit / maintenance / categoryChangesAsRdfTest.php
1 <?php
2
3 use Wikimedia\Rdbms\IDatabase;
4
5 /**
6 * Tests for CategoryChangesAsRdf recent changes exporter.
7 * @covers CategoryChangesAsRdf
8 */
9 class CategoryChangesAsRdfTest extends MediaWikiLangTestCase {
10
11 public function setUp() {
12 parent::setUp();
13 $this->setMwGlobals( [
14 'wgServer' => 'http://acme.test',
15 'wgCanonicalServer' => 'http://acme.test',
16 'wgArticlePath' => '/wiki/$1',
17 ] );
18 }
19
20 public function provideCategoryData() {
21 return [
22 'delete category' => [
23 __DIR__ . "/../data/categoriesrdf/delete.sparql",
24 'getDeletedCatsIterator',
25 'handleDeletes',
26 [
27 (object)[ 'rc_title' => 'Test', 'rc_cur_id' => 1, '_processed' => 1 ],
28 (object)[ 'rc_title' => 'Test 2', 'rc_cur_id' => 2, '_processed' => 2 ],
29 ],
30 ],
31 'move category' => [
32 __DIR__ . "/../data/categoriesrdf/move.sparql",
33 'getMovedCatsIterator',
34 'handleMoves',
35 [
36 (object)[
37 'rc_title' => 'Test',
38 'rc_cur_id' => 4,
39 'page_title' => 'MovedTo',
40 'page_namespace' => NS_CATEGORY,
41 '_processed' => 4,
42 'pp_propname' => null,
43 'cat_pages' => 10,
44 'cat_subcats' => 2,
45 'cat_files' => 1,
46 ],
47 (object)[
48 'rc_title' => 'MovedTo',
49 'rc_cur_id' => 4,
50 'page_title' => 'MovedAgain',
51 'page_namespace' => NS_CATEGORY,
52 'pp_propname' => 'hiddencat',
53 'cat_pages' => 10,
54 'cat_subcats' => 2,
55 'cat_files' => 1,
56 ],
57 (object)[
58 'rc_title' => 'Test 2',
59 'rc_cur_id' => 5,
60 'page_title' => 'AlsoMoved',
61 'page_namespace' => NS_CATEGORY,
62 '_processed' => 5,
63 'pp_propname' => null,
64 'cat_pages' => 10,
65 'cat_subcats' => 2,
66 'cat_files' => 1,
67 ],
68 (object)[
69 'rc_title' => 'Test 3',
70 'rc_cur_id' => 6,
71 'page_title' => 'MovedOut',
72 'page_namespace' => NS_MAIN,
73 'pp_propname' => null,
74 'cat_pages' => 10,
75 'cat_subcats' => 2,
76 'cat_files' => 1,
77 ],
78 (object)[
79 'rc_title' => 'Test 4',
80 'rc_cur_id' => 7,
81 'page_title' => 'Already Done',
82 'page_namespace' => NS_CATEGORY,
83 'pp_propname' => null,
84 'cat_pages' => 10,
85 'cat_subcats' => 2,
86 'cat_files' => 1,
87 ],
88 ],
89 [ 7 => true ],
90 ],
91 'restore deleted category' => [
92 __DIR__ . "/../data/categoriesrdf/restore.sparql",
93 'getRestoredCatsIterator',
94 'handleRestores',
95 [
96 (object)[
97 'rc_title' => 'Restored cat',
98 'rc_cur_id' => 10,
99 '_processed' => 10,
100 'pp_propname' => null,
101 'cat_pages' => 10,
102 'cat_subcats' => 2,
103 'cat_files' => 1,
104 ],
105 (object)[
106 'rc_title' => 'Restored again',
107 'rc_cur_id' => 10,
108 'pp_propname' => null,
109 'cat_pages' => 10,
110 'cat_subcats' => 2,
111 'cat_files' => 1,
112 ],
113 (object)[
114 'rc_title' => 'Already seen',
115 'rc_cur_id' => 11,
116 'pp_propname' => null,
117 'cat_pages' => 10,
118 'cat_subcats' => 2,
119 'cat_files' => 1,
120 ],
121 ],
122 [ 11 => true ],
123 ],
124 'new page' => [
125 __DIR__ . "/../data/categoriesrdf/new.sparql",
126 'getNewCatsIterator',
127 'handleAdds',
128 [
129 (object)[
130 'rc_title' => 'New category',
131 'rc_cur_id' => 20,
132 '_processed' => 20,
133 'pp_propname' => null,
134 'cat_pages' => 10,
135 'cat_subcats' => 2,
136 'cat_files' => 1,
137 ],
138 (object)[
139 'rc_title' => 'Новая категория 😃',
140 'rc_cur_id' => 21,
141 '_processed' => 21,
142 'pp_propname' => 'hiddencat',
143 'cat_pages' => 10,
144 'cat_subcats' => 2,
145 'cat_files' => 1,
146 ],
147 (object)[
148 'rc_title' => 'Processed already',
149 'rc_cur_id' => 22,
150 ],
151 ],
152 [ 22 => true ],
153 ],
154 'edit category' => [
155 __DIR__ . "/../data/categoriesrdf/edit.sparql",
156 'getChangedCatsIterator',
157 'handleEdits',
158 [
159 (object)[
160 'rc_title' => 'Changed category',
161 'rc_cur_id' => 30,
162 '_processed' => 30,
163 'pp_propname' => null,
164 'cat_pages' => 10,
165 'cat_subcats' => 2,
166 'cat_files' => 1,
167 ],
168 (object)[
169 'rc_title' => 'Changed again',
170 'rc_cur_id' => 30,
171 'pp_propname' => null,
172 'cat_pages' => 12,
173 'cat_subcats' => 2,
174 'cat_files' => 1,
175 ],
176 (object)[
177 'rc_title' => 'Processed already',
178 'rc_cur_id' => 31,
179 'pp_propname' => null,
180 'cat_pages' => 10,
181 'cat_subcats' => 2,
182 'cat_files' => 1,
183 ],
184 ],
185 [ 31 => true ],
186 ],
187 // TODO: not sure how to test categorization changes, it uses the database select...
188 ];
189 }
190
191 /**
192 * Mock category links iterator.
193 * @param IDatabase $dbr
194 * @param array $ids
195 * @return array
196 */
197 public function getCategoryLinksIterator( $dbr, array $ids ) {
198 $res = [];
199 foreach ( $ids as $pageid ) {
200 $res[] = (object)[ 'cl_from' => $pageid, 'cl_to' => "Parent of $pageid" ];
201 }
202 return $res;
203 }
204
205 /**
206 * @dataProvider provideCategoryData
207 * @param string $testFileName Name of the test, defines filename with expected results.
208 * @param string $iterator Iterator method name to mock
209 * @param string $handler Handler method to call
210 * @param array $result Result to be returned from mock iterator
211 * @param array $preProcessed List of pre-processed items
212 */
213 public function testSparqlUpdate( $testFileName, $iterator, $handler, $result,
214 array $preProcessed = [] ) {
215 $dumpScript =
216 $this->getMockBuilder( CategoryChangesAsRdf::class )
217 ->setMethods( [ $iterator, 'getCategoryLinksIterator' ] )
218 ->getMock();
219
220 $dumpScript->expects( $this->any() )
221 ->method( 'getCategoryLinksIterator' )
222 ->willReturnCallback( [ $this, 'getCategoryLinksIterator' ] );
223
224 $dumpScript->expects( $this->once() )
225 ->method( $iterator )
226 ->willReturn( [ $result ] );
227
228 $ref = new ReflectionObject( $dumpScript );
229 $processedProperty = $ref->getProperty( 'processed' );
230 $processedProperty->setAccessible( true );
231 $processedProperty->setValue( $dumpScript, $preProcessed );
232
233 $output = fopen( "php://memory", "w+b" );
234 $dbr = wfGetDB( DB_REPLICA );
235 /** @var CategoryChangesAsRdf $dumpScript */
236 $dumpScript->initialize();
237 $dumpScript->getRdf();
238 $dumpScript->$handler( $dbr, $output );
239
240 rewind( $output );
241 $sparql = stream_get_contents( $output );
242 $this->assertFileContains( $testFileName, $sparql );
243
244 $processed = $processedProperty->getValue( $dumpScript );
245 $expectedProcessed = array_keys( $preProcessed );
246 foreach ( $result as $row ) {
247 if ( isset( $row->_processed ) ) {
248 $this->assertArrayHasKey( $row->_processed, $processed,
249 "ID {$row->_processed} was not processed!" );
250 $expectedProcessed[] = $row->_processed;
251 }
252 }
253 $this->assertSame( $expectedProcessed, array_keys( $processed ),
254 'Processed array has wrong items' );
255 }
256
257 public function testUpdateTs() {
258 $dumpScript = new CategoryChangesAsRdf();
259 $dumpScript->initialize();
260 $update = $dumpScript->updateTS( 1503620949 );
261 $outFile = __DIR__ . '/../data/categoriesrdf/updatets.txt';
262 $this->assertFileContains( $outFile, $update );
263 }
264
265 }