Completed
Push — master ( 49a1ab...66d152 )
by Paweł
19:14 queued 06:15
created

iShouldBeNotifiedThatThisProductDoesNotHaveSufficientStock()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 7
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 1
Metric Value
c 1
b 0
f 1
dl 0
loc 7
rs 9.4285
cc 1
eloc 4
nc 1
nop 1
1
<?php
2
3
/*
4
 * This file is part of the Sylius package.
5
 *
6
 * (c) Paweł Jędrzejewski
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 */
11
12
namespace Sylius\Behat\Context\Ui;
13
14
use Behat\Behat\Context\Context;
15
use Sylius\Behat\Page\Shop\Checkout\AddressPageInterface;
16
use Sylius\Behat\Page\Shop\Checkout\SelectPaymentPageInterface;
17
use Sylius\Behat\Page\Shop\Checkout\SelectShippingPageInterface;
18
use Sylius\Behat\Page\Shop\Checkout\CompletePageInterface;
19
use Sylius\Behat\Page\Shop\HomePageInterface;
20
use Sylius\Behat\Page\Shop\Checkout\ThankYouPageInterface;
21
use Sylius\Behat\Service\SharedSecurityServiceInterface;
22
use Sylius\Component\Addressing\Model\CountryInterface;
23
use Sylius\Behat\Page\UnexpectedPageException;
24
use Sylius\Component\Core\Formatter\StringInflector;
25
use Sylius\Component\Core\Model\AddressInterface;
26
use Sylius\Component\Core\Model\ProductInterface;
27
use Sylius\Component\Core\Model\ShippingMethodInterface;
28
use Sylius\Component\Core\Model\ShopUserInterface;
29
use Sylius\Behat\Service\SharedStorageInterface;
30
use Sylius\Component\Order\Repository\OrderRepositoryInterface;
31
use Sylius\Component\Payment\Model\PaymentMethodInterface;
32
use Sylius\Component\Resource\Factory\FactoryInterface;
33
use Webmozart\Assert\Assert;
34
35
/**
36
 * @author Arkadiusz Krakowiak <[email protected]>
37
 */
