Skip to content

Commit d1ebc17

Browse files
authored
Merge pull request magento#3609 from magento-panda/MAGETWO-97411
Fixed issue: - MAGETWO-97411: \Magento\Customer\Model\Customer::getDataModel method takes to much time to load with many addresses customer
2 parents 2c31192 + fcbb2b9 commit d1ebc17

File tree

5 files changed

+120
-15
lines changed

5 files changed

+120
-15
lines changed

app/code/Magento/Customer/Model/Address.php

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -172,12 +172,9 @@ public function updateData(AddressInterface $address)
172172
public function getDataModel($defaultBillingAddressId = null, $defaultShippingAddressId = null)
173173
{
174174
if ($this->getCustomerId() || $this->getParentId()) {
175-
if ($this->getCustomer()->getDefaultBillingAddress()) {
176-
$defaultBillingAddressId = $this->getCustomer()->getDefaultBillingAddress()->getId();
177-
}
178-
if ($this->getCustomer()->getDefaultShippingAddress()) {
179-
$defaultShippingAddressId = $this->getCustomer()->getDefaultShippingAddress()->getId();
180-
}
175+
$customer = $this->getCustomer();
176+
$defaultBillingAddressId = $customer->getDefaultBilling() ?: $defaultBillingAddressId;
177+
$defaultShippingAddressId = $customer->getDefaultShipping() ?: $defaultShippingAddressId;
181178
}
182179
return parent::getDataModel($defaultBillingAddressId, $defaultShippingAddressId);
183180
}

app/code/Magento/Customer/Model/Customer.php

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -219,6 +219,13 @@ class Customer extends \Magento\Framework\Model\AbstractModel
219219
*/
220220
private $accountConfirmation;
221221

222+
/**
223+
* Caching property to store customer address data models by the address ID.
224+
*
225+
* @var array
226+
*/
227+
private $storedAddress;
228+
222229
/**
223230
* @param \Magento\Framework\Model\Context $context
224231
* @param \Magento\Framework\Registry $registry
@@ -314,7 +321,10 @@ public function getDataModel()
314321
$addressesData = [];
315322
/** @var \Magento\Customer\Model\Address $address */
316323
foreach ($this->getAddresses() as $address) {
317-
$addressesData[] = $address->getDataModel();
324+
if (!isset($this->storedAddress[$address->getId()])) {
325+
$this->storedAddress[$address->getId()] = $address->getDataModel();
326+
}
327+
$addressesData[] = $this->storedAddress[$address->getId()];
318328
}
319329
$customerDataObject = $this->customerDataFactory->create();
320330
$this->dataObjectHelper->populateWithArray(

app/code/Magento/Customer/Test/Unit/Model/CustomerTest.php

Lines changed: 81 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,12 @@
1313

1414
use Magento\Customer\Model\Customer;
1515
use Magento\Customer\Model\AccountConfirmation;
16+
use Magento\Customer\Model\ResourceModel\Address\CollectionFactory as AddressCollectionFactory;
17+
use Magento\Customer\Api\Data\CustomerInterfaceFactory;
1618

1719
/**
1820
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
21+
* @SuppressWarnings(PHPMD.TooManyFields)
1922
*/
2023
class CustomerTest extends \PHPUnit\Framework\TestCase
2124
{
@@ -68,6 +71,21 @@ class CustomerTest extends \PHPUnit\Framework\TestCase
6871
*/
6972
private $accountConfirmation;
7073

74+
/**
75+
* @var AddressCollectionFactory|\PHPUnit_Framework_MockObject_MockObject
76+
*/
77+
private $addressesFactory;
78+
79+
/**
80+
* @var CustomerInterfaceFactory|\PHPUnit_Framework_MockObject_MockObject
81+
*/
82+
private $customerDataFactory;
83+
84+
/**
85+
* @var \Magento\Framework\Api\DataObjectHelper|\PHPUnit_Framework_MockObject_MockObject
86+
*/
87+
private $dataObjectHelper;
88+
7189
protected function setUp()
7290
{
7391
$this->_website = $this->createMock(\Magento\Store\Model\Website::class);
@@ -100,6 +118,19 @@ protected function setUp()
100118
$this->_encryptor = $this->createMock(\Magento\Framework\Encryption\EncryptorInterface::class);
101119
$helper = new \Magento\Framework\TestFramework\Unit\Helper\ObjectManager($this);
102120
$this->accountConfirmation = $this->createMock(AccountConfirmation::class);
121+
$this->addressesFactory = $this->getMockBuilder(AddressCollectionFactory::class)
122+
->disableOriginalConstructor()
123+
->setMethods(['create'])
124+
->getMock();
125+
$this->customerDataFactory = $this->getMockBuilder(CustomerInterfaceFactory::class)
126+
->disableOriginalConstructor()
127+
->setMethods(['create'])
128+
->getMock();
129+
$this->dataObjectHelper = $this->getMockBuilder(\Magento\Framework\Api\DataObjectHelper::class)
130+
->disableOriginalConstructor()
131+
->setMethods(['populateWithArray'])
132+
->getMock();
133+
103134
$this->_model = $helper->getObject(
104135
\Magento\Customer\Model\Customer::class,
105136
[
@@ -112,7 +143,10 @@ protected function setUp()
112143
'registry' => $this->registryMock,
113144
'resource' => $this->resourceMock,
114145
'dataObjectProcessor' => $this->dataObjectProcessor,
115-
'accountConfirmation' => $this->accountConfirmation
146+
'accountConfirmation' => $this->accountConfirmation,
147+
'_addressesFactory' => $this->addressesFactory,
148+
'customerDataFactory' => $this->customerDataFactory,
149+
'dataObjectHelper' => $this->dataObjectHelper
116150
]
117151
);
118152
}
@@ -186,13 +220,13 @@ public function testSendNewAccountEmailWithoutStoreId()
186220
->will($this->returnValue($transportMock));
187221

188222
$this->_model->setData([
189-
'website_id' => 1,
190-
'store_id' => 1,
191-
'email' => '[email protected]',
192-
'firstname' => 'FirstName',
193-
'lastname' => 'LastName',
194-
'middlename' => 'MiddleName',
195-
'prefix' => 'Name Prefix',
223+
'website_id' => 1,
224+
'store_id' => 1,
225+
'email' => '[email protected]',
226+
'firstname' => 'FirstName',
227+
'lastname' => 'LastName',
228+
'middlename' => 'MiddleName',
229+
'prefix' => 'Name Prefix',
196230
]);
197231
$this->_model->sendNewAccountEmail('registered');
198232
}
@@ -310,4 +344,43 @@ public function testUpdateData()
310344

311345
$this->assertEquals($this->_model->getData(), $expectedResult);
312346
}
347+
348+
/**
349+
* Test for the \Magento\Customer\Model\Customer::getDataModel() method
350+
*/
351+
public function testGetDataModel()
352+
{
353+
$customerId = 1;
354+
$this->_model->setEntityId($customerId);
355+
$this->_model->setId($customerId);
356+
$addressDataModel = $this->getMockForAbstractClass(\Magento\Customer\Api\Data\AddressInterface::class);
357+
$address = $this->getMockBuilder(\Magento\Customer\Model\Address::class)
358+
->disableOriginalConstructor()
359+
->setMethods(['setCustomer', 'getDataModel'])
360+
->getMock();
361+
$address->expects($this->atLeastOnce())->method('getDataModel')->willReturn($addressDataModel);
362+
$addresses = new \ArrayIterator([$address, $address]);
363+
$addressCollection = $this->getMockBuilder(\Magento\Customer\Model\ResourceModel\Address\Collection::class)
364+
->disableOriginalConstructor()
365+
->setMethods(['setCustomerFilter', 'addAttributeToSelect', 'getIterator', 'getItems'])
366+
->getMock();
367+
$addressCollection->expects($this->atLeastOnce())->method('setCustomerFilter')->willReturnSelf();
368+
$addressCollection->expects($this->atLeastOnce())->method('addAttributeToSelect')->willReturnSelf();
369+
$addressCollection->expects($this->atLeastOnce())->method('getIterator')
370+
->willReturn($addresses);
371+
$addressCollection->expects($this->atLeastOnce())->method('getItems')
372+
->willReturn($addresses);
373+
$this->addressesFactory->expects($this->atLeastOnce())->method('create')->willReturn($addressCollection);
374+
$customerDataObject = $this->getMockForAbstractClass(\Magento\Customer\Api\Data\CustomerInterface::class);
375+
$this->customerDataFactory->expects($this->atLeastOnce())->method('create')->willReturn($customerDataObject);
376+
$this->dataObjectHelper->expects($this->atLeastOnce())->method('populateWithArray')
377+
->with($customerDataObject, $this->_model->getData(), \Magento\Customer\Api\Data\CustomerInterface::class)
378+
->willReturnSelf();
379+
$customerDataObject->expects($this->atLeastOnce())->method('setAddresses')
380+
->with([$addressDataModel, $addressDataModel])
381+
->willReturnSelf();
382+
$customerDataObject->expects($this->atLeastOnce())->method('setId')->with($customerId)->willReturnSelf();
383+
$this->_model->getDataModel();
384+
$this->assertEquals($customerDataObject, $this->_model->getDataModel());
385+
}
313386
}

