1 layout.test | LayoutInterfaceTest::testBlockBasics() |
Add and remove blocks from a custom layout path.
File
- core/
modules/ layout/ tests/ layout.test, line 249 - Tests for the Layout module.
Class
- LayoutInterfaceTest
- Tests the interface for adding, removing, and moving blocks.
Code
function testBlockBasics() {
$this->backdropGet('admin/structure/layouts');
$this->clickLink(t('Add layout'));
// Create a new layout at a new path.
$layout_title = $this->randomName();
$layout_name = strtolower($layout_title);
$layout_url = 'layout-test-path';
$edit = array(
'title' => $layout_title,
'name' => $layout_name,
'layout_template' => 'moscone_flipped',
'path' => $layout_url,
);
$this->backdropPost(NULL, $edit, t('Create layout'));
// We should be taken to the layout content page next.
$this->assertText(t('Layout created. Blocks may now be added to this layout.'));
// Check that a block that requires contexts is not shown.
$this->assertNoLink(t('Main page content'));
$this->assertNoLink(t('Layout bar block'));
// Add a block to the sidebar.
$this->clickLink(t('Add block'), 3);
$this->assertText(t('A testing block for layouts.'));
$this->clickLink(t('Layout foo block'));
$edit = array(
'block_settings[count]' => 5,
);
$this->backdropPost(NULL, $edit, t('Add block'));
// Record the UUID for the newly added block.
$last_block = $this->xpath('(//*[contains(@class,:region)]//*[@data-block-id])[last()]', array(
':region' => 'l-sidebar',
));
$block_uuid = (string) $last_block[0]['data-block-id'];
$block_edit_url = 'admin/structure/layouts/manage/' . $layout_name . '/configure-block/editor/' . $block_uuid;
// Check the admin label and description.
$elements = $this->xpath('//*[contains(@id,:id)]//*[contains(@class,:class)]//span[normalize-space()=:title]', array(
':id' => 'layout-editor-block-' . $block_uuid,
':class' => 'layout-editor-block-title',
':title' => t('Layout foo block'),
));
$this->assertEqual(count($elements), 1, 'The sample block label was found.');
$elements = $this->xpath('//*[contains(@id,:id)]//*[contains(@class,:class)]//*[normalize-space()=:description]', array(
':id' => 'layout-editor-block-' . $block_uuid,
':class' => 'layout-editor-block-content',
':description' => t('A testing block for layouts.'),
));
$this->assertEqual(count($elements), 1, 'The sample block description was found.');
// Change the label and description.
$block_new_label = $this->randomName();
$block_new_description = $this->randomName();
$edit = array(
'admin_label' => $block_new_label,
'admin_description' => $block_new_description,
);
$this->backdropPost($block_edit_url, $edit, t('Update block'));
// Check the new admin label and description.
$elements = $this->xpath('//*[contains(@id,:id)]//*[contains(@class,:class)]//span[normalize-space()=:title]', array(
':id' => 'layout-editor-block-' . $block_uuid,
':class' => 'layout-editor-block-title',
':title' => $block_new_label,
));
$this->assertEqual(count($elements), 1, 'The sample block label was found.');
$elements = $this->xpath('//*[contains(@id,:id)]//*[contains(@class,:class) and contains(text(), :description)]', array(
':id' => 'layout-editor-block-' . $block_uuid,
':class' => 'layout-editor-block-content',
':description' => $block_new_description,
));
$this->assertEqual(count($elements), 1, 'The sample block description was changed.');
// Save the layout.
$this->backdropPost(NULL, array(), t('Save layout'));
// Check that the layout is in the listing of layouts.
$this->backdropGet('admin/structure/layouts');
$this->assertText(check_plain($layout_title));
// Go to the the layout path and confirm the block exists, has the right
// setting, and is the right place.
$this->backdropGet($layout_url);
$this->assertText('Foo subject');
$this->assertText(format_string('The setting of count is @setting.', array('@setting' => 5)));
$elements = $this->xpath('//*[contains(@class,:region)]//*[contains(@class,:block)]', array(
':region' => 'l-sidebar',
':block' => 'block-layout-test-foo',
));
$this->assertEqual(count($elements), 1, 'The sample block was found in the sidebar.');
// Try updating the block title to use a custom string.
$block_new_title = $this->randomName();
$edit = array(
'title_display' => LAYOUT_TITLE_CUSTOM,
'title' => $block_new_title,
);
$this->backdropPost($block_edit_url, $edit, t('Update block'));
$this->backdropPost(NULL, array(), t('Save layout'));
$this->backdropGet($layout_url);
$this->assertText(check_plain($block_new_title));
// Set the block title to nothing.
$edit = array(
'title_display' => LAYOUT_TITLE_NONE,
);
$this->backdropPost($block_edit_url, $edit, t('Update block'));
$this->backdropPost(NULL, array(), t('Save layout'));
$this->backdropGet($layout_url);
$this->assertNoText('Foo subject');
$this->assertNoText($block_new_title);
// Set the block title back to normal and set a special block class.
$custom_class = $this->randomName();
$edit = array(
'title_display' => LAYOUT_TITLE_DEFAULT,
'style_settings[classes]' => $custom_class,
);
$this->backdropPost($block_edit_url, $edit, t('Update block'));
$this->backdropPost(NULL, array(), t('Save layout'));
$this->backdropGet($layout_url);
$this->assertText('Foo subject');
$this->assertNoText($block_new_title);
$block_element = $this->xpath('(//*[contains(@class,:region)]//*[contains(@class,:block)])[contains(@class,:custom-class)]', array(
':region' => 'l-sidebar',
':block' => 'block-layout-test-foo',
':custom-class' => $custom_class,
));
$this->assertEqual(count($block_element), 1, 'The sample block was found in the sidebar.');
// Use the dynamic block style. Save once to update the form (usually done
// via AJAX) then, edit and save again with the dynamic settings.
$title_class = $this->randomName();
$content_class = $this->randomName();
$edit = array(
'style' => 'dynamic',
);
$this->backdropPost($block_edit_url, $edit, t('Update block'));
$edit = array(
'style_settings[wrapper_tag]' => 'aside',
'style_settings[title_tag]' => 'h3',
'style_settings[title_classes]' => $title_class,
'style_settings[content_tag]' => 'p',
'style_settings[content_classes]' => $content_class,
);
$this->backdropPost($block_edit_url, $edit, t('Update block'));
$this->backdropPost(NULL, array(), t('Save layout'));
$this->backdropGet($layout_url);
$block_element = $this->xpath('(//*[contains(@class,:region)]//aside[contains(@class,:block)])[contains(@class,:custom-class)]', array(
':region' => 'l-sidebar',
':block' => 'block-layout-test-foo',
':custom-class' => $custom_class,
));
$this->assertEqual(count($block_element), 1, 'The sample block was found in the sidebar as an aside tag.');
if ($block_element) {
$title_element = $block_element[0]->xpath('h3');
$content_element = $block_element[0]->xpath('p');
$this->assertEqual(count($title_element), 1, 'The sample block has the correct H3 heading tag.');
$this->assertEqual(count($content_element), 1, 'The sample block has the correct P content tag.');
$this->assertEqual($title_element[0]['class'], $title_class, 'The sample block title has the correct class.');
$this->assertEqual($content_element[0]['class'], $content_class, 'The sample block content has the correct class.');
}
// Try injecting XSS into the classes.
$xss = '"><svg onload="alert(\'XSS hole\')">';
// The filtered string after running through backdrop_html_class().
// cspell:disable-next-line
$filtered_xss = 'svg onloadalertXSS hole';
$edit = array(
'style_settings[classes]' => $xss,
'style_settings[title_classes]' => $xss,
'style_settings[content_classes]' => $xss,
);
$this->backdropPost($block_edit_url, $edit, t('Update block'));
$this->backdropPost(NULL, array(), t('Save layout'));
$this->backdropGet($layout_url);
$this->assertNoRaw($xss);
$this->assertRaw($filtered_xss);
// Try moving the block to a different position within the layout.
$edit = array(
'content[positions][content]' => $block_uuid,
'content[positions][sidebar]' => '',
);
$this->backdropPost('admin/structure/layouts/manage/' . $layout_name, $edit, t('Save layout'));
$this->backdropGet($layout_url);
$block_element = $this->xpath('//*[contains(@class,:region)]//*[contains(@class,:block)]', array(
':region' => 'l-content',
':block' => 'block-layout-test-foo',
));
$this->assertEqual(count($block_element), 1, 'The sample block was found in the content area after moving it from the sidebar.');
// Move the block via the block configuration form.
$edit = array(
'region' => 'footer',
);
$this->backdropPost($block_edit_url, $edit, t('Update block'));
$this->backdropPost(NULL, array(), t('Save layout'));
$this->backdropGet($layout_url);
$block_element = $this->xpath('(//*[contains(@class,:region)]//*[contains(@class,:block)])', array(
':region' => 'l-footer',
':block' => 'block-layout-test-foo',
));
$this->assertEqual(count($block_element), 1, 'The sample block was found in the footer after moving via block form.');
// Try moving the block into the sidebar again via the API.
backdrop_static_reset();
$layout = layout_load($layout_name);
$layout->setBlockPosition($block_uuid, 'sidebar');
$layout->save();
$this->backdropGet($layout_url);
$block_element = $this->xpath('(//*[contains(@class,:region)]//*[contains(@class,:block)])', array(
':region' => 'l-sidebar',
':block' => 'block-layout-test-foo',
));
$this->assertEqual(count($block_element), 1, 'The sample block was found in the sidebar after moving via the API.');
// With all the manipulations we've performed, make sure that the block is
// still only shown once, and did not end up in multiple regions on the page
// by accident.
$block_element = $this->xpath('//*[contains(@class,:block)]', array(
':block' => 'block-layout-test-foo',
));
$this->assertEqual(count($block_element), 1, 'The sample block is only displayed once after moving it.');
// Disable the block.
$this->backdropGet('admin/structure/layouts/manage/' . $layout_name);
$disable_link = $this->xpath('//*[@data-block-id=:uuid]//a[contains(@class,"disable-block")]', array(
':uuid' => $block_uuid,
));
$disable_url_parts = backdrop_parse_url($disable_link[0]['href']);
$this->backdropGet($disable_url_parts['path'], $disable_url_parts);
$this->assertText(t('Block "@title" disabled.', array('@title' => $block_new_label)));
// The block is still present in the UI.
$elements = $this->xpath('//*[contains(@id,:id)]//*[contains(@class,:class)]//span[normalize-space()=:title]', array(
':id' => 'layout-editor-block-' . $block_uuid,
':class' => 'layout-editor-block-title',
':title' => $block_new_label . ' (Disabled)',
));
$this->assertEqual(count($elements), 1, 'The sample block label was found.');
$elements = $this->xpath('//*[contains(@id,:id)]//*[contains(@class,:class) and contains(text(), :description)]', array(
':id' => 'layout-editor-block-' . $block_uuid,
':class' => 'layout-editor-block-content',
':description' => $block_new_description,
));
$this->assertEqual(count($elements), 1, 'The sample block description was changed.');
$this->backdropPost(NULL, array(), t('Save layout'));
// But is gone from the layout page.
$this->backdropGet($layout_url);
$this->assertNoText('Foo subject');
$block_element = $this->xpath('//*[contains(@class,:block)]', array(
':block' => 'block-layout-test-foo',
));
$this->assertEqual(count($block_element), 0, 'The sample block is not visible on the page.');
// Re-enable the block.
$this->backdropGet('admin/structure/layouts/manage/' . $layout_name);
$this->backdropGet($disable_url_parts['path'], $disable_url_parts);
$this->assertText(t('Block "@title" disabled.', array('@title' => $block_new_label)));
// The block is still present in the UI.
$elements = $this->xpath('//*[contains(@id,:id)]//*[contains(@class,:class)]//span[normalize-space()=:title]', array(
':id' => 'layout-editor-block-' . $block_uuid,
':class' => 'layout-editor-block-title',
':title' => $block_new_label,
));
$this->assertEqual(count($elements), 1, 'The sample block label was found.');
$elements = $this->xpath('//*[contains(@id,:id)]//*[contains(@class,:class) and contains(text(), :description)]', array(
':id' => 'layout-editor-block-' . $block_uuid,
':class' => 'layout-editor-block-content',
':description' => $block_new_description,
));
$this->assertEqual(count($elements), 1, 'The sample block description was changed.');
$this->backdropPost(NULL, array(), t('Save layout'));
// Block is back on the layout page.
$this->backdropGet($layout_url);
$this->assertText('Foo subject');
$block_element = $this->xpath('//*[contains(@class,:block)]', array(
':block' => 'block-layout-test-foo',
));
$this->assertEqual(count($block_element), 1, 'The sample block is again visible on the page.');
// Finally, try removing the block.
$this->backdropGet('admin/structure/layouts/manage/' . $layout_name);
$remove_link = $this->xpath('//*[@data-block-id=:uuid]//a[contains(@class,"remove-block")]', array(
':uuid' => $block_uuid,
));
$remove_url_parts = backdrop_parse_url($remove_link[0]['href']);
$this->backdropGet($remove_url_parts['path'], $remove_url_parts);
$this->backdropPost(NULL, array(), t('Save layout'));
$this->backdropGet($layout_url);
$this->assertNoText('Foo subject');
$block_element = $this->xpath('//*[contains(@class,:block)]', array(
':block' => 'block-layout-test-foo',
));
$this->assertEqual(count($block_element), 0, 'The sample block has been removed.');
// Delete the layout to prevent it interfering with following tests.
$this->backdropPost('admin/structure/layouts/manage/' . $layout_name . '/delete', array(), t('Delete layout'));
}