Mercurial > hg > isophonics-drupal-site
comparison core/modules/comment/tests/src/Functional/CommentPagerTest.php @ 17:129ea1e6d783
Update, including to Drupal core 8.6.10
author | Chris Cannam |
---|---|
date | Thu, 28 Feb 2019 13:21:36 +0000 |
parents | |
children | af1871eacc83 |
comparison
equal
deleted
inserted
replaced
16:c2387f117808 | 17:129ea1e6d783 |
---|---|
1 <?php | |
2 | |
3 namespace Drupal\Tests\comment\Functional; | |
4 | |
5 use Drupal\comment\CommentManagerInterface; | |
6 use Drupal\Component\Render\FormattableMarkup; | |
7 use Drupal\node\Entity\Node; | |
8 | |
9 /** | |
10 * Tests paging of comments and their settings. | |
11 * | |
12 * @group comment | |
13 */ | |
14 class CommentPagerTest extends CommentTestBase { | |
15 | |
16 /** | |
17 * Confirms comment paging works correctly with flat and threaded comments. | |
18 */ | |
19 public function testCommentPaging() { | |
20 $this->drupalLogin($this->adminUser); | |
21 | |
22 // Set comment variables. | |
23 $this->setCommentForm(TRUE); | |
24 $this->setCommentSubject(TRUE); | |
25 $this->setCommentPreview(DRUPAL_DISABLED); | |
26 | |
27 // Create a node and three comments. | |
28 $node = $this->drupalCreateNode(['type' => 'article', 'promote' => 1]); | |
29 $comments = []; | |
30 $comments[] = $this->postComment($node, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
31 $comments[] = $this->postComment($node, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
32 $comments[] = $this->postComment($node, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
33 | |
34 $this->setCommentSettings('default_mode', CommentManagerInterface::COMMENT_MODE_FLAT, 'Comment paging changed.'); | |
35 | |
36 // Set comments to one per page so that we are able to test paging without | |
37 // needing to insert large numbers of comments. | |
38 $this->setCommentsPerPage(1); | |
39 | |
40 // Check the first page of the node, and confirm the correct comments are | |
41 // shown. | |
42 $this->drupalGet('node/' . $node->id()); | |
43 $this->assertRaw(t('next'), 'Paging links found.'); | |
44 $this->assertTrue($this->commentExists($comments[0]), 'Comment 1 appears on page 1.'); | |
45 $this->assertFalse($this->commentExists($comments[1]), 'Comment 2 does not appear on page 1.'); | |
46 $this->assertFalse($this->commentExists($comments[2]), 'Comment 3 does not appear on page 1.'); | |
47 | |
48 // Check the second page. | |
49 $this->drupalGet('node/' . $node->id(), ['query' => ['page' => 1]]); | |
50 $this->assertTrue($this->commentExists($comments[1]), 'Comment 2 appears on page 2.'); | |
51 $this->assertFalse($this->commentExists($comments[0]), 'Comment 1 does not appear on page 2.'); | |
52 $this->assertFalse($this->commentExists($comments[2]), 'Comment 3 does not appear on page 2.'); | |
53 | |
54 // Check the third page. | |
55 $this->drupalGet('node/' . $node->id(), ['query' => ['page' => 2]]); | |
56 $this->assertTrue($this->commentExists($comments[2]), 'Comment 3 appears on page 3.'); | |
57 $this->assertFalse($this->commentExists($comments[0]), 'Comment 1 does not appear on page 3.'); | |
58 $this->assertFalse($this->commentExists($comments[1]), 'Comment 2 does not appear on page 3.'); | |
59 | |
60 // Post a reply to the oldest comment and test again. | |
61 $oldest_comment = reset($comments); | |
62 $this->drupalGet('comment/reply/node/' . $node->id() . '/comment/' . $oldest_comment->id()); | |
63 $reply = $this->postComment(NULL, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
64 | |
65 $this->setCommentsPerPage(2); | |
66 // We are still in flat view - the replies should not be on the first page, | |
67 // even though they are replies to the oldest comment. | |
68 $this->drupalGet('node/' . $node->id(), ['query' => ['page' => 0]]); | |
69 $this->assertFalse($this->commentExists($reply, TRUE), 'In flat mode, reply does not appear on page 1.'); | |
70 | |
71 // If we switch to threaded mode, the replies on the oldest comment | |
72 // should be bumped to the first page and comment 6 should be bumped | |
73 // to the second page. | |
74 $this->setCommentSettings('default_mode', CommentManagerInterface::COMMENT_MODE_THREADED, 'Switched to threaded mode.'); | |
75 $this->drupalGet('node/' . $node->id(), ['query' => ['page' => 0]]); | |
76 $this->assertTrue($this->commentExists($reply, TRUE), 'In threaded mode, reply appears on page 1.'); | |
77 $this->assertFalse($this->commentExists($comments[1]), 'In threaded mode, comment 2 has been bumped off of page 1.'); | |
78 | |
79 // If (# replies > # comments per page) in threaded expanded view, | |
80 // the overage should be bumped. | |
81 $reply2 = $this->postComment(NULL, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
82 $this->drupalGet('node/' . $node->id(), ['query' => ['page' => 0]]); | |
83 $this->assertFalse($this->commentExists($reply2, TRUE), 'In threaded mode where # replies > # comments per page, the newest reply does not appear on page 1.'); | |
84 | |
85 // Test that the page build process does not somehow generate errors when | |
86 // # comments per page is set to 0. | |
87 $this->setCommentsPerPage(0); | |
88 $this->drupalGet('node/' . $node->id(), ['query' => ['page' => 0]]); | |
89 $this->assertFalse($this->commentExists($reply2, TRUE), 'Threaded mode works correctly when comments per page is 0.'); | |
90 | |
91 $this->drupalLogout(); | |
92 } | |
93 | |
94 /** | |
95 * Confirms comment paging works correctly with flat and threaded comments. | |
96 */ | |
97 public function testCommentPermalink() { | |
98 $this->drupalLogin($this->adminUser); | |
99 | |
100 // Set comment variables. | |
101 $this->setCommentForm(TRUE); | |
102 $this->setCommentSubject(TRUE); | |
103 $this->setCommentPreview(DRUPAL_DISABLED); | |
104 | |
105 // Create a node and three comments. | |
106 $node = $this->drupalCreateNode(['type' => 'article', 'promote' => 1]); | |
107 $comments = []; | |
108 $comments[] = $this->postComment($node, 'comment 1: ' . $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
109 $comments[] = $this->postComment($node, 'comment 2: ' . $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
110 $comments[] = $this->postComment($node, 'comment 3: ' . $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
111 | |
112 $this->setCommentSettings('default_mode', CommentManagerInterface::COMMENT_MODE_FLAT, 'Comment paging changed.'); | |
113 | |
114 // Set comments to one per page so that we are able to test paging without | |
115 // needing to insert large numbers of comments. | |
116 $this->setCommentsPerPage(1); | |
117 | |
118 // Navigate to each comment permalink as anonymous and assert it appears on | |
119 // the page. | |
120 foreach ($comments as $index => $comment) { | |
121 $this->drupalGet($comment->toUrl()); | |
122 $this->assertTrue($this->commentExists($comment), sprintf('Comment %d appears on page %d.', $index + 1, $index + 1)); | |
123 } | |
124 } | |
125 | |
126 /** | |
127 * Tests comment ordering and threading. | |
128 */ | |
129 public function testCommentOrderingThreading() { | |
130 $this->drupalLogin($this->adminUser); | |
131 | |
132 // Set comment variables. | |
133 $this->setCommentForm(TRUE); | |
134 $this->setCommentSubject(TRUE); | |
135 $this->setCommentPreview(DRUPAL_DISABLED); | |
136 | |
137 // Display all the comments on the same page. | |
138 $this->setCommentsPerPage(1000); | |
139 | |
140 // Create a node and three comments. | |
141 $node = $this->drupalCreateNode(['type' => 'article', 'promote' => 1]); | |
142 $comments = []; | |
143 $comments[] = $this->postComment($node, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
144 $comments[] = $this->postComment($node, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
145 $comments[] = $this->postComment($node, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
146 | |
147 // Post a reply to the second comment. | |
148 $this->drupalGet('comment/reply/node/' . $node->id() . '/comment/' . $comments[1]->id()); | |
149 $comments[] = $this->postComment(NULL, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
150 | |
151 // Post a reply to the first comment. | |
152 $this->drupalGet('comment/reply/node/' . $node->id() . '/comment/' . $comments[0]->id()); | |
153 $comments[] = $this->postComment(NULL, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
154 | |
155 // Post a reply to the last comment. | |
156 $this->drupalGet('comment/reply/node/' . $node->id() . '/comment/' . $comments[2]->id()); | |
157 $comments[] = $this->postComment(NULL, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
158 | |
159 // Post a reply to the second comment. | |
160 $this->drupalGet('comment/reply/node/' . $node->id() . '/comment/' . $comments[3]->id()); | |
161 $comments[] = $this->postComment(NULL, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
162 | |
163 // At this point, the comment tree is: | |
164 // - 0 | |
165 // - 4 | |
166 // - 1 | |
167 // - 3 | |
168 // - 6 | |
169 // - 2 | |
170 // - 5 | |
171 | |
172 $this->setCommentSettings('default_mode', CommentManagerInterface::COMMENT_MODE_FLAT, 'Comment paging changed.'); | |
173 | |
174 $expected_order = [ | |
175 0, | |
176 1, | |
177 2, | |
178 3, | |
179 4, | |
180 5, | |
181 6, | |
182 ]; | |
183 $this->drupalGet('node/' . $node->id()); | |
184 $this->assertCommentOrder($comments, $expected_order); | |
185 | |
186 $this->setCommentSettings('default_mode', CommentManagerInterface::COMMENT_MODE_THREADED, 'Switched to threaded mode.'); | |
187 | |
188 $expected_order = [ | |
189 0, | |
190 4, | |
191 1, | |
192 3, | |
193 6, | |
194 2, | |
195 5, | |
196 ]; | |
197 $this->drupalGet('node/' . $node->id()); | |
198 $this->assertCommentOrder($comments, $expected_order); | |
199 } | |
200 | |
201 /** | |
202 * Asserts that the comments are displayed in the correct order. | |
203 * | |
204 * @param \Drupal\comment\CommentInterface[] $comments | |
205 * An array of comments, must be of the type CommentInterface. | |
206 * @param array $expected_order | |
207 * An array of keys from $comments describing the expected order. | |
208 */ | |
209 public function assertCommentOrder(array $comments, array $expected_order) { | |
210 $expected_cids = []; | |
211 | |
212 // First, rekey the expected order by cid. | |
213 foreach ($expected_order as $key) { | |
214 $expected_cids[] = $comments[$key]->id(); | |
215 } | |
216 | |
217 $comment_anchors = $this->xpath('//a[starts-with(@id,"comment-")]'); | |
218 $result_order = []; | |
219 foreach ($comment_anchors as $anchor) { | |
220 $result_order[] = substr($anchor->getAttribute('id'), 8); | |
221 } | |
222 return $this->assertEqual($expected_cids, $result_order, format_string('Comment order: expected @expected, returned @returned.', ['@expected' => implode(',', $expected_cids), '@returned' => implode(',', $result_order)])); | |
223 } | |
224 | |
225 /** | |
226 * Tests calculation of first page with new comment. | |
227 */ | |
228 public function testCommentNewPageIndicator() { | |
229 $this->drupalLogin($this->adminUser); | |
230 | |
231 // Set comment variables. | |
232 $this->setCommentForm(TRUE); | |
233 $this->setCommentSubject(TRUE); | |
234 $this->setCommentPreview(DRUPAL_DISABLED); | |
235 | |
236 // Set comments to one per page so that we are able to test paging without | |
237 // needing to insert large numbers of comments. | |
238 $this->setCommentsPerPage(1); | |
239 | |
240 // Create a node and three comments. | |
241 $node = $this->drupalCreateNode(['type' => 'article', 'promote' => 1]); | |
242 $comments = []; | |
243 $comments[] = $this->postComment($node, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
244 $comments[] = $this->postComment($node, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
245 $comments[] = $this->postComment($node, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
246 | |
247 // Post a reply to the second comment. | |
248 $this->drupalGet('comment/reply/node/' . $node->id() . '/comment/' . $comments[1]->id()); | |
249 $comments[] = $this->postComment(NULL, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
250 | |
251 // Post a reply to the first comment. | |
252 $this->drupalGet('comment/reply/node/' . $node->id() . '/comment/' . $comments[0]->id()); | |
253 $comments[] = $this->postComment(NULL, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
254 | |
255 // Post a reply to the last comment. | |
256 $this->drupalGet('comment/reply/node/' . $node->id() . '/comment/' . $comments[2]->id()); | |
257 $comments[] = $this->postComment(NULL, $this->randomMachineName(), $this->randomMachineName(), TRUE); | |
258 | |
259 // At this point, the comment tree is: | |
260 // - 0 | |
261 // - 4 | |
262 // - 1 | |
263 // - 3 | |
264 // - 2 | |
265 // - 5 | |
266 | |
267 $this->setCommentSettings('default_mode', CommentManagerInterface::COMMENT_MODE_FLAT, 'Comment paging changed.'); | |
268 | |
269 $expected_pages = [ | |
270 // Page of comment 5 | |
271 1 => 5, | |
272 // Page of comment 4 | |
273 2 => 4, | |
274 // Page of comment 3 | |
275 3 => 3, | |
276 // Page of comment 2 | |
277 4 => 2, | |
278 // Page of comment 1 | |
279 5 => 1, | |
280 // Page of comment 0 | |
281 6 => 0, | |
282 ]; | |
283 | |
284 $node = Node::load($node->id()); | |
285 foreach ($expected_pages as $new_replies => $expected_page) { | |
286 $returned_page = \Drupal::entityManager()->getStorage('comment') | |
287 ->getNewCommentPageNumber($node->get('comment')->comment_count, $new_replies, $node, 'comment'); | |
288 $this->assertIdentical($expected_page, $returned_page, format_string('Flat mode, @new replies: expected page @expected, returned page @returned.', ['@new' => $new_replies, '@expected' => $expected_page, '@returned' => $returned_page])); | |
289 } | |
290 | |
291 $this->setCommentSettings('default_mode', CommentManagerInterface::COMMENT_MODE_THREADED, 'Switched to threaded mode.'); | |
292 | |
293 $expected_pages = [ | |
294 // Page of comment 5 | |
295 1 => 5, | |
296 // Page of comment 4 | |
297 2 => 1, | |
298 // Page of comment 4 | |
299 3 => 1, | |
300 // Page of comment 4 | |
301 4 => 1, | |
302 // Page of comment 4 | |
303 5 => 1, | |
304 // Page of comment 0 | |
305 6 => 0, | |
306 ]; | |
307 | |
308 \Drupal::entityManager()->getStorage('node')->resetCache([$node->id()]); | |
309 $node = Node::load($node->id()); | |
310 foreach ($expected_pages as $new_replies => $expected_page) { | |
311 $returned_page = \Drupal::entityManager()->getStorage('comment') | |
312 ->getNewCommentPageNumber($node->get('comment')->comment_count, $new_replies, $node, 'comment'); | |
313 $this->assertEqual($expected_page, $returned_page, format_string('Threaded mode, @new replies: expected page @expected, returned page @returned.', ['@new' => $new_replies, '@expected' => $expected_page, '@returned' => $returned_page])); | |
314 } | |
315 } | |
316 | |
317 /** | |
318 * Confirms comment paging works correctly with two pagers. | |
319 */ | |
320 public function testTwoPagers() { | |
321 // Add another field to article content-type. | |
322 $this->addDefaultCommentField('node', 'article', 'comment_2'); | |
323 // Set default to display comment list with unique pager id. | |
324 entity_get_display('node', 'article', 'default') | |
325 ->setComponent('comment_2', [ | |
326 'label' => 'hidden', | |
327 'type' => 'comment_default', | |
328 'weight' => 30, | |
329 'settings' => [ | |
330 'pager_id' => 1, | |
331 'view_mode' => 'default', | |
332 ], | |
333 ]) | |
334 ->save(); | |
335 | |
336 // Make sure pager appears in formatter summary and settings form. | |
337 $account = $this->drupalCreateUser(['administer node display']); | |
338 $this->drupalLogin($account); | |
339 $this->drupalGet('admin/structure/types/manage/article/display'); | |
340 $this->assertNoText(t('Pager ID: @id', ['@id' => 0]), 'No summary for standard pager'); | |
341 $this->assertText(t('Pager ID: @id', ['@id' => 1])); | |
342 $this->drupalPostForm(NULL, [], 'comment_settings_edit'); | |
343 // Change default pager to 2. | |
344 $this->drupalPostForm(NULL, ['fields[comment][settings_edit_form][settings][pager_id]' => 2], t('Save')); | |
345 $this->assertText(t('Pager ID: @id', ['@id' => 2])); | |
346 // Revert the changes. | |
347 $this->drupalPostForm(NULL, [], 'comment_settings_edit'); | |
348 $this->drupalPostForm(NULL, ['fields[comment][settings_edit_form][settings][pager_id]' => 0], t('Save')); | |
349 $this->assertNoText(t('Pager ID: @id', ['@id' => 0]), 'No summary for standard pager'); | |
350 | |
351 $this->drupalLogin($this->adminUser); | |
352 | |
353 // Add a new node with both comment fields open. | |
354 $node = $this->drupalCreateNode(['type' => 'article', 'promote' => 1, 'uid' => $this->webUser->id()]); | |
355 // Set comment options. | |
356 $comments = []; | |
357 foreach (['comment', 'comment_2'] as $field_name) { | |
358 $this->setCommentForm(TRUE, $field_name); | |
359 $this->setCommentPreview(DRUPAL_OPTIONAL, $field_name); | |
360 $this->setCommentSettings('default_mode', CommentManagerInterface::COMMENT_MODE_FLAT, 'Comment paging changed.', $field_name); | |
361 | |
362 // Set comments to one per page so that we are able to test paging without | |
363 // needing to insert large numbers of comments. | |
364 $this->setCommentsPerPage(1, $field_name); | |
365 for ($i = 0; $i < 3; $i++) { | |
366 $comment = t('Comment @count on field @field', [ | |
367 '@count' => $i + 1, | |
368 '@field' => $field_name, | |
369 ]); | |
370 $comments[] = $this->postComment($node, $comment, $comment, TRUE, $field_name); | |
371 } | |
372 } | |
373 | |
374 // Check the first page of the node, and confirm the correct comments are | |
375 // shown. | |
376 $this->drupalGet('node/' . $node->id()); | |
377 $this->assertRaw(t('next'), 'Paging links found.'); | |
378 $this->assertRaw('Comment 1 on field comment'); | |
379 $this->assertRaw('Comment 1 on field comment_2'); | |
380 // Navigate to next page of field 1. | |
381 $this->clickLinkWithXPath('//h3/a[normalize-space(text())=:label]/ancestor::section[1]//a[@rel="next"]', [':label' => 'Comment 1 on field comment']); | |
382 // Check only one pager updated. | |
383 $this->assertRaw('Comment 2 on field comment'); | |
384 $this->assertRaw('Comment 1 on field comment_2'); | |
385 // Return to page 1. | |
386 $this->drupalGet('node/' . $node->id()); | |
387 // Navigate to next page of field 2. | |
388 $this->clickLinkWithXPath('//h3/a[normalize-space(text())=:label]/ancestor::section[1]//a[@rel="next"]', [':label' => 'Comment 1 on field comment_2']); | |
389 // Check only one pager updated. | |
390 $this->assertRaw('Comment 1 on field comment'); | |
391 $this->assertRaw('Comment 2 on field comment_2'); | |
392 // Navigate to next page of field 1. | |
393 $this->clickLinkWithXPath('//h3/a[normalize-space(text())=:label]/ancestor::section[1]//a[@rel="next"]', [':label' => 'Comment 1 on field comment']); | |
394 // Check only one pager updated. | |
395 $this->assertRaw('Comment 2 on field comment'); | |
396 $this->assertRaw('Comment 2 on field comment_2'); | |
397 } | |
398 | |
399 /** | |
400 * Follows a link found at a give xpath query. | |
401 * | |
402 * Will click the first link found with the given xpath query by default, | |
403 * or a later one if an index is given. | |
404 * | |
405 * If the link is discovered and clicked, the test passes. Fail otherwise. | |
406 * | |
407 * @param string $xpath | |
408 * Xpath query that targets an anchor tag, or set of anchor tags. | |
409 * @param array $arguments | |
410 * An array of arguments with keys in the form ':name' matching the | |
411 * placeholders in the query. The values may be either strings or numeric | |
412 * values. | |
413 * @param int $index | |
414 * Link position counting from zero. | |
415 * | |
416 * @return string|false | |
417 * Page contents on success, or FALSE on failure. | |
418 * | |
419 * @see WebTestBase::clickLink() | |
420 */ | |
421 protected function clickLinkWithXPath($xpath, $arguments = [], $index = 0) { | |
422 $url_before = $this->getUrl(); | |
423 $urls = $this->xpath($xpath, $arguments); | |
424 if (isset($urls[$index])) { | |
425 $url_target = $this->getAbsoluteUrl($urls[$index]->getAttribute('href')); | |
426 $this->pass(new FormattableMarkup('Clicked link %label (@url_target) from @url_before', ['%label' => $xpath, '@url_target' => $url_target, '@url_before' => $url_before]), 'Browser'); | |
427 return $this->drupalGet($url_target); | |
428 } | |
429 $this->fail(new FormattableMarkup('Link %label does not exist on @url_before', ['%label' => $xpath, '@url_before' => $url_before]), 'Browser'); | |
430 return FALSE; | |
431 } | |
432 | |
433 } |