Skip to content

Commit 7801954

Browse files
committed
[Task] Add new checkoutAddressAttribute template
1 parent a7adde8 commit 7801954

File tree

16 files changed

+534
-0
lines changed

16 files changed

+534
-0
lines changed
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Create custom address attribute and all corresponding functionality to use it in checkout address forms.
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
<?php
2+
/**
3+
* CustomAttributes
4+
*
5+
* @copyright Copyright © 2019 Staempfli AG. All rights reserved.
6+
* @author juan.alonso@staempfli.com
7+
*/
8+
9+
namespace ${Vendorname}\${Modulename}\Block\Widget;
10+
11+
use Magento\Framework\View\Element\Template;
12+
13+
class CustomAttributes extends Template
14+
{
15+
/**
16+
* @var string $_template
17+
*/
18+
protected $_template = "${Vendorname}_${Modulename}::custom-attributes.phtml";
19+
/**
20+
* @var \Magento\Framework\Api\AddressMetadataInterface
21+
*/
22+
private $addressMetadata;
23+
24+
public function __construct(
25+
\Magento\Customer\Api\AddressMetadataInterface $addressMetadata,
26+
Template\Context $context,
27+
array $data = []
28+
) {
29+
parent::__construct($context, $data);
30+
$this->addressMetadata = $addressMetadata;
31+
}
32+
33+
public function getCustomAttributes()
34+
{
35+
$customAttributes = [];
36+
37+
/* @var \Magento\Customer\Api\Data\AddressInterface $address */
38+
$address = $this->getData('address');
39+
$customAttributesMetadata = $this->addressMetadata->getCustomAttributesMetadata(get_class($address));
40+
41+
foreach ($customAttributesMetadata as $attributeMetadata) {
42+
$attributeCode = $attributeMetadata->getAttributeCode();
43+
$customAttributes[$attributeCode] = $address->getCustomAttribute($attributeCode) ? $address->getCustomAttribute($attributeCode)->getValue() : '';
44+
}
45+
46+
return $customAttributes;
47+
}
48+
}
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
<?php
2+
/**
3+
* EditPlugin
4+
*
5+
* @copyright Copyright © 2019 Staempfli AG. All rights reserved.
6+
* @author juan.alonso@staempfli.com
7+
*/
8+
9+
namespace ${Vendorname}\${Modulename}\Plugin\Block\Address;
10+
11+
12+
class EditPlugin
13+
{
14+
public function afterGetNameBlockHtml(\Magento\Customer\Block\Address\Edit $editAddressBlock, $nameBlockHtml)
15+
{
16+
$customAttributesBlock = $editAddressBlock->getLayout()
17+
->createBlock(\${Vendorname}\${Modulename}\Block\Widget\CustomAttributes::class)
18+
->setData('address', $editAddressBlock->getAddress());
19+
20+
return $nameBlockHtml . $customAttributesBlock->toHtml() ;
21+
}
22+
}
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
<?php
2+
namespace ${Vendorname}\${Modulename}\Plugin\Model\Checkout;
3+
4+
class LayoutProcessor
5+
{
6+
/**
7+
* @param \Magento\Checkout\Block\Checkout\LayoutProcessor $subject
8+
* @param array $jsLayout
9+
* @return array
10+
* @SuppressWarnings("unused")
11+
*/
12+
public function afterProcess(\Magento\Checkout\Block\Checkout\LayoutProcessor $subject, array $jsLayout) //@codingStandardsIgnoreLine
13+
{
14+
foreach ($jsLayout['components']['checkout']['children']['steps']['children']['shipping-step']['children']
15+
['shippingAddress']['children']['shipping-address-fieldset']['children'] as $childname => &$child) {
16+
switch ($childname) {
17+
case '${fieldname}':
18+
$child['sortOrder'] = 120;
19+
break;
20+
}
21+
}
22+
23+
return $jsLayout;
24+
}
25+
}
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
<?php
2+
/**
3+
* CustomAttributeListPlugin
4+
*
5+
* @copyright Copyright © 2019 Staempfli AG. All rights reserved.
6+
* @author juan.alonso@staempfli.com
7+
*/
8+
9+
namespace ${Vendorname}\${Modulename}\Plugin\Model\Quote\Address;
10+
11+
class CustomAttributeListPlugin
12+
{
13+
/**
14+
* @var \Magento\Customer\Api\AddressMetadataInterface
15+
*/
16+
private $addressMetadata;
17+
18+
public function __construct(\Magento\Customer\Api\AddressMetadataInterface $addressMetadata)
19+
{
20+
$this->addressMetadata = $addressMetadata;
21+
}
22+
23+
/**
24+
* @param \Magento\Quote\Model\Quote\Address\CustomAttributeListInterface $subject
25+
* @param $result
26+
* @return array
27+
* @throws \Magento\Framework\Exception\LocalizedException
28+
* @SuppressWarnings("unused")
29+
*/
30+
public function afterGetAttributes(\Magento\Quote\Model\Quote\Address\CustomAttributeListInterface $subject, $result) //@codingStandardsIgnoreLine
31+
{
32+
$customAttributes = [];
33+
$customAttributesMetadata = $this->addressMetadata->getCustomAttributesMetadata(\Magento\Quote\Api\Data\AddressInterface::class);
34+
foreach ($customAttributesMetadata as $attributeMetadata) {
35+
$attributeCode = $attributeMetadata->getAttributeCode();
36+
$customAttributes[$attributeCode] = true;
37+
}
38+
39+
return array_merge($result, $customAttributes);
40+
}
41+
}
Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
<?php
2+
namespace ${Vendorname}\${Modulename}\Plugin\Model;
3+
4+
use Magento\Quote\Model\Quote\Address as QuoteAddress;
5+
use Magento\Quote\Model\Quote\Address\ToOrderAddress;
6+
use Magento\Sales\Model\Order\Address as OrderAddress;
7+
8+
class QuoteAddressToOrderAddressPlugin
9+
{
10+
/**
11+
* @var \Magento\Customer\Api\AddressMetadataInterface
12+
*/
13+
private $addressMetadata;
14+
15+
public function __construct(\Magento\Customer\Api\AddressMetadataInterface $addressMetadata)
16+
{
17+
$this->addressMetadata = $addressMetadata;
18+
}
19+
20+
/**
21+
* @param ToOrderAddress $toOrderAddress
22+
* @param \Closure $proceed
23+
* @param QuoteAddress $quoteAddress
24+
* @param array $data
25+
* @return OrderAddress
26+
* @throws \Magento\Framework\Exception\LocalizedException
27+
* @SuppressWarnings("unused")
28+
*/
29+
public function aroundConvert(ToOrderAddress $toOrderAddress, \Closure $proceed, QuoteAddress $quoteAddress, $data = []) //@codingStandardsIgnoreLine
30+
{
31+
/** @var OrderAddress $orderAddress */
32+
$orderAddress = $proceed($quoteAddress, $data);
33+
34+
$customAttributesMetadata = $this->addressMetadata->getCustomAttributesMetadata(get_class($quoteAddress));
35+
foreach ($customAttributesMetadata as $attributeMetadata) {
36+
$attributeCode = $attributeMetadata->getAttributeCode();
37+
$value = $quoteAddress->getData($attributeCode);
38+
if (null !== $value) {
39+
$orderAddress->setData($attributeCode, $value);
40+
}
41+
}
42+
return $orderAddress;
43+
}
44+
}
Lines changed: 208 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,208 @@
1+
<?php
2+
namespace ${Vendorname}\${Modulename}\Setup;
3+
4+
use Magento\Customer\Setup\CustomerSetup;
5+
use Magento\Customer\Setup\CustomerSetupFactory;
6+
use Magento\Framework\Setup\InstallDataInterface;
7+
use Magento\Framework\Setup\ModuleContextInterface;
8+
use Magento\Framework\Setup\ModuleDataSetupInterface;
9+
use Magento\Quote\Setup\QuoteSetup;
10+
use Magento\Quote\Setup\QuoteSetupFactory;
11+
use Magento\Sales\Setup\SalesSetup;
12+
use Magento\Sales\Setup\SalesSetupFactory;
13+
use Magento\Config\Model\ResourceModel\Config;
14+
15+
/**
16+
* Upgrade Data script
17+
*
18+
* @codeCoverageIgnore
19+
*/
20+
class InstallData implements InstallDataInterface
21+
{
22+
/**
23+
* @var CustomerSetupFactory
24+
*/
25+
protected $customerSetupFactory;
26+
/**
27+
* @var QuoteSetupFactory
28+
*/
29+
private $quoteSetupFactory;
30+
/**
31+
* @var SalesSetupFactory
32+
*/
33+
private $salesSetupFactory;
34+
/**
35+
* @var Config
36+
*/
37+
private $config;
38+
39+
public function __construct(
40+
CustomerSetupFactory $customerSetupFactory,
41+
QuoteSetupFactory $quoteSetupFactory,
42+
SalesSetupFactory $salesSetupFactory,
43+
Config $config
44+
) {
45+
$this->customerSetupFactory = $customerSetupFactory;
46+
$this->quoteSetupFactory = $quoteSetupFactory;
47+
$this->salesSetupFactory = $salesSetupFactory;
48+
$this->config = $config;
49+
}
50+
51+
/**
52+
* {@inheritdoc}
53+
* @codingStandardsIgnoreStart
54+
*/
55+
public function install(ModuleDataSetupInterface $setup, ModuleContextInterface $context) //@codingStandardsIgnoreLine
56+
{
57+
$setup->startSetup();
58+
59+
$this->addCustomerAddressAttribute($setup, '${fieldname}', '${fieldname}', 120, true, false);
60+
$this->createQuoteAndSalesAttributes($setup, '${fieldname}');
61+
$this->addAttributeInAddressTemplates();
62+
63+
$setup->endSetup();
64+
}
65+
66+
/**
67+
* @param ModuleDataSetupInterface $setup
68+
* @param string $attributeCode
69+
* @param string $label
70+
* @param int $sortOrder
71+
* @param bool $showOnFrontend
72+
* @param bool $required
73+
* @param string $type
74+
* @param string $input
75+
* @param string|null $sourceModel
76+
* @throws \Magento\Framework\Exception\LocalizedException
77+
*/
78+
private function addCustomerAddressAttribute(
79+
ModuleDataSetupInterface $setup,
80+
string $attributeCode,
81+
string $label,
82+
int $sortOrder,
83+
bool $showOnFrontend = false,
84+
bool $required = false,
85+
string $type = 'varchar',
86+
string $input = 'text',
87+
$sourceModel = null
88+
) {
89+
/** @var CustomerSetup $customerSetup */
90+
$customerSetup = $this->customerSetupFactory->create(['setup' => $setup]);
91+
92+
$customerSetup->addAttribute(
93+
'customer_address',
94+
$attributeCode,
95+
[
96+
'type' => $type,
97+
'label' => $label,
98+
'input' => $input,
99+
'required' => $required,
100+
'sort_order' => 0,
101+
'visible' => true,
102+
'user_defined' => 0,
103+
'system' => false,
104+
'is_used_in_grid' => false,
105+
'source' => $sourceModel,
106+
]
107+
);
108+
109+
$attribute = $customerSetup->getEavConfig()->getAttribute('customer_address', $attributeCode);
110+
$forms = ['adminhtml_customer'];
111+
if ($showOnFrontend) {
112+
$forms = ['adminhtml_customer_address', 'customer_register_address', 'customer_address_edit'];
113+
}
114+
$attribute->setData('used_in_forms', $forms);
115+
$attribute->save(); //@codingStandardsIgnoreLine
116+
$customerSetup->updateAttribute('customer_address', $attributeCode, 'sort_order', $sortOrder);
117+
}
118+
119+
private function createQuoteAndSalesAttributes(
120+
ModuleDataSetupInterface $setup,
121+
string $attributeCode,
122+
string $type = 'varchar',
123+
string $length = '255'
124+
) {
125+
/** @var QuoteSetup $quoteSetup */
126+
$quoteSetup = $this->quoteSetupFactory->create(['setup' => $setup]);
127+
/** @var SalesSetup $salesSetup */
128+
$salesSetup = $this->salesSetupFactory->create(['setup' => $setup]);
129+
130+
$quoteSetup->addAttribute('quote_address', $attributeCode, ['type' => $type, 'length' => $length]);
131+
$salesSetup->addAttribute('order_address', $attributeCode, ['type' => $type, 'length' => $length]);
132+
133+
}
134+
135+
private function addAttributeInAddressTemplates()
136+
{
137+
$this->config->saveConfig(
138+
'customer/address_templates/text',
139+
<<<'TEMPLATE'
140+
{{depend salutation}}{{var salutation}} {{/depend}}{{var firstname}} {{var lastname}}
141+
{{depend company}}{{var company}}{{/depend}}
142+
{{depend company_addition}}{{var company_addition}}{{/depend}}
143+
{{if street1}}{{var street1}}
144+
{{/if}}
145+
{{depend street2}}{{var street2}}{{/depend}}
146+
{{depend street3}}{{var street3}}{{/depend}}
147+
{{depend street4}}{{var street4}}{{/depend}}
148+
{{if postcode}}{{var postcode}} {{/if}}{{if city}}{{var city}}{{/if}}{{if region}}, {{var region}}{{/if}}
149+
{{var country}}
150+
Tel: {{var telephone_prefix}} {{var telephone}}
151+
{{depend ${fieldname}}}{{var ${fieldname}}}{{/depend}}
152+
TEMPLATE
153+
,
154+
'default',
155+
0
156+
);
157+
$this->config->saveConfig(
158+
'customer/address_templates/html',
159+
<<<'TEMPLATE'
160+
{{depend salutation}}{{var salutation}} {{/depend}}{{var firstname}} {{var lastname}}<br/>
161+
{{depend company}}{{var company}}<br />{{/depend}}
162+
{{depend company_addition}}{{var company_addition}}<br />{{/depend}}
163+
{{if street1}}{{var street1}}<br />{{/if}}
164+
{{depend street2}}{{var street2}}<br />{{/depend}}
165+
{{depend street3}}{{var street3}}<br />{{/depend}}
166+
{{depend street4}}{{var street4}}<br />{{/depend}}
167+
{{if postcode}}{{var postcode}} {{/if}}{{if city}}{{var city}}{{/if}}{{if region}}, {{var region}}{{/if}}<br/>
168+
{{var country}}<br/>
169+
Tel: {{var telephone_prefix}} {{var telephone}}
170+
{{depend ${fieldname}}}<br/>{{var ${fieldname}}}{{/depend}}
171+
TEMPLATE
172+
,
173+
'default',
174+
0
175+
);
176+
//@codingStandardsIgnoreStart
177+
$this->config->saveConfig(
178+
'customer/address_templates/oneline',
179+
<<<'TEMPLATE'
180+
{{depend salutation}}{{var salutation}} {{/depend}}{{var firstname}} {{var lastname}}{{depend company}}, {{var company}}<br />{{/depend}}{{depend company_addition}}, {{var company_addition}}{{/depend}}{{if street1}}, {{var street1}}{{/if}}{{depend street2}}, {{var street2}}{{/depend}}{{depend street3}}, {{var street3}}{{/depend}}{{depend street4}}, {{var street4}}{{/depend}}, {{if postcode}}{{var postcode}} {{/if}}{{if city}}{{var city}}{{/if}}{{if region}}, {{var region}}{{/if}}, {{var country}}
181+
TEMPLATE
182+
,
183+
'default',
184+
0
185+
);
186+
//@codingStandardsIgnoreEnd
187+
$this->config->saveConfig(
188+
'customer/address_templates/pdf',
189+
<<<'TEMPLATE'
190+
{{depend salutation}}{{var salutation}} {{/depend}}{{var firstname}} {{var lastname}}|
191+
{{depend company}}{{var company}}|{{/depend}}
192+
{{depend company_addition}}{{var company_addition}}|{{/depend}}
193+
{{if street1}}{{var street1}}|{{/if}}
194+
{{depend street2}}{{var street2}}|{{/depend}}
195+
{{depend street3}}{{var street3}}|{{/depend}}
196+
{{depend street4}}{{var street4}}|{{/depend}}
197+
{{if postcode}}{{var postcode}} {{/if}}{{if city}}{{var city}}{{/if}}{{if region}}, {{var region}}{{/if}}|
198+
{{var country}}|
199+
Tel: {{var telephone_prefix}} {{var telephone}}
200+
{{depend ${fieldname}}}{{var ${fieldname}}}{{/depend}}
201+
TEMPLATE
202+
,
203+
'default',
204+
0
205+
);
206+
}
207+
208+
}

0 commit comments

Comments
 (0)