dev/tests/integration/testsuite/Magento/Customer/Model/AddressTest.php

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -67,4 +67,28 @@ public function testUpdateDataOverrideExistingData()
6767
$this->assertEquals('CompanyZ', $updatedAddressData->getCompany());
6868
$this->assertEquals('99999', $updatedAddressData->getPostcode());
6969
}
70+
71+
/**
72+
* @magentoDataFixture Magento/Customer/_files/customer_sample.php
73+
*/
74+
public function testUpdateDataForExistingCustomer()
75+
{
76+
/** @var \Magento\Customer\Model\CustomerRegistry $customerRegistry */
77+
$customerRegistry = \Magento\TestFramework\Helper\Bootstrap::getObjectManager()->get(CustomerRegistry::class);
78+
/** @var \Magento\Customer\Model\Data\Address $addressData */
79+
$updatedAddressData = $this->addressFactory->create()
80+
->setId(1)
81+
->setCustomerId($customerRegistry->retrieveByEmail('[email protected]')->getId())
82+
->setCity('CityZ')
83+
->setCompany('CompanyZ')
84+
->setPostcode('99999');
85+
$updatedAddressData = $this->addressModel->updateData($updatedAddressData)->getDataModel();
86+
87+
$this->assertEquals(1, $updatedAddressData->getId());
88+
$this->assertEquals('CityZ', $updatedAddressData->getCity());
89+
$this->assertEquals('CompanyZ', $updatedAddressData->getCompany());
90+
$this->assertEquals('99999', $updatedAddressData->getPostcode());
91+
$this->assertEquals(true, $updatedAddressData->isDefaultBilling());
92+
$this->assertEquals(true, $updatedAddressData->isDefaultShipping());
93+
}
7094
}

dev/tests/integration/testsuite/Magento/Customer/_files/customer_sample.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
'lastname' => 'test lastname',
2020
'email' => '[email protected]',
2121
'default_billing' => 1,
22+
'default_shipping' => 1,
2223
'password' => '123123q',
2324
'attribute_set_id' => 1,
2425
];

0 commit comments

Comments
 (0)