1
|
|
|
<?php |
2
|
|
|
/* |
3
|
|
|
* WellCommerce Open-Source E-Commerce Platform |
4
|
|
|
* |
5
|
|
|
* This file is part of the WellCommerce package. |
6
|
|
|
* |
7
|
|
|
* (c) Adam Piotrowski <[email protected]> |
8
|
|
|
* |
9
|
|
|
* For the full copyright and license information, |
10
|
|
|
* please view the LICENSE file that was distributed with this source code. |
11
|
|
|
*/ |
12
|
|
|
namespace WellCommerce\Bundle\OrderBundle\Form\Front; |
13
|
|
|
|
14
|
|
|
use WellCommerce\Bundle\CoreBundle\Form\AbstractFormBuilder; |
15
|
|
|
use WellCommerce\Bundle\OrderBundle\Context\OrderContext; |
16
|
|
|
use WellCommerce\Bundle\OrderBundle\Entity\Order; |
17
|
|
|
use WellCommerce\Bundle\OrderBundle\Entity\PaymentMethod; |
18
|
|
|
use WellCommerce\Bundle\OrderBundle\Entity\ShippingMethod; |
19
|
|
|
use WellCommerce\Bundle\OrderBundle\Entity\ShippingMethodCost; |
20
|
|
|
use WellCommerce\Bundle\OrderBundle\Provider\Front\OrderProviderInterface; |
21
|
|
|
use WellCommerce\Bundle\OrderBundle\Provider\PaymentMethodProviderInterface; |
22
|
|
|
use WellCommerce\Bundle\OrderBundle\Provider\ShippingMethodOptionsProviderInterface; |
23
|
|
|
use WellCommerce\Bundle\OrderBundle\Provider\ShippingMethodProviderInterface; |
24
|
|
|
use WellCommerce\Component\Form\Elements\ElementInterface; |
25
|
|
|
use WellCommerce\Component\Form\Elements\FormInterface; |
26
|
|
|
use WellCommerce\Component\Form\Elements\Optioned\RadioGroup; |
27
|
|
|
|
28
|
|
|
/** |
29
|
|
|
* Class CartFormBuilder |
30
|
|
|
* |
31
|
|
|
* @author Adam Piotrowski <[email protected]> |
32
|
|
|
*/ |
33
|
|
|
class CartFormBuilder extends AbstractFormBuilder |
34
|
|
|
{ |
35
|
|
|
public function getAlias(): string |
36
|
|
|
{ |
37
|
|
|
return 'front.cart'; |
38
|
|
|
} |
39
|
|
|
|
40
|
|
|
public function buildForm(FormInterface $form) |
41
|
|
|
{ |
42
|
|
|
$order = $this->getOrderProvider()->getCurrentOrder(); |
43
|
|
|
|
44
|
|
|
$shippingAddress = $form->addChild($this->getElement('nested_fieldset', [ |
45
|
|
|
'name' => 'shippingAddress', |
46
|
|
|
'label' => 'client.heading.shipping_address', |
47
|
|
|
])); |
48
|
|
|
|
49
|
|
|
$shippingAddress->addChild($this->getElement('select', [ |
50
|
|
|
'name' => 'shippingAddress.country', |
51
|
|
|
'label' => 'client.label.address.country', |
52
|
|
|
'options' => $this->get('country.repository')->all(), |
53
|
|
|
'default' => $this->getShopStorage()->getCurrentShop()->getDefaultCountry(), |
54
|
|
|
])); |
55
|
|
|
|
56
|
|
|
$shippingMethods = $form->addChild($this->getElement('radio_group', [ |
57
|
|
|
'name' => 'shippingMethod', |
58
|
|
|
'label' => 'order.label.shipping_method', |
59
|
|
|
'transformer' => $this->getRepositoryTransformer('entity', $this->get('shipping_method.repository')), |
60
|
|
|
])); |
61
|
|
|
|
62
|
|
|
$this->addShippingMethods($order, $shippingMethods); |
63
|
|
|
|
64
|
|
|
$this->addShippingOptions($order, $form); |
65
|
|
|
|
66
|
|
|
$paymentMethods = $form->addChild($this->getElement('radio_group', [ |
67
|
|
|
'name' => 'paymentMethod', |
68
|
|
|
'label' => 'order.label.payment_method', |
69
|
|
|
'transformer' => $this->getRepositoryTransformer('entity', $this->get('payment_method.repository')), |
70
|
|
|
])); |
71
|
|
|
|
72
|
|
|
$this->addPaymentMethods($order, $paymentMethods); |
73
|
|
|
|
74
|
|
|
$form->addFilter($this->getFilter('no_code')); |
75
|
|
|
$form->addFilter($this->getFilter('trim')); |
76
|
|
|
$form->addFilter($this->getFilter('secure')); |
77
|
|
|
} |
78
|
|
|
|
79
|
|
|
/** |
80
|
|
|
* Adds shipping options if available for order's shipping method |
81
|
|
|
* |
82
|
|
|
* @param Order $order |
83
|
|
|
* @param FormInterface $form |
84
|
|
|
*/ |
85
|
|
|
private function addShippingOptions(Order $order, FormInterface $form) |
86
|
|
|
{ |
87
|
|
|
if ($order->getShippingMethod() instanceof ShippingMethod) { |
88
|
|
|
$provider = $this->getOptionsProvider($order->getShippingMethod()); |
89
|
|
|
if ($provider instanceof ShippingMethodOptionsProviderInterface) { |
90
|
|
|
$form->addChild($this->getElement('select', [ |
91
|
|
|
'name' => 'shippingMethodOption', |
92
|
|
|
'label' => 'order.label.shipping_method', |
93
|
|
|
'options' => $provider->getShippingOptions(), |
94
|
|
|
])); |
95
|
|
|
} |
96
|
|
|
} |
97
|
|
|
} |
98
|
|
|
|
99
|
|
|
/** |
100
|
|
|
* Adds shipping method options to select |
101
|
|
|
* |
102
|
|
|
* @param Order $order |
103
|
|
|
* @param ElementInterface|RadioGroup $radioGroup |
104
|
|
|
*/ |
105
|
|
|
private function addShippingMethods(Order $order, ElementInterface $radioGroup) |
106
|
|
|
{ |
107
|
|
|
$collection = $this->getShippingMethodProvider()->getCosts(new OrderContext($order)); |
108
|
|
|
|
109
|
|
|
$collection->map(function (ShippingMethodCost $shippingMethodCost) use ($radioGroup) { |
110
|
|
|
$shippingMethod = $shippingMethodCost->getShippingMethod(); |
111
|
|
|
$baseCurrency = $shippingMethod->getCurrency()->getCode(); |
112
|
|
|
$grossAmount = $shippingMethodCost->getCost()->getGrossAmount(); |
113
|
|
|
|
114
|
|
|
$label = [ |
115
|
|
|
'name' => $shippingMethod->translate()->getName(), |
116
|
|
|
'comment' => $this->getCurrencyHelper()->convertAndFormat($grossAmount, $baseCurrency), |
117
|
|
|
]; |
118
|
|
|
|
119
|
|
|
$radioGroup->addOptionToSelect($shippingMethod->getId(), $label); |
|
|
|
|
120
|
|
|
}); |
121
|
|
|
} |
122
|
|
|
|
123
|
|
|
/** |
124
|
|
|
* Adds payment method options to select |
125
|
|
|
* |
126
|
|
|
* @param Order $order |
127
|
|
|
* @param ElementInterface|RadioGroup $radioGroup |
128
|
|
|
*/ |
129
|
|
|
private function addPaymentMethods(Order $order, ElementInterface $radioGroup) |
130
|
|
|
{ |
131
|
|
|
$paymentMethods = $this->getPaymentMethodProvider()->getPaymentMethodsForOrder($order); |
132
|
|
|
|
133
|
|
|
$paymentMethods->map(function (PaymentMethod $paymentMethod) use ($radioGroup) { |
134
|
|
|
$radioGroup->addOptionToSelect($paymentMethod->getId(), $paymentMethod->translate()->getName()); |
|
|
|
|
135
|
|
|
}); |
136
|
|
|
} |
137
|
|
|
|
138
|
|
|
private function getShippingMethodProvider(): ShippingMethodProviderInterface |
139
|
|
|
{ |
140
|
|
|
return $this->get('shipping_method.provider'); |
141
|
|
|
} |
142
|
|
|
|
143
|
|
|
private function getPaymentMethodProvider(): PaymentMethodProviderInterface |
144
|
|
|
{ |
145
|
|
|
return $this->get('payment_method.provider'); |
146
|
|
|
} |
147
|
|
|
|
148
|
|
|
private function getOrderProvider(): OrderProviderInterface |
149
|
|
|
{ |
150
|
|
|
return $this->get('order.provider.front'); |
151
|
|
|
} |
152
|
|
|
|
153
|
|
|
private function getOptionsProvider(ShippingMethod $method) |
154
|
|
|
{ |
155
|
|
|
$provider = $method->getOptionsProvider(); |
156
|
|
|
$collection = $this->get('shipping_method.options_provider.collection'); |
157
|
|
|
|
158
|
|
|
if ($collection->containsKey($provider)) { |
159
|
|
|
return $collection->get($provider); |
160
|
|
|
} |
161
|
|
|
|
162
|
|
|
return null; |
163
|
|
|
} |
164
|
|
|
} |
165
|
|
|
|
Let’s take a look at an example:
In the above example, the authenticate() method works fine as long as you just pass instances of MyUser. However, if you now also want to pass a different implementation of User which does not have a getDisplayName() method, the code will break.
Available Fixes
Change the type-hint for the parameter:
Add an additional type-check:
Add the method to the interface: