[Shop] Registration after checkout

This commit is contained in:
Wojdylak 2024-09-10 11:33:51 +02:00 committed by Grzegorz Sadowski
parent 32219b6123
commit 15f9616768
7 changed files with 57 additions and 29 deletions

View file

@ -10,7 +10,7 @@ Feature: Having registration form prefilled after checkout
And the store ships everywhere for Free
And the store allows paying Offline
@no-api @todo-ui
@no-api @ui @javascript
Scenario: Having prefilled registration form after checkout
Given I have product "PHP T-Shirt" in the cart
And I complete addressing step with email "john@example.com" and "United States" based billing address
@ -20,7 +20,7 @@ Feature: Having registration form prefilled after checkout
And I should be able to proceed to the registration
And the registration form should be prefilled with "john@example.com" email
@no-api @todo-ui
@no-api @ui @javascript
Scenario: Not being able to create an account if customer is logged in
Given I am a logged in customer
And I have product "PHP T-Shirt" in the cart

View file

@ -10,7 +10,7 @@ Feature: Registering a new account after checkout
And the store ships everywhere for Free
And the store allows paying Offline
@no-api @todo-ui
@no-api @ui @javascript
Scenario: Displaying thank you page after registration
Given on this channel account verification is required
And I have product "PHP T-Shirt" in the cart
@ -23,7 +23,7 @@ Feature: Registering a new account after checkout
And I register this account
Then I should be on registration thank you page
@no-api @todo-ui
@no-api @ui @javascript
Scenario: Registering a new account after checkout when channel has enabled registration verification
Given on this channel account verification is required
And I have product "PHP T-Shirt" in the cart
@ -37,7 +37,7 @@ Feature: Registering a new account after checkout
And I verify my account using link sent to "john@example.com"
Then I should be able to log in as "john@example.com" with "sylius" password
@no-api @todo-ui
@no-api @ui @javascript
Scenario: Registering a new account after checkout when channel has disabled registration verification
Given on this channel account verification is not required
And I have product "PHP T-Shirt" in the cart

View file

@ -390,6 +390,6 @@ class RegistrationContext implements Context
private function assertFieldValidationMessage(string $element, string $expectedMessage): void
{
Assert::true($this->registerElement->checkValidationMessageFor($element, $expectedMessage));
Assert::same($this->registerElement->getValidationMessage($element), $expectedMessage);
}
}

View file

