Loading core/modules/contextual/js/contextual.es6.js +3 −1 Original line number Diff line number Diff line Loading @@ -186,7 +186,9 @@ // Drupal.contextual.collection. window.setTimeout(() => { initContextual( $context.find(`[data-contextual-id="${contextualID.id}"]`), $context .find(`[data-contextual-id="${contextualID.id}"]:empty`) .eq(0), html, ); }); Loading core/modules/contextual/js/contextual.js +1 −1 Original line number Diff line number Diff line Loading @@ -108,7 +108,7 @@ if (html && html.length) { window.setTimeout(function () { initContextual($context.find("[data-contextual-id=\"".concat(contextualID.id, "\"]")), html); initContextual($context.find("[data-contextual-id=\"".concat(contextualID.id, "\"]:empty")).eq(0), html); }); return; } Loading core/modules/contextual/tests/modules/contextual_test/config/optional/views.view.contextual_recent.yml 0 → 100644 +327 −0 Original line number Diff line number Diff line langcode: en status: true dependencies: module: - node - user id: contextual_recent label: 'Recent content' module: node description: 'Recent content.' tag: default base_table: node_field_data base_field: nid display: default: display_plugin: default id: default display_title: Master position: 0 display_options: access: type: perm options: perm: 'access content' cache: type: tag options: { } query: type: views_query options: disable_sql_rewrite: false distinct: false replica: false query_comment: '' query_tags: { } exposed_form: type: basic options: submit_button: Apply reset_button: false reset_button_label: Reset exposed_sorts_label: 'Sort by' expose_sort_order: true sort_asc_label: Asc sort_desc_label: Desc pager: type: some options: items_per_page: 10 offset: 0 style: type: html_list options: grouping: { } row_class: '' default_row_class: true type: ul wrapper_class: item-list class: '' row: type: fields fields: title: id: title table: node_field_data field: title entity_type: node entity_field: title label: '' exclude: false alter: alter_text: false make_link: false absolute: false trim: false word_boundary: false ellipsis: false strip_tags: false html: false hide_empty: false empty_zero: false relationship: none group_type: group admin_label: '' element_type: '' element_class: '' element_label_type: '' element_label_class: '' element_label_colon: false element_wrapper_type: '' element_wrapper_class: '' element_default_classes: true empty: '' hide_alter_empty: true type: string settings: link_to_entity: true plugin_id: field changed: id: changed table: node_field_data field: changed relationship: none group_type: group admin_label: '' label: '' exclude: false alter: alter_text: false text: '' make_link: false path: '' absolute: false external: false replace_spaces: false path_case: none trim_whitespace: false alt: '' rel: '' link_class: '' prefix: '' suffix: '' target: '' nl2br: false max_length: 0 word_boundary: true ellipsis: true more_link: false more_link_text: '' more_link_path: '' strip_tags: false trim: false preserve_tags: '' html: false element_type: '' element_class: '' element_label_type: '' element_label_class: '' element_label_colon: false element_wrapper_type: '' element_wrapper_class: '' element_default_classes: true empty: '' hide_empty: false empty_zero: false hide_alter_empty: true click_sort_column: value type: timestamp_ago settings: { } group_column: value group_columns: { } group_rows: true delta_limit: 0 delta_offset: 0 delta_reversed: false delta_first_last: false multi_type: separator separator: ', ' field_api_classes: false entity_type: node entity_field: changed plugin_id: field filters: status_extra: id: status_extra table: node_field_data field: status_extra relationship: none group_type: group admin_label: '' operator: '=' value: false group: 1 exposed: false expose: operator_id: '' label: '' description: '' use_operator: false operator: '' identifier: '' required: false remember: false multiple: false remember_roles: authenticated: authenticated operator_limit_selection: false operator_list: { } is_grouped: false group_info: label: '' description: '' identifier: '' optional: true widget: select multiple: false remember: false default_group: All default_group_multiple: { } group_items: { } entity_type: node plugin_id: node_status langcode: id: langcode table: node_field_data field: langcode relationship: none group_type: group admin_label: '' operator: in value: '***LANGUAGE_language_content***': '***LANGUAGE_language_content***' group: 1 exposed: false expose: operator_id: '' label: '' description: '' use_operator: false operator: '' identifier: '' required: false remember: false multiple: false remember_roles: authenticated: authenticated reduce: false operator_limit_selection: false operator_list: { } is_grouped: false group_info: label: '' description: '' identifier: '' optional: true widget: select multiple: false remember: false default_group: All default_group_multiple: { } group_items: { } entity_type: node entity_field: langcode plugin_id: language sorts: changed: id: changed table: node_field_data field: changed relationship: none group_type: group admin_label: '' order: DESC exposed: false expose: label: '' granularity: second entity_type: node entity_field: changed plugin_id: date title: 'Recent content' header: { } footer: { } empty: area_text_custom: id: area_text_custom table: views field: area_text_custom relationship: none group_type: group admin_label: '' empty: true tokenize: false content: 'No content available.' plugin_id: text_custom relationships: uid: id: uid table: node_field_data field: uid relationship: none group_type: group admin_label: author required: true entity_type: node entity_field: uid plugin_id: standard arguments: { } display_extenders: { } use_more: false use_more_always: false use_more_text: More link_url: '' link_display: '0' cache_metadata: contexts: - 'languages:language_content' - 'languages:language_interface' - user - 'user.node_grants:view' - user.permissions max-age: -1 tags: { } block_1: display_plugin: block id: block_1 display_title: Block position: 2 display_options: display_extenders: { } defaults: style: false row: false row: type: 'entity:node' options: relationship: none view_mode: teaser cache_metadata: contexts: - 'languages:language_content' - 'languages:language_interface' - user - 'user.node_grants:view' - user.permissions max-age: -1 tags: { } core/modules/contextual/tests/src/FunctionalJavascript/DuplicateContextualLinksTest.php 0 → 100644 +58 −0 Original line number Diff line number Diff line <?php namespace Drupal\Tests\contextual\FunctionalJavascript; use Drupal\FunctionalJavascriptTests\WebDriverTestBase; /** * Tests the UI for correct contextual links. * * @group contextual */ class DuplicateContextualLinksTest extends WebDriverTestBase { /** * {@inheritdoc} */ public static $modules = [ 'block', 'contextual', 'node', 'views', 'views_ui', 'contextual_test', ]; /** * {@inheritdoc} */ protected $defaultTheme = 'stark'; /** * Tests the contextual links with same id. */ public function testSameContextualLinks() { $this->drupalPlaceBlock('views_block:contextual_recent-block_1', ['id' => 'first']); $this->drupalPlaceBlock('views_block:contextual_recent-block_1', ['id' => 'second']); $this->drupalCreateContentType(['type' => 'page']); $this->drupalCreateNode(); $this->drupalLogin($this->drupalCreateUser([ 'access content', 'access contextual links', 'administer nodes', 'administer blocks', 'administer views', 'edit any page content', ])); // Ensure same contextual links work correct with fresh and cached page. foreach (['fresh', 'cached'] as $state) { $this->drupalGet('user'); $contextual_id = '[data-contextual-id^="node:node=1"]'; $this->assertJsCondition("(typeof jQuery !== 'undefined' && jQuery('[data-contextual-id]:empty').length === 0)"); $this->getSession()->executeScript("jQuery('#block-first $contextual_id .trigger').trigger('click');"); $contextual_links = $this->assertSession()->waitForElementVisible('css', "#block-first $contextual_id .contextual-links"); $this->assertTrue($contextual_links->isVisible(), "Contextual links are visible with $state page."); } } } Loading
core/modules/contextual/js/contextual.es6.js +3 −1 Original line number Diff line number Diff line Loading @@ -186,7 +186,9 @@ // Drupal.contextual.collection. window.setTimeout(() => { initContextual( $context.find(`[data-contextual-id="${contextualID.id}"]`), $context .find(`[data-contextual-id="${contextualID.id}"]:empty`) .eq(0), html, ); }); Loading
core/modules/contextual/js/contextual.js +1 −1 Original line number Diff line number Diff line Loading @@ -108,7 +108,7 @@ if (html && html.length) { window.setTimeout(function () { initContextual($context.find("[data-contextual-id=\"".concat(contextualID.id, "\"]")), html); initContextual($context.find("[data-contextual-id=\"".concat(contextualID.id, "\"]:empty")).eq(0), html); }); return; } Loading
core/modules/contextual/tests/modules/contextual_test/config/optional/views.view.contextual_recent.yml 0 → 100644 +327 −0 Original line number Diff line number Diff line langcode: en status: true dependencies: module: - node - user id: contextual_recent label: 'Recent content' module: node description: 'Recent content.' tag: default base_table: node_field_data base_field: nid display: default: display_plugin: default id: default display_title: Master position: 0 display_options: access: type: perm options: perm: 'access content' cache: type: tag options: { } query: type: views_query options: disable_sql_rewrite: false distinct: false replica: false query_comment: '' query_tags: { } exposed_form: type: basic options: submit_button: Apply reset_button: false reset_button_label: Reset exposed_sorts_label: 'Sort by' expose_sort_order: true sort_asc_label: Asc sort_desc_label: Desc pager: type: some options: items_per_page: 10 offset: 0 style: type: html_list options: grouping: { } row_class: '' default_row_class: true type: ul wrapper_class: item-list class: '' row: type: fields fields: title: id: title table: node_field_data field: title entity_type: node entity_field: title label: '' exclude: false alter: alter_text: false make_link: false absolute: false trim: false word_boundary: false ellipsis: false strip_tags: false html: false hide_empty: false empty_zero: false relationship: none group_type: group admin_label: '' element_type: '' element_class: '' element_label_type: '' element_label_class: '' element_label_colon: false element_wrapper_type: '' element_wrapper_class: '' element_default_classes: true empty: '' hide_alter_empty: true type: string settings: link_to_entity: true plugin_id: field changed: id: changed table: node_field_data field: changed relationship: none group_type: group admin_label: '' label: '' exclude: false alter: alter_text: false text: '' make_link: false path: '' absolute: false external: false replace_spaces: false path_case: none trim_whitespace: false alt: '' rel: '' link_class: '' prefix: '' suffix: '' target: '' nl2br: false max_length: 0 word_boundary: true ellipsis: true more_link: false more_link_text: '' more_link_path: '' strip_tags: false trim: false preserve_tags: '' html: false element_type: '' element_class: '' element_label_type: '' element_label_class: '' element_label_colon: false element_wrapper_type: '' element_wrapper_class: '' element_default_classes: true empty: '' hide_empty: false empty_zero: false hide_alter_empty: true click_sort_column: value type: timestamp_ago settings: { } group_column: value group_columns: { } group_rows: true delta_limit: 0 delta_offset: 0 delta_reversed: false delta_first_last: false multi_type: separator separator: ', ' field_api_classes: false entity_type: node entity_field: changed plugin_id: field filters: status_extra: id: status_extra table: node_field_data field: status_extra relationship: none group_type: group admin_label: '' operator: '=' value: false group: 1 exposed: false expose: operator_id: '' label: '' description: '' use_operator: false operator: '' identifier: '' required: false remember: false multiple: false remember_roles: authenticated: authenticated operator_limit_selection: false operator_list: { } is_grouped: false group_info: label: '' description: '' identifier: '' optional: true widget: select multiple: false remember: false default_group: All default_group_multiple: { } group_items: { } entity_type: node plugin_id: node_status langcode: id: langcode table: node_field_data field: langcode relationship: none group_type: group admin_label: '' operator: in value: '***LANGUAGE_language_content***': '***LANGUAGE_language_content***' group: 1 exposed: false expose: operator_id: '' label: '' description: '' use_operator: false operator: '' identifier: '' required: false remember: false multiple: false remember_roles: authenticated: authenticated reduce: false operator_limit_selection: false operator_list: { } is_grouped: false group_info: label: '' description: '' identifier: '' optional: true widget: select multiple: false remember: false default_group: All default_group_multiple: { } group_items: { } entity_type: node entity_field: langcode plugin_id: language sorts: changed: id: changed table: node_field_data field: changed relationship: none group_type: group admin_label: '' order: DESC exposed: false expose: label: '' granularity: second entity_type: node entity_field: changed plugin_id: date title: 'Recent content' header: { } footer: { } empty: area_text_custom: id: area_text_custom table: views field: area_text_custom relationship: none group_type: group admin_label: '' empty: true tokenize: false content: 'No content available.' plugin_id: text_custom relationships: uid: id: uid table: node_field_data field: uid relationship: none group_type: group admin_label: author required: true entity_type: node entity_field: uid plugin_id: standard arguments: { } display_extenders: { } use_more: false use_more_always: false use_more_text: More link_url: '' link_display: '0' cache_metadata: contexts: - 'languages:language_content' - 'languages:language_interface' - user - 'user.node_grants:view' - user.permissions max-age: -1 tags: { } block_1: display_plugin: block id: block_1 display_title: Block position: 2 display_options: display_extenders: { } defaults: style: false row: false row: type: 'entity:node' options: relationship: none view_mode: teaser cache_metadata: contexts: - 'languages:language_content' - 'languages:language_interface' - user - 'user.node_grants:view' - user.permissions max-age: -1 tags: { }
core/modules/contextual/tests/src/FunctionalJavascript/DuplicateContextualLinksTest.php 0 → 100644 +58 −0 Original line number Diff line number Diff line <?php namespace Drupal\Tests\contextual\FunctionalJavascript; use Drupal\FunctionalJavascriptTests\WebDriverTestBase; /** * Tests the UI for correct contextual links. * * @group contextual */ class DuplicateContextualLinksTest extends WebDriverTestBase { /** * {@inheritdoc} */ public static $modules = [ 'block', 'contextual', 'node', 'views', 'views_ui', 'contextual_test', ]; /** * {@inheritdoc} */ protected $defaultTheme = 'stark'; /** * Tests the contextual links with same id. */ public function testSameContextualLinks() { $this->drupalPlaceBlock('views_block:contextual_recent-block_1', ['id' => 'first']); $this->drupalPlaceBlock('views_block:contextual_recent-block_1', ['id' => 'second']); $this->drupalCreateContentType(['type' => 'page']); $this->drupalCreateNode(); $this->drupalLogin($this->drupalCreateUser([ 'access content', 'access contextual links', 'administer nodes', 'administer blocks', 'administer views', 'edit any page content', ])); // Ensure same contextual links work correct with fresh and cached page. foreach (['fresh', 'cached'] as $state) { $this->drupalGet('user'); $contextual_id = '[data-contextual-id^="node:node=1"]'; $this->assertJsCondition("(typeof jQuery !== 'undefined' && jQuery('[data-contextual-id]:empty').length === 0)"); $this->getSession()->executeScript("jQuery('#block-first $contextual_id .trigger').trigger('click');"); $contextual_links = $this->assertSession()->waitForElementVisible('css', "#block-first $contextual_id .contextual-links"); $this->assertTrue($contextual_links->isVisible(), "Contextual links are visible with $state page."); } } }