Mercurial > hg > isophonics-drupal-site
comparison core/modules/media/tests/src/Functional/MediaUiFunctionalTest.php @ 14:1fec387a4317
Update Drupal core to 8.5.2 via Composer
author | Chris Cannam |
---|---|
date | Mon, 23 Apr 2018 09:46:53 +0100 |
parents | 4c8ae668cc8c |
children | c2387f117808 |
comparison
equal
deleted
inserted
replaced
13:5fb285c0d0e3 | 14:1fec387a4317 |
---|---|
1 <?php | 1 <?php |
2 | 2 |
3 namespace Drupal\Tests\media\Functional; | 3 namespace Drupal\Tests\media\Functional; |
4 | 4 |
5 use Behat\Mink\Element\NodeElement; | |
5 use Drupal\media\Entity\Media; | 6 use Drupal\media\Entity\Media; |
6 use Drupal\media\Entity\MediaType; | 7 use Drupal\Core\Field\FieldStorageDefinitionInterface; |
8 use Drupal\Core\Url; | |
9 use Drupal\field\Entity\FieldConfig; | |
10 use Drupal\field\Entity\FieldStorageConfig; | |
7 | 11 |
8 /** | 12 /** |
9 * Ensures that media UI works correctly. | 13 * Ensures that media UI works correctly. |
10 * | 14 * |
11 * @group media | 15 * @group media |
27 */ | 31 */ |
28 protected function setUp() { | 32 protected function setUp() { |
29 parent::setUp(); | 33 parent::setUp(); |
30 $this->drupalPlaceBlock('local_actions_block'); | 34 $this->drupalPlaceBlock('local_actions_block'); |
31 $this->drupalPlaceBlock('local_tasks_block'); | 35 $this->drupalPlaceBlock('local_tasks_block'); |
32 | |
33 // We need to test without any default configuration in place. | |
34 // @TODO: Remove this when https://www.drupal.org/node/2883813 lands. | |
35 MediaType::load('file')->delete(); | |
36 MediaType::load('image')->delete(); | |
37 } | 36 } |
38 | 37 |
39 /** | 38 /** |
40 * Tests the media actions (add/edit/delete). | 39 * Tests the media actions (add/edit/delete). |
41 */ | 40 */ |
57 // Tests media add form. | 56 // Tests media add form. |
58 $media_name = $this->randomMachineName(); | 57 $media_name = $this->randomMachineName(); |
59 $page->fillField('name[0][value]', $media_name); | 58 $page->fillField('name[0][value]', $media_name); |
60 $revision_log_message = $this->randomString(); | 59 $revision_log_message = $this->randomString(); |
61 $page->fillField('revision_log_message[0][value]', $revision_log_message); | 60 $page->fillField('revision_log_message[0][value]', $revision_log_message); |
61 $source_field = $this->randomString(); | |
62 $page->fillField('field_media_test[0][value]', $source_field); | |
62 $page->pressButton('Save'); | 63 $page->pressButton('Save'); |
63 $media_id = $this->container->get('entity.query')->get('media')->execute(); | 64 $media_id = $this->container->get('entity.query')->get('media')->execute(); |
64 $media_id = reset($media_id); | 65 $media_id = reset($media_id); |
65 /** @var \Drupal\media\MediaInterface $media */ | 66 /** @var \Drupal\media\MediaInterface $media */ |
66 $media = $this->container->get('entity_type.manager') | 67 $media = $this->container->get('entity_type.manager') |
177 $this->drupalGet('media/' . $second_media_item->id()); | 178 $this->drupalGet('media/' . $second_media_item->id()); |
178 $assert_session->statusCodeEquals(200); | 179 $assert_session->statusCodeEquals(200); |
179 $assert_session->pageTextContains($second_media_item->getName()); | 180 $assert_session->pageTextContains($second_media_item->getName()); |
180 } | 181 } |
181 | 182 |
183 /** | |
184 * Test that media in ER fields use the Rendered Entity formatter by default. | |
185 */ | |
186 public function testRenderedEntityReferencedMedia() { | |
187 $page = $this->getSession()->getPage(); | |
188 $assert_session = $this->assertSession(); | |
189 | |
190 $this->drupalCreateContentType(['type' => 'page', 'name' => 'Page']); | |
191 $this->drupalGet('/admin/structure/types/manage/page/fields/add-field'); | |
192 $page->selectFieldOption('new_storage_type', 'field_ui:entity_reference:media'); | |
193 $page->fillField('label', 'Foo field'); | |
194 $page->fillField('field_name', 'foo_field'); | |
195 $page->pressButton('Save and continue'); | |
196 $this->drupalGet('/admin/structure/types/manage/page/display'); | |
197 $assert_session->fieldValueEquals('fields[field_foo_field][type]', 'entity_reference_entity_view'); | |
198 } | |
199 | |
200 /** | |
201 * Data provider for testMediaReferenceWidget(). | |
202 * | |
203 * @return array[] | |
204 * Test data. See testMediaReferenceWidget() for the child array structure. | |
205 */ | |
206 public function providerTestMediaReferenceWidget() { | |
207 return [ | |
208 // Single-value fields with a single media type and the default widget: | |
209 // - The user can create and list the media. | |
210 'single_value:single_type:create_list' => [1, [TRUE], TRUE], | |
211 // - The user can list but not create the media. | |
212 'single_value:single_type:list' => [1, [FALSE], TRUE], | |
213 // - The user can create but not list the media. | |
214 'single_value:single_type:create' => [1, [TRUE], FALSE], | |
215 // - The user can neither create nor list the media. | |
216 'single_value:single_type' => [1, [FALSE], FALSE], | |
217 | |
218 // Single-value fields with the tags-style widget: | |
219 // - The user can create and list the media. | |
220 'single_value:single_type:create_list:tags' => [1, [TRUE], TRUE, 'entity_reference_autocomplete_tags'], | |
221 // - The user can list but not create the media. | |
222 'single_value:single_type:list:tags' => [1, [FALSE], TRUE, 'entity_reference_autocomplete_tags'], | |
223 // - The user can create but not list the media. | |
224 'single_value:single_type:create:tags' => [1, [TRUE], FALSE, 'entity_reference_autocomplete_tags'], | |
225 // - The user can neither create nor list the media. | |
226 'single_value:single_type:tags' => [1, [FALSE], FALSE, 'entity_reference_autocomplete_tags'], | |
227 | |
228 // Single-value fields with two media types: | |
229 // - The user can create both types. | |
230 'single_value:two_type:create2_list' => [1, [TRUE, TRUE], TRUE], | |
231 // - The user can create only one type. | |
232 'single_value:two_type:create1_list' => [1, [TRUE, FALSE], TRUE], | |
233 // - The user cannot create either type. | |
234 'single_value:two_type:list' => [1, [FALSE, FALSE], TRUE], | |
235 | |
236 // Multiple-value field with a cardinality of 3, with media the user can | |
237 // create and list. | |
238 'multi_value:single_type:create_list' => [3, [TRUE], TRUE], | |
239 // The same, with the tags field. | |
240 'multi-value:single_type:create_list:tags' => [3, [TRUE], TRUE, 'entity_reference_autocomplete_tags'], | |
241 | |
242 // Unlimited value field. | |
243 'unlimited_value:single_type:create_list' => [FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED, [TRUE], TRUE], | |
244 // Unlimited value field with the tags widget. | |
245 'unlimited_value:single_type:create_list' => [FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED, [TRUE], TRUE, 'entity_reference_autocomplete_tags'], | |
246 ]; | |
247 } | |
248 | |
249 /** | |
250 * Tests the default autocomplete widgets for media reference fields. | |
251 * | |
252 * @param int $cardinality | |
253 * The field cardinality. | |
254 * @param bool[] $media_type_create_access | |
255 * An array of booleans indicating whether to grant the test user create | |
256 * access for each media type. A media type is created automatically for | |
257 * each; for example, an array [TRUE, FALSE] would create two media types, | |
258 * one that allows the user to create media and a second that does not. | |
259 * @param bool $list_access | |
260 * Whether to grant the test user access to list media. | |
261 * | |
262 * @see media_field_widget_entity_reference_autocomplete_form_alter() | |
263 * @see media_field_widget_multiple_entity_reference_autocomplete_form_alter() | |
264 * | |
265 * @dataProvider providerTestMediaReferenceWidget | |
266 */ | |
267 public function testMediaReferenceWidget($cardinality, array $media_type_create_access, $list_access, $widget_id = 'entity_reference_autocomplete') { | |
268 $assert_session = $this->assertSession(); | |
269 | |
270 // Create two content types. | |
271 $non_media_content_type = $this->createContentType(); | |
272 $content_type = $this->createContentType(); | |
273 | |
274 // Create some media types. | |
275 $media_types = []; | |
276 $permissions = []; | |
277 $create_media_types = []; | |
278 foreach ($media_type_create_access as $id => $access) { | |
279 if ($access) { | |
280 $create_media_types[] = "media_type_$id"; | |
281 $permissions[] = "create media_type_$id media"; | |
282 } | |
283 $this->createMediaType(['bundle' => "media_type_$id"]); | |
284 $media_types["media_type_$id"] = "media_type_$id"; | |
285 } | |
286 | |
287 // Create a user that can create content of the type, with other | |
288 // permissions as given by the data provider. | |
289 $permissions[] = "create {$content_type->id()} content"; | |
290 if ($list_access) { | |
291 $permissions[] = "access media overview"; | |
292 } | |
293 $test_user = $this->drupalCreateUser($permissions); | |
294 | |
295 // Create a non-media entity reference. | |
296 $non_media_storage = FieldStorageConfig::create([ | |
297 'field_name' => 'field_not_a_media_field', | |
298 'entity_type' => 'node', | |
299 'type' => 'entity_reference', | |
300 'cardinality' => FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED, | |
301 'settings' => [ | |
302 'target_type' => 'node', | |
303 ], | |
304 ]); | |
305 $non_media_storage->save(); | |
306 $non_media_field = FieldConfig::create([ | |
307 'label' => 'No media here!', | |
308 'field_storage' => $non_media_storage, | |
309 'entity_type' => 'node', | |
310 'bundle' => $non_media_content_type->id(), | |
311 'settings' => [ | |
312 'handler' => 'default', | |
313 'handler_settings' => [ | |
314 'target_bundles' => [ | |
315 $non_media_content_type->id() => $non_media_content_type->id(), | |
316 ], | |
317 ], | |
318 ], | |
319 ]); | |
320 $non_media_field->save(); | |
321 \Drupal::entityTypeManager() | |
322 ->getStorage('entity_form_display') | |
323 ->load('node.' . $non_media_content_type->id() . '.default') | |
324 ->setComponent('field_not_a_media_field', [ | |
325 'type' => $widget_id, | |
326 ]) | |
327 ->save(); | |
328 | |
329 // Create a media field through the user interface to ensure that the | |
330 // help text handling does not break the default value entry on the field | |
331 // settings form. | |
332 // Using drupalPostForm() to avoid dealing with JavaScript on the previous | |
333 // page in the field creation. | |
334 $edit = [ | |
335 'new_storage_type' => 'field_ui:entity_reference:media', | |
336 'label' => "Media (cardinality $cardinality)", | |
337 'field_name' => 'media_reference', | |
338 ]; | |
339 $this->drupalPostForm("admin/structure/types/manage/{$content_type->id()}/fields/add-field", $edit, 'Save and continue'); | |
340 $edit = []; | |
341 foreach ($media_types as $type) { | |
342 $edit["settings[handler_settings][target_bundles][$type]"] = TRUE; | |
343 } | |
344 $this->drupalPostForm("admin/structure/types/manage/{$content_type->id()}/fields/node.{$content_type->id()}.field_media_reference", $edit, "Save settings"); | |
345 \Drupal::entityTypeManager() | |
346 ->getStorage('entity_form_display') | |
347 ->load('node.' . $content_type->id() . '.default') | |
348 ->setComponent('field_media_reference', [ | |
349 'type' => $widget_id, | |
350 ]) | |
351 ->save(); | |
352 | |
353 // Some of the expected texts. | |
354 $create_help = 'Create your media on the media add page (opens a new window), then add it by name to the field below.'; | |
355 $list_text = 'See the media list (opens a new window) to help locate media.'; | |
356 $use_help = 'Type part of the media name.'; | |
357 $create_header = "Create new media"; | |
358 $use_header = "Use existing media"; | |
359 | |
360 // First check that none of the help texts are on the non-media content. | |
361 $this->drupalGet("/node/add/{$non_media_content_type->id()}"); | |
362 $this->assertNoHelpTexts([ | |
363 $create_header, | |
364 $create_help, | |
365 $use_header, | |
366 $use_help, | |
367 $list_text, | |
368 'Allowed media types:', | |
369 ]); | |
370 | |
371 // Now, check that the widget displays the expected help text under the | |
372 // given conditions for the test user. | |
373 $this->drupalLogin($test_user); | |
374 $this->drupalGet("/node/add/{$content_type->id()}"); | |
375 | |
376 // Specific expected help texts for the media field. | |
377 $create_header = "Create new media"; | |
378 $use_header = "Use existing media"; | |
379 $type_list = 'Allowed media types: ' . implode(", ", array_keys($media_types)); | |
380 | |
381 $fieldset_selector = '#edit-field-media-reference-wrapper fieldset'; | |
382 $fieldset = $assert_session->elementExists('css', $fieldset_selector); | |
383 | |
384 $this->assertSame("Media (cardinality $cardinality)", $assert_session->elementExists('css', 'legend', $fieldset)->getText()); | |
385 | |
386 // Assert text that should be displayed regardless of other access. | |
387 $this->assertHelpTexts([$use_header, $use_help, $type_list], $fieldset_selector); | |
388 | |
389 // The entire section for creating new media should only be displayed if | |
390 // the user can create at least one media of the type. | |
391 if ($create_media_types) { | |
392 if (count($create_media_types) === 1) { | |
393 $url = Url::fromRoute('entity.media.add_form')->setRouteParameter('media_type', $create_media_types[0]); | |
394 } | |
395 else { | |
396 $url = Url::fromRoute('entity.media.add_page'); | |
397 } | |
398 $this->assertHelpTexts([$create_header, $create_help], $fieldset_selector); | |
399 $this->assertHelpLink( | |
400 $fieldset, | |
401 'media add page', | |
402 [ | |
403 'target' => '_blank', | |
404 'href' => $url->toString(), | |
405 ] | |
406 ); | |
407 } | |
408 else { | |
409 $this->assertNoHelpTexts([$create_header, $create_help]); | |
410 $this->assertNoHelpLink($fieldset, 'media add page'); | |
411 } | |
412 | |
413 if ($list_access) { | |
414 $this->assertHelpTexts([$list_text], $fieldset_selector); | |
415 $this->assertHelpLink( | |
416 $fieldset, | |
417 'media list', | |
418 [ | |
419 'target' => '_blank', | |
420 'href' => Url::fromRoute('entity.media.collection')->toString(), | |
421 ] | |
422 ); | |
423 } | |
424 else { | |
425 $this->assertNoHelpTexts([$list_text]); | |
426 $this->assertNoHelpLink($fieldset, 'media list'); | |
427 } | |
428 } | |
429 | |
430 /** | |
431 * Asserts that the given texts are present exactly once. | |
432 * | |
433 * @param string[] $texts | |
434 * A list of the help texts to check. | |
435 * @param string $selector | |
436 * (optional) The selector to search. | |
437 */ | |
438 public function assertHelpTexts(array $texts, $selector = '') { | |
439 $assert_session = $this->assertSession(); | |
440 foreach ($texts as $text) { | |
441 // We only want to escape single quotes, so use str_replace() rather than | |
442 // addslashes(). | |
443 $text = str_replace("'", "\'", $text); | |
444 if ($selector) { | |
445 $assert_session->elementsCount('css', $selector . ":contains('$text')", 1); | |
446 } | |
447 else { | |
448 $assert_session->pageTextContains($text); | |
449 } | |
450 } | |
451 } | |
452 | |
453 /** | |
454 * Asserts that none of the given texts are present. | |
455 * | |
456 * @param string[] $texts | |
457 * A list of the help texts to check. | |
458 */ | |
459 public function assertNoHelpTexts(array $texts) { | |
460 $assert_session = $this->assertSession(); | |
461 foreach ($texts as $text) { | |
462 $assert_session->pageTextNotContains($text); | |
463 } | |
464 } | |
465 | |
466 /** | |
467 * Asserts whether a given link is present. | |
468 * | |
469 * @param \Behat\Mink\Element\NodeElement $element | |
470 * The element to search. | |
471 * @param string $text | |
472 * The link text. | |
473 * @param string[] $attributes | |
474 * An associative array of any expected attributes, keyed by the | |
475 * attribute name. | |
476 */ | |
477 protected function assertHelpLink(NodeElement $element, $text, array $attributes = []) { | |
478 // Find all the links inside the element. | |
479 $link = $element->findLink($text); | |
480 | |
481 $this->assertNotEmpty($link); | |
482 foreach ($attributes as $attribute => $value) { | |
483 $this->assertEquals($link->getAttribute($attribute), $value); | |
484 } | |
485 } | |
486 | |
487 /** | |
488 * Asserts that a given link is not present. | |
489 * | |
490 * @param \Behat\Mink\Element\NodeElement $element | |
491 * The element to search. | |
492 * @param string $text | |
493 * The link text. | |
494 */ | |
495 protected function assertNoHelpLink(NodeElement $element, $text) { | |
496 $assert_session = $this->assertSession(); | |
497 // Assert that the link and its text are not present anywhere on the page. | |
498 $assert_session->elementNotExists('named', ['link', $text], $element); | |
499 $assert_session->pageTextNotContains($text); | |
500 } | |
501 | |
502 /** | |
503 * Test the media collection route. | |
504 */ | |
505 public function testMediaCollectionRoute() { | |
506 /** @var \Drupal\Core\Entity\EntityStorageInterface $media_storage */ | |
507 $media_storage = $this->container->get('entity_type.manager')->getStorage('media'); | |
508 | |
509 $this->container->get('module_installer')->uninstall(['views']); | |
510 | |
511 // Create a media type and media item. | |
512 $media_type = $this->createMediaType(); | |
513 $media = $media_storage->create([ | |
514 'bundle' => $media_type->id(), | |
515 'name' => 'Unnamed', | |
516 ]); | |
517 $media->save(); | |
518 | |
519 $this->drupalGet($media->toUrl('collection')); | |
520 | |
521 $assert_session = $this->assertSession(); | |
522 | |
523 // Media list table exists. | |
524 $assert_session->elementExists('css', 'th:contains("Media Name")'); | |
525 $assert_session->elementExists('css', 'th:contains("Type")'); | |
526 $assert_session->elementExists('css', 'th:contains("Operations")'); | |
527 // Media item is present. | |
528 $assert_session->elementExists('css', 'td:contains("Unnamed")'); | |
529 } | |
530 | |
182 } | 531 } |