38
final class CheckoutContext implements Context
39
{
40
    /**
41
     * @var SharedStorageInterface
42
     */
43
    private $sharedStorage;
44
45
    /**
46
     * @var HomePageInterface
47
     */
48
    private $homePage;
49
50
    /**
51
     * @var AddressPageInterface
52
     */
53
    private $addressPage;
54
55
    /**
56
     * @var SelectPaymentPageInterface
57
     */
58
    private $selectPaymentPage;
59
60
    /**
61
     * @var ThankYouPageInterface
62
     */
63
    private $thankYouPage;
64
65
    /**
66
     * @var SelectShippingPageInterface
67
     */
68
    private $selectShippingPage;
69
70
    /**
71
     * @var CompletePageInterface
72
     */
73
    private $completePage;
74
75
    /**
76
     * @var OrderRepositoryInterface
77
     */
78
    private $orderRepository;
79
80
    /**
81
     * @var SharedSecurityServiceInterface
82
     */
83
    private $sharedSecurityService;
84
85
    /**
86
     * @var FactoryInterface
87
     */
88
    private $addressFactory;
89
90
    /**
91
     * @param SharedStorageInterface $sharedStorage
92
     * @param HomePageInterface $homePage
93
     * @param AddressPageInterface $addressPage
94
     * @param SelectPaymentPageInterface $selectPaymentPage
95
     * @param ThankYouPageInterface $thankYouPage
96
     * @param SelectShippingPageInterface $selectShippingPage
97
     * @param CompletePageInterface $completePage
98
     * @param OrderRepositoryInterface $orderRepository
99
     * @param SharedSecurityServiceInterface $sharedSecurityService
100
     * @param FactoryInterface $addressFactory
101
     */
102
    public function __construct(
103
        SharedStorageInterface $sharedStorage,
104
        HomePageInterface $homePage,
105
        AddressPageInterface $addressPage,
106
        SelectPaymentPageInterface $selectPaymentPage,
107
        ThankYouPageInterface $thankYouPage,
108
        SelectShippingPageInterface $selectShippingPage,
109
        CompletePageInterface $completePage,
110
        OrderRepositoryInterface $orderRepository,
111
        SharedSecurityServiceInterface $sharedSecurityService,
112
        FactoryInterface $addressFactory
113
    ) {
114
        $this->sharedStorage = $sharedStorage;
115
        $this->homePage = $homePage;
116
        $this->addressPage = $addressPage;
117
        $this->selectPaymentPage = $selectPaymentPage;
118
        $this->thankYouPage = $thankYouPage;
119
        $this->selectShippingPage = $selectShippingPage;
120
        $this->completePage = $completePage;
121
        $this->orderRepository = $orderRepository;
122
        $this->sharedSecurityService = $sharedSecurityService;
123
        $this->addressFactory = $addressFactory;
124
    }
125
126
    /**
127
     * @Given /^I proceed without selecting shipping address$/
128
     */
129
    public function iProceedWithoutSelectingShippingAddress()
130
    {
131
        $this->addressPage->open();
132
        $this->addressPage->nextStep();
133
    }
134
135
    /**
136
     * @Given I am at the checkout addressing step
137
     */
138
    public function iAmAtTheCheckoutAddressingStep()
139
    {
140
        $this->addressPage->open();
141
    }
142
143
    /**
144
     * @Given /^(this user) bought this product$/
145
     */
146
    public function thisUserBought(ShopUserInterface $user)
147
    {
148
        $this->sharedSecurityService->performActionAsShopUser($user, function () {
149
            $this->iProceedSelectingPaymentMethod();
150
            $this->iConfirmMyOrder();
151
        });
152
    }
153
154
    /**
155
     * @When /^I specify the shipping (address as "([^"]+)", "([^"]+)", "([^"]+)", "([^"]+)" for "([^"]+)")$/
156
     * @When /^I (do not specify any shipping address) information$/
157
     */
158
    public function iSpecifyTheShippingAddressAs(AddressInterface $address)
159
    {
160
        $key = sprintf(
161
            'shipping_address_%s_%s',
162
            strtolower($address->getFirstName()),
163
            strtolower($address->getLastName())
164
        );
165
        $this->sharedStorage->set($key, $address);
166
167
        $this->addressPage->specifyShippingAddress($address);
168
    }
169
170
    /**
171
     * @When I specify shipping country province as :province
172
     */
173
    public function iSpecifyShippingCountryProvinceAs($province)
174
    {
175
        $this->addressPage->specifyShippingAddressProvince($province);
176
    }
177
178
    /**
179
     * @When I specify billing country province as :province
180
     */
181
    public function iSpecifyBillingCountryProvinceAs($province)
182
    {
183
        $this->addressPage->specifyBillingAddressProvince($province);
184
    }
185
186
    /**
187
     * @When /^I specify the billing (address as "([^"]+)", "([^"]+)", "([^"]+)", "([^"]+)" for "([^"]+)")$/
188
     * @When /^I (do not specify any billing address) information$/
189
     */
190
    public function iSpecifyTheBillingAddressAs(AddressInterface $address)
191
    {
192
        $this->iChooseTheDifferentBillingAddress();
193
        $key = sprintf(
194
            'billing_address_%s_%s',
195
            strtolower($address->getFirstName()),
196
            strtolower($address->getLastName())
197
        );
198
        $this->sharedStorage->set($key, $address);
199
200
        $this->addressPage->specifyBillingAddress($address);
201
    }
202
203
    /**
204
     * @When /^I specified the shipping (address as "([^"]+)", "([^"]+)", "([^"]+)", "([^"]+)" for "([^"]+)")$/
205
     */
206
    public function iSpecifiedTheShippingAddress(AddressInterface $address)
207
    {
208
        $this->addressPage->open();
209
        $this->iSpecifyTheShippingAddressAs($address);
210
211
        $key = sprintf('billing_address_%s_%s', strtolower($address->getFirstName()), strtolower($address->getLastName()));
212
        $this->sharedStorage->set($key, $address);
213
214
        $this->iCompleteTheAddressingStep();
215
    }
216
217
    /**
218
     * @When I choose the different billing address
219
     */
220
    public function iChooseTheDifferentBillingAddress()
221
    {
222
        $this->addressPage->chooseDifferentBillingAddress();
223
    }
224
225
    /**
226
     * @When I specify the email as :email
227
     * @When I do not specify the email
228
     */
229
    public function iSpecifyTheEmail($email = null)
230
    {
231
        $this->addressPage->specifyEmail($email);
232
    }
233
234
    /**
235
     * @When I select :shippingMethod shipping method
236
     */
237
    public function iSelectShippingMethod($shippingMethod)
238
    {
239
        $this->selectShippingPage->selectShippingMethod($shippingMethod);
240
    }
241
242
    /**
243
     * @Then I should not be able to select :shippingMethod shipping method
244
     */
245
    public function iShouldNotBeAbleToSelectShippingMethod($shippingMethod)
246
    {
247
        Assert::false(
248
            $this->selectShippingPage->hasShippingMethod($shippingMethod),
249
            sprintf('Shipping method "%s" should not be available but it does.', $shippingMethod)
250
        );
251
    }
252
253
    /**
254
     * @When I complete the addressing step
255
     * @When I try to complete the addressing step
256
     */
257
    public function iCompleteTheAddressingStep()
258
    {
259
        $this->addressPage->nextStep();
260
    }
261
262
    /**
263
     * @When I go back to store
264
     */
265
    public function iGoBackToStore()
266
    {
267
        $this->addressPage->backToStore();
268
    }
269
270
    /**
271
     * @When I complete the shipping step
272
     */
273
    public function iCompleteTheShippingStep()
274
    {
275
        $this->selectShippingPage->nextStep();
276
    }
277
278
    /**
279
     * @When I decide to change my address
280
     */
281
    public function iDecideToChangeMyAddress()
282
    {
283
        $this->selectShippingPage->changeAddress();
284
    }
285
286
    /**
287
     * @When I decide to change order shipping method
288
     */
289
    public function iDecideToChangeMyShippingMethod()
290
    {
291
        $this->selectPaymentPage->changeShippingMethod();
292
    }
293
294
    /**
295
     * @When I go to the addressing step
296
     */
297
    public function iGoToTheAddressingStep()
298
    {
299
        if ($this->selectShippingPage->isOpen()) {
300
            $this->selectShippingPage->changeAddressByStepLabel();
301
302
            return;
303
        }
304
305
        if ($this->selectPaymentPage->isOpen()) {
306
            $this->selectPaymentPage->changeAddressByStepLabel();
307
308
            return;
309
        }
310
311
        if ($this->completePage->isOpen()) {
312
            $this->completePage->changeAddress();
313
314
            return;
315
        }
316
317
        throw new UnexpectedPageException('It is impossible to go to addressing step from current page.');
318
    }
319
320
    /**
321
     * @When I go to the shipping step
322
     */
323
    public function iGoToTheShippingStep()
324
    {
325
        if ($this->selectPaymentPage->isOpen()) {
326
            $this->selectPaymentPage->changeShippingMethodByStepLabel();
327
328
            return;
329
        }
330
331
        if ($this->completePage->isOpen()) {
332
            $this->completePage->changeShippingMethod();
333
334
            return;
335
        }
336
337
        throw new UnexpectedPageException('It is impossible to go to shipping step from current page.');
338
    }
339
340
    /**
341
     * @When I go to the payment step
342
     */
343
    public function iGoToThePaymentStep()
344
    {
345
        $this->completePage->changePaymentMethod();
346
    }
347
348
    /**
349
     * @When /^I proceed selecting ("[^"]+" as shipping country)$/
350
     */
351
    public function iProceedSelectingShippingCountry(CountryInterface $shippingCountry = null)
352
    {
353
        $this->addressPage->open();
354
        $shippingAddress = $this->createDefaultAddress();
355
        if (null !== $shippingCountry) {
356
            $shippingAddress->setCountryCode($shippingCountry->getCode());
357
        }
358
359
        $this->addressPage->specifyShippingAddress($shippingAddress);
360
        $this->addressPage->nextStep();
361
    }
362
363
    /**
364
     * @When /^I proceed selecting ("[^"]+" as shipping country) with "([^"]+)" method$/
365
     */
366
    public function iProceedSelectingShippingCountryAndShippingMethod(CountryInterface $shippingCountry = null, $shippingMethodName)
367
    {
368
        $this->iProceedSelectingShippingCountry($shippingCountry);
369
370
        $this->selectShippingPage->selectShippingMethod($shippingMethodName ?: 'Free');
371
        $this->selectShippingPage->nextStep();
372
    }
373
374
    /**
375
     * @When /^I proceed selecting "([^"]+)" shipping method$/
376
     * @Given /^I chose "([^"]*)" shipping method$/
377
     */
378
    public function iProceedSelectingShippingMethod($shippingMethodName)
379
    {
380
        $this->iProceedSelectingShippingCountryAndShippingMethod(null, $shippingMethodName);
381
    }
382
383
    /**
384
     * @When /^I choose "([^"]*)" payment method$/
385
     */
386
    public function iChoosePaymentMethod($paymentMethodName)
387
    {
388
        $this->selectPaymentPage->selectPaymentMethod($paymentMethodName ?: 'Offline');
389
        $this->selectPaymentPage->nextStep();
390
    }
391
392
    /**
393
     * @When I change payment method to :paymentMethodName
394
     */
395
    public function iChangePaymentMethodTo($paymentMethodName)
396
    {
397
        $this->thankYouPage->choosePaymentMethod($paymentMethodName);
398
    }
399
400
    /**
401
     * @When /^I proceed selecting "([^"]*)" as shipping country with "([^"]*)" payment method$/
402
     */
403
    public function iProceedSelectingShippingCountryAndPaymentMethod($shippingCountry, $paymentMethodName)
404
    {
405
        $this->iProceedSelectingShippingCountryAndShippingMethod($shippingCountry, null);
406
407
        $this->iChoosePaymentMethod($paymentMethodName);
408
    }
409
410
    /**
411
     * @Given I have proceeded selecting :paymentMethodName payment method
412
     * @When /^I (?:proceed|proceeded) selecting "([^"]+)" payment method$/
413
     */
414
    public function iProceedSelectingPaymentMethod($paymentMethodName = 'Offline')
415
    {
416
        $this->iProceedSelectingShippingCountryAndPaymentMethod(null, $paymentMethodName);
417
    }
418
419
    /**
420
     * @When /^I change shipping method to "([^"]*)"$/
421
     */
422
    public function iChangeShippingMethod($shippingMethodName)
423
    {
424
        $this->selectPaymentPage->changeShippingMethod();
425
        $this->selectShippingPage->selectShippingMethod($shippingMethodName);
426
        $this->selectShippingPage->nextStep();
427
    }
428
429
    /**
430
     * @When /^I provide additional note like "([^"]+)"$/
431
     */
432
    public function iProvideAdditionalNotesLike($notes)
433
    {
434
        $this->sharedStorage->set('additional_note', $notes);
435
        $this->completePage->addNotes($notes);
436
    }
437
438
    /**
439
     * @When /^I proceed as guest "([^"]*)" with ("[^"]+" as shipping country)$/
440
     */
441
    public function iProceedLoggingAsGuestWithAsShippingCountry($email, CountryInterface $shippingCountry = null)
442
    {
443
        $this->addressPage->open();
444
        $this->addressPage->specifyEmail($email);
445
        $shippingAddress = $this->createDefaultAddress();
446
        if (null !== $shippingCountry) {
447
            $shippingAddress->setCountryCode($shippingCountry->getCode());
448
        }
449
450
        $this->addressPage->specifyShippingAddress($shippingAddress);
451
        $this->addressPage->nextStep();
452
    }
453
454
    /**
455
     * @Given I have confirmed my order
456
     * @When I confirm my order
457
     */
458
    public function iConfirmMyOrder()
459
    {
460
        $this->completePage->confirmOrder();
461
    }
462
463
    /**
464
     * @When I specify the password as :password
465
     */
466
    public function iSpecifyThePasswordAs($password)
467
    {
468
        $this->addressPage->specifyPassword($password);
469
    }
470
471
    /**
472
     * @When I sign in
473
     */
474
    public function iSignIn()
475
    {
476
        $this->addressPage->signIn();
477
    }
478
479
    /**
480
     * @Then I should see the thank you page
481
     */
482
    public function iShouldSeeTheThankYouPage()
483
    {
484
        Assert::true(
485
            $this->thankYouPage->hasThankYouMessage(),
486
            'I should see thank you message, but I do not'
487
        );
488
    }
489
490
    /**
491
     * @Then I should not see the thank you page
492
     */
493
    public function iShouldNotSeeTheThankYouPage()
494
    {
495
        Assert::false(
496
            $this->thankYouPage->isOpen(),
497
            'I should not see thank you message, but I do'
498
        );
499
    }
500
501
    /**
502
     * @Given I should be informed with :paymentMethod payment method instructions
503
     */
504
    public function iShouldBeInformedWithPaymentMethodInstructions(PaymentMethodInterface $paymentMethod)
505
    {
506
        Assert::same(
507
            $this->thankYouPage->getInstructions(),
508
            $paymentMethod->getInstructions()
509
        );
510
    }
511
512
    /**
513
     * @Then /^I should be redirected (?:|back )to the thank you page$/
514
     */
515
    public function iShouldBeRedirectedBackToTheThankYouPage()
516
    {
517
        $this->thankYouPage->waitForResponse(5);
518
519
        Assert::true(
520
            $this->thankYouPage->isOpen(),
521
            'I should be on thank you page, but I am not.'
522
        );
523
    }
524
525
    /**
526
     * @Then I should be on the checkout shipping step
527
     */
528
    public function iShouldBeOnTheCheckoutShippingStep()
529
    {
530
        Assert::true(
531
            $this->selectShippingPage->isOpen(),
532
            'Checkout shipping page should be opened, but it is not.'
533
        );
534
    }
535
536
    /**
537
     * @Then I should be on the checkout summary step
538
     */
539
    public function iShouldBeOnTheCheckoutSummaryStep()
540
    {
541
        Assert::true(
542
            $this->completePage->isOpen(),
543
            'Checkout summary page should be opened, but it is not.'
544
        );
545
    }
546
547
    /**
548
     * @Then /^I should(?:| also) be notified that the "([^"]+)" and the "([^"]+)" in (shipping|billing) details are required$/
549
     */
550
    public function iShouldBeNotifiedThatTheAndTheInShippingDetailsAreRequired($firstElement, $secondElement, $type)
551
    {
552
        $this->assertElementValidationMessage($type, $firstElement, sprintf('Please enter %s.', $firstElement));
553
        $this->assertElementValidationMessage($type, $secondElement, sprintf('Please enter %s.', $secondElement));
554
    }
555
556
    /**
557
     * @Then I should be informed that my order cannot be shipped to this address
558
     */
559
    public function iShouldBeInformedThatMyOrderCannotBeShippedToThisAddress()
560
    {
561
        Assert::true(
562
            $this->selectShippingPage->hasNoShippingMethodsMessage(),
563
            'Shipping page should have no shipping methods message but it does not.'
564
        );
565
    }
566
567
    /**
568
     * @Then I should be able to log in
569
     */
570
    public function iShouldBeAbleToLogIn()
571
    {
572
        Assert::true(
573
            $this->addressPage->canSignIn(),
574
            'I should be able to login, but I am not.'
575
        );
576
    }
577
578
    /**
579
     * @Then the login form should no longer be accessible
580
     */
581
    public function theLoginFormShouldNoLongerBeAccessible()
582
    {
583
        Assert::false(
584
            $this->addressPage->canSignIn(),
585
            'I should not be able to login, but I am.'
586
        );
587
    }
588
589
    /**
590
     * @Then I should be notified about bad credentials
591
     */
592
    public function iShouldBeNotifiedAboutBadCredentials()
593
    {
594
        Assert::true(
595
            $this->addressPage->checkInvalidCredentialsValidation(),
596
            'I should see validation error, but I do not.'
597
        );
598
    }
599
600
    /**
601
     * @Then my order's shipping address should be to :fullName
602
     */
603
    public function iShouldSeeThisShippingAddressAsShippingAddress($fullName)
604
    {
605
        $address = $this->sharedStorage->get('shipping_address_'.StringInflector::nameToLowercaseCode($fullName));
606
        Assert::true(
607
            $this->completePage->hasShippingAddress($address),
608
            'Shipping address is improper.'
609
        );
610
    }
611
612
    /**
613
     * @Then my order's billing address should be to :fullName
614
     */
615
    public function iShouldSeeThisBillingAddressAsBillingAddress($fullName)
616
    {
617
        $address = $this->sharedStorage->get('billing_address_'.StringInflector::nameToLowercaseCode($fullName));
618
        Assert::true(
619
            $this->completePage->hasBillingAddress($address),
620
            'Billing address is improper.'
621
        );
622
    }
623
624
    /**
625
     * @Then address to :fullName should be used for both shipping and billing of my order
626
     */
627
    public function iShouldSeeThisShippingAddressAsShippingAndBillingAddress($fullName)
628
    {
629
        $this->iShouldSeeThisShippingAddressAsShippingAddress($fullName);
630
        $this->iShouldSeeThisBillingAddressAsBillingAddress($fullName);
631
    }
632
633
    /**
634
     * @Given I am at the checkout payment step
635
     */
636
    public function iAmAtTheCheckoutPaymentStep()
637
    {
638
        $this->selectPaymentPage->open();
639
    }
640
641
    /**
642
     * @When I complete the payment step
643
     */
644
    public function iCompleteThePaymentStep()
645
    {
646
        $this->selectPaymentPage->nextStep();
647
    }
648
649
    /**
650
     * @When I select :paymentMethodName payment method
651
     */
652
    public function iSelectPaymentMethod($paymentMethodName)
653
    {
654
        $this->selectPaymentPage->selectPaymentMethod($paymentMethodName);
655
    }
656
657
    /**
658
     * @Then I should not be able to select :paymentMethodName payment method
659
     */
660
    public function iShouldNotBeAbleToSelectPaymentMethod($paymentMethodName)
661
    {
662
        Assert::false(
663
            $this->selectPaymentPage->hasPaymentMethod($paymentMethodName),
664
            sprintf('Payment method "%s" should not be available, but it does.', $paymentMethodName)
665
        );
666
    }
667
668
    /**
669
     * @Then I should be able to select :paymentMethodName payment method
670
     */
671
    public function iShouldBeAbleToSelectPaymentMethod($paymentMethodName)
672
    {
673
        Assert::true(
674
            $this->selectPaymentPage->hasPaymentMethod($paymentMethodName),
675
            sprintf('Payment method "%s" should be available, but it does not.', $paymentMethodName)
676
        );
677
    }
678
679
    /**
680
     * @When I proceed order with :shippingMethod shipping method and :paymentMethod payment
681
     */
682
    public function iProceedOrderWithShippingMethodAndPayment($shippingMethod, $paymentMethod)
683
    {
684
        $this->iSelectShippingMethod($shippingMethod);
685
        $this->iCompleteTheShippingStep();
686
        $this->iSelectPaymentMethod($paymentMethod);
687
        $this->iCompleteThePaymentStep();
688
    }
689
690
    /**
691
     * @Given I should have :quantity :productName products in the cart
692
     */
693
    public function iShouldHaveProductsInTheCart($quantity, $productName)
694
    {
695
        Assert::true(
696
            $this->completePage->hasItemWithProductAndQuantity($productName, $quantity),
697
            sprintf('There is no "%s" with quantity %s on order summary page, but it should.', $productName, $quantity)
698
        );
699
    }
700
701
    /**
702
     * @Then my order shipping should be :price
703
     */
704
    public function myOrderShippingShouldBe($price)
705
    {
706
        Assert::true(
707
            $this->completePage->hasShippingTotal($price),
708
            sprintf('The shipping total should be %s, but it is not.',$price)
709
        );
710
    }
711
712
    /**
713
     * @Then /^the ("[^"]+" product) should have unit price discounted by ("\$\d+")$/
714
     */
715
    public function theShouldHaveUnitPriceDiscountedFor(ProductInterface $product, $amount)
716
    {
717
        Assert::true(
718
            $this->completePage->hasProductDiscountedUnitPriceBy($product, $amount),
719
            sprintf('Product %s should have discounted price by %s, but it does not have.', $product->getName(), $amount)
720
        );
721
    }
722
723
    /**
724
     * @Then /^my order total should be ("(?:\£|\$)\d+")$/
725
     */
726
    public function myOrderTotalShouldBe($total)
727
    {
728
        Assert::true(
729
            $this->completePage->hasOrderTotal($total),
730
            sprintf('Order total should have %s total, but it does not have.', $total)
731
        );
732
    }
733
734
    /**
735
     * @Then my order promotion total should be :promotionTotal
736
     */
737
    public function myOrderPromotionTotalShouldBe($promotionTotal)
738
    {
739
        Assert::true(
740
            $this->completePage->hasPromotionTotal($promotionTotal),
741
            sprintf('The total discount should be %s, but it does not.', $promotionTotal)
742
        );
743
    }
744
745
    /**
746
     * @Then :promotionName should be applied to my order
747
     */
748
    public function shouldBeAppliedToMyOrder($promotionName)
749
    {
750
        Assert::true(
751
            $this->completePage->hasPromotion($promotionName),
752
            sprintf('The promotion %s should appear on the page, but it does not.', $promotionName)
753
        );
754
    }
755
756
    /**
757
     * @Given my tax total should be :taxTotal
758
     */
759
    public function myTaxTotalShouldBe($taxTotal)
760
    {
761
        Assert::true(
762
            $this->completePage->hasTaxTotal($taxTotal),
763
            sprintf('The tax total should be %s, but it does not.', $taxTotal)
764
        );
765
    }
766
767
    /**
768
     * @Then my order's shipping method should be :shippingMethod
769
     */
770
    public function myOrderSShippingMethodShouldBe(ShippingMethodInterface $shippingMethod)
771
    {
772
        Assert::true(
773
            $this->completePage->hasShippingMethod($shippingMethod),
774
            sprintf('I should see %s shipping method, but I do not.', $shippingMethod->getName())
775
        );
776
    }
777
778
    /**
779
     * @Then my order's payment method should be :paymentMethod
780
     */
781
    public function myOrderSPaymentMethodShouldBe(PaymentMethodInterface $paymentMethod)
782
    {
783
        Assert::true(
784
            $this->completePage->hasPaymentMethod($paymentMethod),
785
            sprintf('I should see %s payment method, but I do not.', $paymentMethod->getName())
786
        );
787
    }
788
789
    /**
790
     * @Then I should be redirected to the homepage
791
     */
792
    public function iShouldBeRedirectedToTheHomepage()
793
    {
794
        Assert::true(
795
            $this->homePage->isOpen(),
796
            'Shop homepage should be opened, but it is not.'
797
        );
798
    }
799
800
    /**
801
     * @Then I should be redirected to the addressing step
802
     */
803
    public function iShouldBeRedirectedToTheAddressingStep()
804
    {
805
        Assert::true(
806
            $this->addressPage->isOpen(),
807
            'Checkout addressing step should be opened, but it is not.'
808
        );
809
    }
810
811
    /**
812
     * @Given I should be able to go to the shipping step again
813
     */
814
    public function iShouldBeAbleToGoToTheShippingStepAgain()
815
    {
816
        $this->addressPage->nextStep();
817
818
        Assert::true(
819
            $this->selectShippingPage->isOpen(),
820
            'Checkout shipping step should be opened, but it is not.'
821
        );
822
    }
823
824
    /**
825
     * @Then I should be redirected to the shipping step
826
     */
827
    public function iShouldBeRedirectedToTheShippingStep()
828
    {
829
        Assert::true(
830
            $this->selectShippingPage->isOpen(),
831
            'Checkout shipping step should be opened, but it is not.'
832
        );
833
    }
834
835
    /**
836
     * @Then I should be able to pay again
837
     */
838
    public function iShouldBeAbleToPayAgain()
839
    {
840
        Assert::true(
841
            $this->thankYouPage->isOpen(),
842
            'I should be on thank you page, but I am not.'
843
        );
844
845
        Assert::true(
846
            $this->thankYouPage->hasPayAction(),
847
            'I should be able to pay, but I am not able to.'
848
        );
849
    }
850
851
    /**
852
     * @Given I should be able to go to the payment step again
853
     */
854
    public function iShouldBeAbleToGoToThePaymentStepAgain()
855
    {
856
        $this->selectShippingPage->nextStep();
857
858
        Assert::true(
859
            $this->selectPaymentPage->isOpen(),
860
            'Checkout payment step should be opened, but it is not.'
861
        );
862
    }
863
864
    /**
865
     * @Then I should be redirected to the payment step
866
     */
867
    public function iShouldBeRedirectedToThePaymentStep()
868
    {
869
        Assert::true(
870
            $this->selectPaymentPage->isOpen(),
871
            'Checkout payment step should be opened, but it is not.'
872
        );
873
    }
874
875
    /**
876
     * @Given I should be able to go to the summary page again
877
     */
878
    public function iShouldBeAbleToGoToTheSummaryPageAgain()
879
    {
880
        $this->selectPaymentPage->nextStep();
881
882
        Assert::true(
883
            $this->completePage->isOpen(),
884
            'Checkout summary page should be opened, but it is not.'
885
        );
886
    }
887
888
    /**
889
     * @Given I should see shipping method :shippingMethodName with fee :fee
890
     */
891
    public function iShouldSeeShippingFee($shippingMethodName, $fee)
892
    {
893
        Assert::true(
894
            $this->selectShippingPage->hasShippingMethodFee($shippingMethodName, $fee),
895
            sprintf('The shipping fee should be %s, but it does not.', $fee)
896
        );
897
    }
898
899
    /**
900
     * @When /^I complete addressing step with email "([^"]+)" and ("([^"]+)" as shipping country)$/
901
     */
902
    public function iCompleteAddressingStepWithEmail($email, AddressInterface $address)
903
    {
904
        $this->addressPage->open();
905
        $this->iSpecifyTheEmail($email);
906
        $this->iSpecifyTheShippingAddressAs($address);
907
        $this->iCompleteTheAddressingStep();
908
    }
909
910
    /**
911
     * @Given I confirm my changes
912
     */
913
    public function iConfirmMyChanges()
914
    {
915
        $this->thankYouPage->saveChanges();
916
    }
917
918
    /**
919
     * @Then the :product product should have unit price :price
920
     */
921
    public function theProductShouldHaveUnitPrice(ProductInterface $product, $price)
922
    {
923
        Assert::true(
924
            $this->completePage->hasProductUnitPrice($product, $price),
925
            sprintf('Product %s should have unit price %s, but it does not have.', $product->getName(), $price)
926
        );
927
    }
928
929
    /**
930
     * @Given /^I should be notified that (this product) does not have sufficient stock$/
931
     */
932
    public function iShouldBeNotifiedThatThisProductDoesNotHaveSufficientStock(ProductInterface $product)
933
    {
934
        Assert::true(
935
            $this->completePage->hasProductOutOfStockValidationMessage($product),
936
            sprintf('I should see validation message for %s product', $product->getName())
937
        );
938
    }
939
940
    /**
941
     * @return AddressInterface
942
     */
943
    private function createDefaultAddress()
944
    {
945
        /** @var AddressInterface $address */
946
        $address = $this->addressFactory->createNew();
947
        $address->setFirstName('John');
948
        $address->setLastName('Doe');
949
        $address->setCountryCode('US');
950
        $address->setCity('North Bridget');
951
        $address->setPostcode('93-554');
952
        $address->setStreet('0635 Myron Hollow Apt. 711');
953
        $address->setPhoneNumber('321123456');
954
955
        return $address;
956
    }
957
958
    /**
959
     * @param string $type
960
     * @param string $element
961
     * @param string $expectedMessage
962
     *
963
     * @throws \InvalidArgumentException
964
     */
965
    private function assertElementValidationMessage($type, $element, $expectedMessage)
966
    {
967
        $element = sprintf('%s_%s', $type, implode('_', explode(' ', $element)));
968
        Assert::true(
969
            $this->addressPage->checkValidationMessageFor($element, $expectedMessage),
970
            sprintf('The %s should be required.', $element)
971
        );
972
    }
973
}
974