PollTestBase.php in Poll 8
Namespace
Drupal\Tests\poll\FunctionalFile
tests/src/Functional/PollTestBase.phpView source
<?php
namespace Drupal\Tests\poll\Functional;
use Drupal\poll\PollInterface;
use Drupal\Tests\BrowserTestBase;
use InvalidArgumentException;
/**
* Defines a base class for testing the Poll module.
*/
abstract class PollTestBase extends BrowserTestBase {
/**
* @var \Drupal\user\UserInterface
*/
protected $admin_user;
/**
* @var \Drupal\user\UserInterface
*/
protected $web_user;
/**
* @var \Drupal\poll\PollInterface
*/
protected $poll;
/**
* List of permissions used by admin_user.
*
* @var array
*/
protected $adminPermissions = [];
/**
* List of permissions used by web_user.
*
* @var array
*/
protected $webUserPermissions = [];
/**
* Modules to enable.
*
* @var array
*/
public static $modules = array(
'poll',
'node',
'block',
);
/**
* {@inheritdoc}
*/
protected $defaultTheme = 'classy';
/**
* {@inheritdoc}
*/
protected function setUp() {
parent::setUp();
$this
->drupalPlaceBlock('local_tasks_block');
$this
->drupalPlaceBlock('local_actions_block');
$this
->drupalPlaceBlock('page_title_block');
$this->admin_user = $this
->drupalCreateUser(array_merge([
'administer polls',
'access polls',
'access poll overview',
'view poll results',
], $this->adminPermissions));
$this->web_user = $this
->drupalCreateUser(array_merge([
'access polls',
'cancel own vote',
], $this->webUserPermissions));
$this->poll = $this
->pollCreate();
}
/**
* Creates a poll.
*
* @param int $choice_count
* (optional) The number of choices to generate. Defaults to 7.
* @param \Drupal\user\UserInterface $account
* (optional) Poll creator user. Defaults to NULL, then use $this->admin_user.
* @param boolean $preview
* (optional) Whether to test if the preview is working or not. Defaults to
* TRUE.
*
* @return mixed
* The created poll entity, or FALSE on error.
*/
function pollCreate($choice_count = 7, $account = NULL, $preview = TRUE) {
if (!$account) {
$this
->drupalLogin($this->admin_user);
}
else {
$this
->drupalLogin($account);
}
// Get the form first to initialize the state of the internal browser.
$this
->drupalGet('poll/add');
$question = $this
->randomMachineName();
$choices = $this
->generateChoices($choice_count);
list($edit, $index) = $this
->pollGenerateEdit($question, $choices);
// Re-submit the form until all choices are filled in.
if (count($choices) > 0) {
for ($delta = 0; $delta <= count($choices); $delta++) {
$this
->drupalPostForm(NULL, $edit, t('Add another item'));
list($edit, $index) = $this
->pollGenerateEdit($question, $choices, $index);
}
}
// if ($preview) {
// $this->drupalPostForm('poll/add', $edit, t('Preview'));
// $this->assertPollChoiceOrder($choices, $index, TRUE);
// list($edit, $index) = $this->pollGenerateEdit($title, $choices, $index);
// }
$this
->drupalPostForm(NULL, $edit, t('Save'));
// Load the first poll returned from the database.
$polls = \Drupal::entityTypeManager()
->getStorage('poll')
->loadByProperties(array(
'question' => $question,
));
$poll = reset($polls);
$this
->assertText(t('The poll @question has been added.', array(
'@question' => $question,
)));
$this
->assertInstanceOf(PollInterface::class, $poll);
return $poll instanceof PollInterface ? $poll : FALSE;
}
/**
* Generates POST values for the poll node form, specifically poll choices.
*
* @param string $question
* The poll question.
* @param array $choices
* An array containing poll choices, as generated by
* PollTestBase::generateChoices().
* @param int $index
* (optional) The amount/number of already submitted poll choices. Defaults
* to 0.
*
* @return array
* An indexed array containing:
* - The generated POST values, suitable for
* Drupal\simpletest\WebTestBase::drupalPostForm().
* - The number of poll choices contained in 'edit', for potential re-usage
* in subsequent invocations of this function.
*/
private function pollGenerateEdit($question, array $choices, $index = 0) {
$max_new_choices = 1;
$already_submitted_choices = array_slice($choices, 0, $index);
$new_choices = array_values(array_slice($choices, $index, $max_new_choices));
$edit = array(
'question[0][value]' => $question,
);
foreach ($already_submitted_choices as $k => $text) {
$edit['choice[' . $k . '][choice]'] = $text;
}
foreach ($new_choices as $k => $text) {
$edit['choice[' . $k . '][choice]'] = $text;
}
return array(
$edit,
count($already_submitted_choices) + count($new_choices),
);
}
/**
* Generates random choices for the poll.
*
* @param int $count
* (optional) The number of choices to generate. Defaults to 7.
*
* @return array $choices
* An array of generated choices.
*/
private function generateChoices($count = 7) {
$choices = array();
for ($i = 1; $i <= $count; $i++) {
$choices[] = $this
->randomMachineName();
}
return $choices;
}
/**
* Asserts correct poll choice order in the node form after submission.
*
* Verifies both the order in the DOM and in the 'weight' form elements.
*
* @param array $choices
* An array containing poll choices, as generated by
* PollTestBase::generateChoices().
* @param int $index
* (optional) The amount/number of already submitted poll choices. Defaults
* to 0.
* @param bool $preview
* (optional) Whether to also check the poll preview. Defaults to FALSE.
*
* @see PollTestBase::pollGenerateEdit()
*/
function assertPollChoiceOrder(array $choices, $index = 0, $preview = FALSE) {
$expected = array();
$weight = 0;
foreach ($choices as $id => $label) {
if ($id < $index) {
// Directly assert the weight form element value for this choice.
$this
->assertFieldByName('choice[' . $id . '][_weight]', $weight);
// The expected weight of each choice is higher than the previous one.
$weight++;
// Append to our (to be reversed) stack of labels.
$expected[$weight] = $label;
}
}
ksort($expected);
// Verify DOM order of poll choices (i.e., #weight of form elements).
$elements = $this
->xpath('//input[starts-with(@name, :prefix) and contains(@name, :suffix)]', array(
':prefix' => 'choice[chid:',
':suffix' => '][chtext]',
));
$expected_order = $expected;
foreach ($elements as $element) {
$next_label = array_shift($expected_order);
$this
->assertEqual((string) $element['value'], $next_label);
}
// If requested, also verify DOM order in preview.
if ($preview) {
$elements = $this
->xpath('//div[contains(@class, :teaser)]/descendant::div[@class=:text]', array(
':teaser' => 'node-teaser',
':text' => 'text',
));
$expected_order = $expected;
foreach ($elements as $element) {
$next_label = array_shift($expected_order);
$this
->assertEqual((string) $element, $next_label, "Found choice {$next_label} in preview.");
}
}
}
/**
* Get the Choice ID of a poll.
*
* @param \Drupal\poll\PollInterface $poll
* The poll of the choice.
* @param int $delta
* The number of the choice.
*
* @return int $key
* Returns the choice ID or an error.
*
* @throws InvalidArgumentException
* Throws it if the poll does not have the choice delta.
*/
protected function getChoiceId(PollInterface $poll, $delta) {
$options = $poll
->getOptions();
$keys = array_keys($options);
foreach ($keys as $id => $key) {
if ($delta == $id + 1) {
return $key;
}
}
throw new InvalidArgumentException();
}
/**
* Get the Choice ID of a poll from the label.
*
* @param \Drupal\poll\PollInterface $poll
* The poll of the choice.
* @param string $label
* The label of the choice.
*
* @return int $id
* Returns the choice id or an error.
*
* @throws InvalidArgumentException
* Throws it if the poll does not have the choice label.
*/
protected function getChoiceIdByLabel(PollInterface $poll, $label) {
$options = $poll
->getOptions();
foreach ($options as $id => $option) {
if ($label == $option) {
return $id;
}
}
throw new InvalidArgumentException();
}
}
Classes
Name | Description |
---|---|
PollTestBase | Defines a base class for testing the Poll module. |