@ -13,27 +13,12 @@ declare(strict_types=1);
namespace Sylius\Behat\Element\Shop\Account;
use Behat\Mink\Element\NodeElement;
use Behat\Mink\Exception\ElementNotFoundException;
use FriendsOfBehat\PageObjectExtension\Element\Element;
use Sylius\Component\Core\Formatter\StringInflector;
final class RegisterElement extends Element implements RegisterElementInterface
{
public function checkValidationMessageFor(string $element, string $message): bool
{
$errorLabel = $this
->getElement(StringInflector::nameToCode($element))
->getParent()
->find('css', '[data-test-validation-error]')
;
if (null === $errorLabel) {
throw new ElementNotFoundException($this->getSession(), 'Validation message', 'css', '[data-test-validation-error]');
}
return $message === $errorLabel->getText();
}
public function register(): void
{
$this->getElement('register_button')->click();
@ -42,6 +27,7 @@ final class RegisterElement extends Element implements RegisterElementInterface
public function specifyEmail(?string $email): void
{
$this->getElement('email')->setValue($email);
$this->waitForFormUpdate();
}
public function getEmail(): string
@ -52,31 +38,52 @@ final class RegisterElement extends Element implements RegisterElementInterface
public function specifyFirstName(?string $firstName): void
{
$this->getElement('first_name')->setValue($firstName);
$this->waitForFormUpdate();
}
public function specifyLastName(?string $lastName): void
{
$this->getElement('last_name')->setValue($lastName);
$this->waitForFormUpdate();
}
public function specifyPassword(?string $password): void
{
$this->getElement('password')->setValue($password);
$this->waitForFormUpdate();
}
public function specifyPhoneNumber(string $phoneNumber): void
{
$this->getElement('phone_number')->setValue($phoneNumber);
$this->waitForFormUpdate();
}
public function verifyPassword(?string $password): void
{
$this->getElement('password_verification')->setValue($password);
$this->waitForFormUpdate();
}
public function subscribeToTheNewsletter(): void
{
$this->getElement('newsletter')->check();
$this->waitForFormUpdate();
}
/**
* @param array<string, string> $parameters
*/
public function getValidationMessage(string $element, array $parameters = []): string
{
$foundElement = $this->getFieldElement($element, $parameters);
$validationMessage = $foundElement->find('css', '.invalid-feedback');
if (null === $validationMessage) {
throw new ElementNotFoundException($this->getSession(), 'Validation message', 'css', '.invalid-feedback');
}
return $validationMessage->getText();
}
protected function getDefinedElements(): array
@ -84,6 +91,7 @@ final class RegisterElement extends Element implements RegisterElementInterface
return array_merge(parent::getDefinedElements(), [
'email' => '[data-test-email]',
'first_name' => '[data-test-first-name]',
'form' => '[data-live-name-value="sylius_shop:account:register:form"]',
'last_name' => '[data-test-last-name]',
'newsletter' => '[data-test-subscribed-to-newsletter]',
'password' => '[data-test-password-first]',
@ -92,4 +100,27 @@ final class RegisterElement extends Element implements RegisterElementInterface
'register_button' => '[data-test-button="register-button"]',
]);
}
protected function waitForFormUpdate(): void
{
$form = $this->getElement('form');
usleep(500000); // we need to sleep, as sometimes the check below is executed faster than the form sets the busy attribute
$form->waitFor(1500, fn () => !$form->hasAttribute('busy'));
}
/**
* @param array<string, string> $parameters
*
* @throws ElementNotFoundException
*/
private function getFieldElement(string $element, array $parameters): NodeElement
{
$element = $this->getElement($element, $parameters);
while (null !== $element && !$element->hasClass('field')) {
$element = $element->getParent();
}
return $element;
}
}

View file

@ -17,11 +17,6 @@ use Behat\Mink\Exception\ElementNotFoundException;
interface RegisterElementInterface
{
/**
* @throws ElementNotFoundException
*/
public function checkValidationMessageFor(string $element, string $message): bool;
public function register(): void;
public function specifyEmail(?string $email): void;
@ -39,4 +34,6 @@ interface RegisterElementInterface
public function verifyPassword(?string $password): void;
public function subscribeToTheNewsletter(): void;
public function getValidationMessage(string $element, array $parameters = []): string;
}

View file

@ -67,7 +67,7 @@ class ThankYouPage extends SymfonyPage implements ThankYouPageInterface
protected function getDefinedElements(): array
{
return array_merge(parent::getDefinedElements(), [
'create_account_button' => '[data-test-create-an-account]',
'create_account_button' => '[data-test-button="create-an-account"]',
'instructions' => '[data-test-payment-method-instructions]',
'order_details_in_account' => '[data-test-show-order-in-account]',
'payment_method_page' => '[data-test-button="payment-method-page"]',

View file

@ -1,7 +1,7 @@
{% form_theme form '@SyliusShop/Form/theme.html.twig' %}
<div class="container" {{ attributes }}>
{{ form_start(form, {'attr': {'class': 'ui loadable form', 'novalidate': 'novalidate', 'id': form.vars.id}}) }}
{{ form_start(form, {'action': path('sylius_shop_register'), 'attr': {'class': 'ui loadable form', 'novalidate': 'novalidate', 'id': form.vars.id}}) }}
{{ form_row(form._token) }}
<div class="row justify-content-center mt-4 mb-5">