diff --git a/modules/lightning_scheduler/tests/features/transitions.feature b/modules/lightning_scheduler/tests/features/transitions.feature index 894c161d30455a597e3a3b7aa8121b33151e80c3..a0e5224c1f48937e79a5c192deb4b79189605c19 100644 --- a/modules/lightning_scheduler/tests/features/transitions.feature +++ b/modules/lightning_scheduler/tests/features/transitions.feature @@ -3,8 +3,8 @@ Feature: Scheduling transitions on content @368f0045 @javascript Scenario: Automatically publishing, then unpublishing, in the future - Given I am logged in as a user with the "create test content, view own unpublished content, edit own test content, use editorial transition create_new_draft, use editorial transition review, use editorial transition publish, use editorial transition archive, schedule editorial transition publish, schedule editorial transition archive, view latest version, administer nodes" permissions - When I visit "/node/add/test" + Given I am logged in as a user with the "create moderated content, view own unpublished content, edit own moderated content, use editorial transition create_new_draft, use editorial transition review, use editorial transition publish, use editorial transition archive, schedule editorial transition publish, schedule editorial transition archive, view latest version, administer nodes" permissions + When I visit "/node/add/moderated" And I enter "Schedule This" for "Title" And I schedule a transition to Published in 10 seconds And I schedule a transition to Archived in 20 seconds diff --git a/tests/contexts/DiffContext.behat.inc b/tests/contexts/DiffContext.behat.inc deleted file mode 100644 index 5b1521a01eb57f4cfc59546bc7f826341c4ddd0e..0000000000000000000000000000000000000000 --- a/tests/contexts/DiffContext.behat.inc +++ /dev/null @@ -1,64 +0,0 @@ -<?php - -namespace Acquia\LightningExtension\Context; - -use Behat\MinkExtension\Context\RawMinkContext; -use Drupal\DrupalDriverManager; -use Drupal\DrupalExtension\Context\DrupalSubContextInterface; - -/** - * Contains step definitions for interacting with the Diff module. - * - * @internal - * This is an internal part of Lightning Workflow's testing system and may be - * changed or removed at any time without warning. External code should not - * extend, instantiate, or use this class in any way! If you want to use the - * functionality of this class, you should copy the relevant code into your - * own project. - */ -final class DiffContext extends RawMinkContext implements DrupalSubContextInterface { - - /** - * {@inheritdoc} - */ - public function __construct(DrupalDriverManager $drupal) { - } - - /** - * Compares two revisions of a node. - * - * @param string $a - * The one-based index of a revision to compare. 1st is oldest. - * @param string $b - * The one-based index of a revision to compare. 1st is oldest. - * - * @When I compare the :a and :b revisions - */ - public function compareRevisions($a, $b) { - $page = $this->getSession()->getPage(); - - $re = '/^[0-9]+(st|nd|rd|th)$/i'; - - if (preg_match($re, $a)) { - $a = substr($a, 0, -2); - } - if (preg_match($re, $b)) { - $b = substr($b, 0, -2); - } - $a = ((int) $a) - 1; - $b = ((int) $b) - 1; - - $page->clickLink('Revisions'); - - /** @var \Behat\Mink\Element\NodeElement[] $rows */ - $rows = $page->findAll('css', '.diff-revisions tbody tr'); - $rows = array_reverse($rows); - $a = $rows[$a]->findField('radios_left')->getValue(); - $b = $rows[$b]->findField('radios_right')->getValue(); - - $page->selectFieldOption('radios_left', $a); - $page->selectFieldOption('radios_right', $b); - $page->pressButton('Compare'); - } - -} diff --git a/tests/contexts/ModerationContext.behat.inc b/tests/contexts/ModerationContext.behat.inc index e640ca95ebfad27840f6528eb9a30f3d3dc602ef..5dc2c695b29cfe97a7e223005e77660b5766851d 100644 --- a/tests/contexts/ModerationContext.behat.inc +++ b/tests/contexts/ModerationContext.behat.inc @@ -6,10 +6,9 @@ use Behat\Mink\Element\DocumentElement; use Behat\Mink\Element\NodeElement; use Behat\Mink\Exception\ElementNotFoundException; use Behat\Mink\Exception\ExpectationException; -use Drupal\DrupalExtension\Context\DrupalSubContextBase; -use Drupal\node\Entity\NodeType; -use Drupal\workflows\Entity\Workflow; -use Webmozart\Assert\Assert; +use Behat\MinkExtension\Context\RawMinkContext; +use Drupal\DrupalDriverManager; +use Drupal\DrupalExtension\Context\DrupalSubContextInterface; /** * Contains miscellaneous step definitions for testing moderation UIs. @@ -21,44 +20,37 @@ use Webmozart\Assert\Assert; * functionality of this class, you should copy the relevant code into your * own project. */ -final class ModerationContext extends DrupalSubContextBase { - - use AwaitTrait; +final class ModerationContext extends RawMinkContext implements DrupalSubContextInterface { /** - * Content types which had moderation enabled during the scenario. - * - * @var string[] + * {@inheritdoc} */ - private $moderated = []; - - /** - * Cleans up after the scenario. - * - * @AfterScenario - */ - public function tearDown() { - /** @var \Drupal\workflows\WorkflowInterface $workflow */ - $workflow = Workflow::load('editorial'); - Assert::isInstanceOf($workflow, '\Drupal\workflows\WorkflowInterface'); - - while ($this->moderated) { - $workflow->getTypePlugin()->removeEntityTypeAndBundle('node', array_pop($this->moderated)); - } - $workflow->save(); + public function __construct(DrupalDriverManager $drupal) { } /** * Opens the moderation sidebar. * * @When I open the moderation sidebar + * + * @throws \Behat\Mink\Exception\ElementNotFoundException + * If the moderation sidebar does not appear on the page. */ public function openModerationSidebar() { $this->assertSession() ->elementExists('css', '#toolbar-bar') ->clickLink('Tasks'); - $this->awaitElement('.moderation-sidebar-container'); + $session = $this->getSession(); + + $sidebar = $session->getPage() + ->waitFor(10, function (DocumentElement $page) { + return $page->find('css', '.moderation-sidebar-container'); + }); + + if (empty($sidebar)) { + throw new ElementNotFoundException($session->getDriver(), 'element', 'css', '.moderation-sidebar-container'); + } } /** @@ -68,30 +60,19 @@ final class ModerationContext extends DrupalSubContextBase { * The label of the expected moderation state. * * @Then the current moderation state should be :state + * + * @throws \Behat\Mink\Exception\ExpectationException + * If the current moderation state is not the expected one. */ public function assertCurrentModerationState($state) { $assert_session = $this->assertSession(); $toolbar = $assert_session->elementExists('css', '#toolbar-bar'); $current_state = $assert_session->elementExists('named', ['link', 'Tasks'], $toolbar) ->getAttribute('data-label'); - Assert::same($current_state, $state); - } - - /** - * Enables moderation for a content type. - * - * @param string $node_type - * The machine name of the content type. - * - * @When I enable moderation for the :node_type content type - */ - public function addModerationToContentType($node_type) { - /** @var \Drupal\node\NodeTypeInterface $node_type */ - $node_type = NodeType::load($node_type); - $node_type->setThirdPartySetting('lightning_workflow', 'workflow', 'editorial'); - lightning_workflow_node_type_insert($node_type); - array_push($this->moderated, $node_type->id()); + if ($current_state !== $state) { + throw new ExpectationException("Expected the current moderation state to be $state, but it is $current_state.", $this->getSession()->getDriver()); + } } /** @@ -100,22 +81,23 @@ final class ModerationContext extends DrupalSubContextBase { * @Then I should see a dashboard for moderating content */ public function assertModerationDashboard() { - $assert = $this->assertSession(); - - $assert->elementExists('css', "[data-block-plugin-id='views_block:content_moderation_dashboard_in_review-block_1']"); - $assert->elementExists('css', "[data-block-plugin-id='views_block:content_moderation_dashboard_in_review-block_2']"); - $assert->elementExists('css', "[data-block-plugin-id='moderation_dashboard_activity']"); - $assert->elementExists('css', "[data-block-plugin-id='views_block:moderation_dashboard_recently_created-block_1']"); - $assert->elementExists('css', "[data-block-plugin-id='views_block:content_moderation_dashboard_in_review-block_3']"); - $assert->elementExists('css', "[data-block-plugin-id='views_block:moderation_dashboard_recent_changes-block_1']"); - $assert->elementExists('css', "[data-block-plugin-id='views_block:moderation_dashboard_recent_changes-block_2']"); - $assert->elementExists('css', "[data-block-plugin-id='views_block:moderation_dashboard_recently_created-block_2']"); + $this->assertBlock('views_block:content_moderation_dashboard_in_review-block_1'); + $this->assertBlock('views_block:content_moderation_dashboard_in_review-block_2'); + $this->assertBlock('moderation_dashboard_activity'); + $this->assertBlock('views_block:moderation_dashboard_recently_created-block_1'); + $this->assertBlock('views_block:content_moderation_dashboard_in_review-block_3'); + $this->assertBlock('views_block:moderation_dashboard_recent_changes-block_1'); + $this->assertBlock('views_block:moderation_dashboard_recent_changes-block_2'); + $this->assertBlock('views_block:moderation_dashboard_recently_created-block_2'); } /** * Autosaves the current form. * * @When I wait for my work to be autosaved + * + * @throws \Behat\Mink\Exception\ExpectationException + * If the autosave notification does not appear or disappear as expected. */ public function awaitAutosave() { $driver = $this->getSession()->getDriver(); @@ -142,11 +124,15 @@ final class ModerationContext extends DrupalSubContextBase { * Restores autosaved work. * * @Then I should be able to restore my work + * + * @throws \Behat\Mink\Exception\ElementNotFoundException + * If the "Resume editing" button does not appear. */ public function assertRestoreFromAutosave() { + $session = $this->getSession(); + /** @var \Behat\Mink\Element\NodeElement $button */ - $button = $this->getSession() - ->getPage() + $button = $session->getPage() ->waitFor(10, function (DocumentElement $page) { return $page->findButton('Resume editing'); }); @@ -155,8 +141,111 @@ final class ModerationContext extends DrupalSubContextBase { $button->press(); } else { - throw new ElementNotFoundException($this->getSession()->getDriver(), 'button', 'named', 'Resume editing'); + throw new ElementNotFoundException($session->getDriver(), 'button', 'named', 'Resume editing'); + } + } + + /** + * Compares two revisions of a node. + * + * @param string $a + * The one-based index of a revision to compare. 1st is oldest. + * @param string $b + * The one-based index of a revision to compare. 1st is oldest. + * + * @When I compare the :a and :b revisions + */ + public function compareRevisions($a, $b) { + $page = $this->getSession()->getPage(); + + $re = '/^[0-9]+(st|nd|rd|th)$/i'; + + if (preg_match($re, $a)) { + $a = substr($a, 0, -2); } + if (preg_match($re, $b)) { + $b = substr($b, 0, -2); + } + $a = ((int) $a) - 1; + $b = ((int) $b) - 1; + + $page->clickLink('Revisions'); + + /** @var \Behat\Mink\Element\NodeElement[] $rows */ + $rows = $page->findAll('css', '.diff-revisions tbody tr'); + $rows = array_reverse($rows); + $a = $rows[$a]->findField('radios_left')->getValue(); + $b = $rows[$b]->findField('radios_right')->getValue(); + + $page->selectFieldOption('radios_left', $a); + $page->selectFieldOption('radios_right', $b); + $page->pressButton('Compare'); + } + + /** + * Asserts that Quick Edit is enabled for at least one entity on the page. + * + * @throws \Behat\Mink\Exception\ExpectationException + * If Quick Edit is disabled on the current page. + * + * @Then Quick Edit should be enabled + */ + public function assertQuickEditEnabled() { + $session = $this->getSession(); + + $is_enabled = $session->wait(10000, 'Drupal.quickedit.collections.entities.length > 0'); + + if (empty($is_enabled)) { + throw new ExpectationException('Expected Quick Edit to be enabled, but it is not.', $session->getDriver()); + } + } + + /** + * Asserts that Quick Edit is not enabled for any entities on the page. + * + * @throws \Behat\Mink\Exception\ExpectationException + * If Quick Edit is enabled on the current page. + * + * @Then Quick Edit should be disabled + */ + public function assertQuickEditDisabled() { + $session = $this->getSession(); + + $is_disabled = $session->wait(10000, 'Drupal.quickedit.collections.entities.length === 0'); + + if (empty($is_disabled)) { + throw new ExpectationException('Expected Quick Edit to be disabled, but it is not.', $session->getDriver()); + } + } + + /** + * Asserts that a block exists with a Quick Edit contextual link. + * + * @param string $plugin + * The block plugin ID. + * + * @Then I should see a :plugin block with Quick Edit + */ + public function assertQuickEditableBlock($plugin) { + $block = $this->assertBlock($plugin); + + $assert = $this->assertSession(); + $links = $assert->elementExists('css', 'ul.contextual-links', $block); + $assert->elementExists('named', ['link', 'Quick edit'], $links); + } + + /** + * Asserts the presence of a particular block by its plugin ID. + * + * @param string $plugin_id + * The block plugin ID. + * + * @return \Behat\Mink\Element\ElementInterface + * The block element. + */ + private function assertBlock($plugin_id) { + return $this->assertSession() + ->elementExists('css', '[data-block-plugin-id="' . $plugin_id . '"]'); } } diff --git a/tests/contexts/QuickEditContext.behat.inc b/tests/contexts/QuickEditContext.behat.inc deleted file mode 100644 index efdc89e099fd4eefc55e0c7753e2d1e0617ba748..0000000000000000000000000000000000000000 --- a/tests/contexts/QuickEditContext.behat.inc +++ /dev/null @@ -1,104 +0,0 @@ -<?php - -namespace Acquia\LightningExtension\Context; - -use Behat\Mink\Exception\ExpectationException; -use Behat\MinkExtension\Context\RawMinkContext; -use Drupal\DrupalDriverManager; -use Drupal\DrupalExtension\Context\DrupalSubContextInterface; - -/** - * Contains step definitions for interacting with Quick Edit. - * - * @internal - * This is an internal part of Lightning Workflow's testing system and may be - * changed or removed at any time without warning. External code should not - * extend, instantiate, or use this class in any way! If you want to use the - * functionality of this class, you should copy the relevant code into your - * own project. - */ -final class QuickEditContext extends RawMinkContext implements DrupalSubContextInterface { - - /** - * {@inheritdoc} - */ - public function __construct(DrupalDriverManager $drupal) { - } - - /** - * Asserts that Quick Edit is enabled for at least one entity on the page. - * - * @throws \Behat\Mink\Exception\ExpectationException - * If Quick Edit is disabled on the current page. - * - * @Then Quick Edit should be enabled - */ - public function assertEnabled() { - $is_enabled = $this->await('Drupal.quickedit.collections.entities.length > 0'); - - if (empty($is_enabled)) { - throw new ExpectationException('Expected Quick Edit to be enabled, but it is not.', $this->getSession()->getDriver()); - } - } - - /** - * Asserts that Quick Edit is not enabled for any entities on the page. - * - * @throws \Behat\Mink\Exception\ExpectationException - * If Quick Edit is enabled on the current page. - * - * @Then Quick Edit should be disabled - */ - public function assertDisabled() { - $is_disabled = $this->await('Drupal.quickedit.collections.entities.length === 0'); - - if (empty($is_disabled)) { - throw new ExpectationException('Expected Quick Edit to be disabled, but it is not.', $this->getSession()->getDriver()); - } - } - - /** - * Asserts that a block exists with a Quick Edit contextual link. - * - * @param string $plugin - * The block plugin ID. - * - * @Then I should see a :plugin block with Quick Edit - */ - public function assertBlock($plugin) { - $assert = $this->assertSession(); - $links = $assert->elementExists('css', "div[data-block-plugin-id='$plugin'] ul.contextual-links"); - $assert->elementExists('named', ['link', 'Quick edit'], $links); - } - - /** - * Waits for any running AJAX requests to finish and a condition to be true. - * - * @param string $condition - * (optional) An additional JavaScript expression which is expected to be - * TRUE once AJAX requests are finished. Defaults to 'true'. - * - * @return bool - * TRUE if all AJAX requests are finished and the given condition is true, - * otherwise FALSE. - */ - private function await($condition = 'true') { - $condition = <<<JS -(function() { - function isAjaxing(instance) { - return instance && instance.ajaxing === true; - } - return ( - // Assert no AJAX request is running (via jQuery or Drupal) and no - // animation is running. - (typeof jQuery === 'undefined' || (jQuery.active === 0 && jQuery(':animated').length === 0)) && - (typeof Drupal === 'undefined' || typeof Drupal.ajax === 'undefined' || typeof Drupal.ajax.instances === 'undefined' || !Drupal.ajax.instances.some(isAjaxing)) && - ($condition) - ); -}()); -JS; - - return $this->getSession()->wait(10000, $condition); - } - -} diff --git a/tests/features/Autosave.feature b/tests/features/Autosave.feature index 3f833b78b519d75ea5b0c4381a36ab6c7e326ed5..8433878515adc3bbb8750a402fa69968b77b213c 100644 --- a/tests/features/Autosave.feature +++ b/tests/features/Autosave.feature @@ -5,8 +5,8 @@ Feature: Autosave for content editing forms @javascript @with-module:autosave_form @af96a97b @orca_public Scenario: Retrieving autosaved work - Given I am logged in as a user with the "access content overview, edit any test content, use editorial transition create_new_draft" permissions - And test content: + Given I am logged in as a user with the "access content overview, edit any moderated content, use editorial transition create_new_draft" permissions + And moderated content: | title | moderation_state | | Test | published | When I visit "/admin/content" diff --git a/tests/features/ContentModeration.feature b/tests/features/ContentModeration.feature index 4d5f23d28c06d48c340b99af1ddc31fa9e80eacb..a933134ecec9a6f60c0151f0267ad79e9add545e 100644 --- a/tests/features/ContentModeration.feature +++ b/tests/features/ContentModeration.feature @@ -4,7 +4,7 @@ Feature: Moderated content content. Background: - Given test content: + Given moderated content: | title | moderation_state | promote | | Alpha | review | 1 | | Beta | published | 1 | @@ -12,7 +12,7 @@ Feature: Moderated content @03ebc3ee @orca_public Scenario: Publishing moderated content - Given I am logged in as a user with the "access content overview, view any unpublished content, use editorial transition review, use editorial transition publish, create test content, edit any test content, create url aliases" permissions + Given I am logged in as a user with the "access content overview, view any unpublished content, use editorial transition review, use editorial transition publish, create moderated content, edit any moderated content, create url aliases" permissions When I visit "/admin/content" And I click "Alpha" And I visit the edit form @@ -24,7 +24,7 @@ Feature: Moderated content @c0c17d43 @orca_public Scenario: Unpublishing moderated content - Given I am logged in as a user with the "access content overview, use editorial transition publish, use editorial transition archive, create test content, edit any test content, create url aliases" permissions + Given I am logged in as a user with the "access content overview, use editorial transition publish, use editorial transition archive, create moderated content, edit any moderated content, create url aliases" permissions And I visit "/admin/content" And I click "Beta" And I visit the edit form @@ -46,7 +46,7 @@ Feature: Moderated content @6a1db3b1 Scenario: Examining the moderation history of a piece of content - Given I am logged in as a user with the "access content overview, view any unpublished content, edit any test content, use editorial transition create_new_draft, use editorial transition review, use editorial transition publish, view all revisions" permissions + Given I am logged in as a user with the "access content overview, view any unpublished content, edit any moderated content, use editorial transition create_new_draft, use editorial transition review, use editorial transition publish, view all revisions" permissions When I visit "/admin/content" And I click "Charlie" And I visit the edit form diff --git a/tests/features/Diff.feature b/tests/features/Diff.feature index 7c0d1b728e7bdd1559df706a20fd55fd1488a0e4..adb9cb52ed5f42ba4c297b3ccb5a2ad44d9a2072 100644 --- a/tests/features/Diff.feature +++ b/tests/features/Diff.feature @@ -3,8 +3,8 @@ Feature: Diffing different revisions of content @5b4ba63e @with-module:diff Scenario: Diffing two node revisions - Given I am logged in as a user with the "access content overview, view any unpublished content, edit any test content, use editorial transition create_new_draft, view all revisions" permissions - And test content: + Given I am logged in as a user with the "access content overview, view any unpublished content, edit any moderated content, use editorial transition create_new_draft, view all revisions" permissions + And moderated content: | title | body | moderation_state | | Pastafazoul | First revision | draft | When I visit "/admin/content" diff --git a/tests/features/ModerationSidebar.feature b/tests/features/ModerationSidebar.feature index 0b6c96681126861924ec552ed5a733d9f32c6209..cbaaf70584374e1d9682cd3082c059e17a4980a5 100644 --- a/tests/features/ModerationSidebar.feature +++ b/tests/features/ModerationSidebar.feature @@ -3,8 +3,8 @@ Feature: A sidebar for moderating content @1d83813d @javascript @with-module:toolbar @with-module:moderation_sidebar Scenario: Moderating content using the sidebar - Given I am logged in as a user with the "access content overview, access toolbar, use moderation sidebar, view any unpublished content, edit any test content, use editorial transition review, use editorial transition publish" permissions - And test content: + Given I am logged in as a user with the "access content overview, access toolbar, use moderation sidebar, view any unpublished content, edit any moderated content, use editorial transition review, use editorial transition publish" permissions + And moderated content: | title | moderation_state | | Test | draft | When I visit "/admin/content" diff --git a/tests/features/Quickedit.feature b/tests/features/Quickedit.feature index 7f48064526ac1c60bc228514384864cd2543d0ad..2e44c9d9bcdbddcf49cf909890b0a48c7c832fee 100644 --- a/tests/features/Quickedit.feature +++ b/tests/features/Quickedit.feature @@ -3,8 +3,8 @@ Feature: Integration of workflows with Quick Edit @f2beeeda @javascript @with-module:quickedit @orca_public Scenario: Quick Edit should be available for unpublished content - Given I am logged in as a user with the "access content overview, access in-place editing, access contextual links, use editorial transition create_new_draft, view any unpublished content, edit any test content" permissions - And test content: + Given I am logged in as a user with the "access content overview, access in-place editing, access contextual links, use editorial transition create_new_draft, view any unpublished content, edit any moderated content" permissions + And moderated content: | title | moderation_state | | Foobar | draft | When I visit "/admin/content" diff --git a/tests/src/FixtureContext.php b/tests/src/FixtureContext.php index b3c57333423c02408d33d8d8bcff3f8d2ef94ff3..e0dc64551f4514536cef0650b9693ecf97daedbe 100644 --- a/tests/src/FixtureContext.php +++ b/tests/src/FixtureContext.php @@ -20,8 +20,8 @@ final class FixtureContext extends FixtureBase { // Create a temporary content type specifically for testing. $node_type = NodeType::create([ - 'type' => 'test', - 'name' => 'Test', + 'type' => 'moderated', + 'name' => 'Moderated', ]); $node_type->setThirdPartySetting('lightning_workflow', 'workflow', 'editorial'); $node_type->setThirdPartySetting('lightning_workflow', 'autosave', TRUE);