Skip to content

Commit 026fd48

Browse files
committed
ACP2E-464: Remove wildcard and LIKE operator and replace with equal operator in customer grid filter search
1 parent be4c4e0 commit 026fd48

File tree

12 files changed

+246
-22
lines changed

12 files changed

+246
-22
lines changed
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
<?php
2+
/**
3+
* Copyright © Magento, Inc. All rights reserved.
4+
* See COPYING.txt for license details.
5+
*/
6+
declare(strict_types=1);
7+
8+
namespace Magento\Customer\Model\Config\Source;
9+
10+
use Magento\Framework\Data\OptionSourceInterface;
11+
12+
class FilterConditionType implements OptionSourceInterface
13+
{
14+
public const PARTIAL_MATCH = 0;
15+
16+
public const FULL_MATCH = 1;
17+
18+
/**
19+
* @inheritdoc
20+
*/
21+
public function toOptionArray()
22+
{
23+
return [
24+
['value' => self::PARTIAL_MATCH, 'label' => __('Partial Match')],
25+
['value' => self::FULL_MATCH, 'label' => __('Full Match')]
26+
];
27+
}
28+
}

app/code/Magento/Customer/Test/Unit/Ui/Component/Listing/AttributeRepositoryTest.php

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,8 +13,10 @@
1313
use Magento\Customer\Api\CustomerMetadataManagementInterface;
1414
use Magento\Customer\Api\Data\AttributeMetadataInterface;
1515
use Magento\Customer\Api\Data\OptionInterface;
16+
use Magento\Customer\Model\AttributeMetadataDataProvider;
1617
use Magento\Customer\Model\Indexer\Attribute\Filter;
1718
use Magento\Customer\Ui\Component\Listing\AttributeRepository;
19+
use Magento\Eav\Model\Entity\Attribute\AbstractAttribute;
1820
use PHPUnit\Framework\MockObject\MockObject;
1921
use PHPUnit\Framework\TestCase;
2022

@@ -47,6 +49,16 @@ class AttributeRepositoryTest extends TestCase
4749
/** @var AttributeRepository */
4850
protected $component;
4951

52+
/**
53+
* @var AttributeMetadataDataProvider|MockObject
54+
*/
55+
private $attributeMetadataDataProvider;
56+
57+
/**
58+
* @var AbstractAttribute|MockObject
59+
*/
60+
private $attributeModel;
61+
5062
protected function setUp(): void
5163
{
5264
$this->customerMetadataManagement = $this->getMockForAbstractClass(
@@ -83,12 +95,21 @@ protected function setUp(): void
8395

8496
$this->attributeFilter = $this->createMock(Filter::class);
8597

98+
$this->attributeMetadataDataProvider = $this->createMock(
99+
AttributeMetadataDataProvider::class
100+
);
101+
102+
$this->attributeModel = $this->getMockBuilder(AbstractAttribute::class)
103+
->disableOriginalConstructor()
104+
->getMockForAbstractClass();
105+
86106
$this->component = new AttributeRepository(
87107
$this->customerMetadataManagement,
88108
$this->addressMetadataManagement,
89109
$this->customerMetadata,
90110
$this->addressMetadata,
91-
$this->attributeFilter
111+
$this->attributeFilter,
112+
$this->attributeMetadataDataProvider
92113
);
93114
}
94115

@@ -148,6 +169,10 @@ public function testGetList()
148169
->method('filter')
149170
->willReturnArgument(0);
150171

172+
$this->attributeModel->addData(['grid_filter_condition_type' => 1]);
173+
$this->attributeMetadataDataProvider->method('getAttribute')
174+
->willReturn($this->attributeModel);
175+
151176
$this->assertEquals(
152177
[
153178
$billingPrefix . $attributeCode => [
@@ -169,6 +194,7 @@ public function testGetList()
169194
'validation_rules' => [],
170195
'required'=> false,
171196
'entity_type_code' => 'customer_address',
197+
'grid_filter_condition_type' => 1
172198
]
173199
],
174200
$this->component->getList()

app/code/Magento/Customer/Test/Unit/Ui/Component/Listing/ColumnsTest.php

Lines changed: 24 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
use Magento\Customer\Ui\Component\Listing\AttributeRepository;
1313
use Magento\Customer\Ui\Component\Listing\Column\InlineEditUpdater;
1414
use Magento\Customer\Ui\Component\Listing\Columns;
15+
use Magento\Customer\Ui\Component\Listing\Filter\FilterConfigProviderInterface;
1516
use Magento\Framework\View\Element\UiComponent\ContextInterface;
1617
use Magento\Framework\View\Element\UiComponent\Processor;
1718
use Magento\Ui\Component\Listing\Columns\ColumnInterface;
@@ -55,6 +56,11 @@ class ColumnsTest extends TestCase
5556
*/
5657
protected $component;
5758

59+
/**
60+
* @var FilterConfigProviderInterface|MockObject
61+
*/
62+
private $textFilterConfigProvider;
63+
5864
/**
5965
* @inheritdoc
6066
*/
@@ -86,11 +92,24 @@ protected function setUp(): void
8692
)->disableOriginalConstructor()
8793
->getMock();
8894

95+
$this->textFilterConfigProvider = $this->getMockForAbstractClass(FilterConfigProviderInterface::class);
96+
$this->textFilterConfigProvider->method('getConfig')
97+
->willReturn(
98+
[
99+
'conditionType' => 'like'
100+
]
101+
);
102+
89103
$this->component = new Columns(
90104
$this->context,
91105
$this->columnFactory,
92106
$this->attributeRepository,
93-
$this->inlineEditUpdater
107+
$this->inlineEditUpdater,
108+
[],
109+
[],
110+
[
111+
'text' => $this->textFilterConfigProvider
112+
]
94113
);
95114
}
96115

@@ -193,7 +212,10 @@ public function testPrepareWithUpdateColumn(): void
193212
[
194213
'name' => $attributeCode,
195214
'dataType' => $backendType,
196-
'filter' => 'text',
215+
'filter' => [
216+
'filterType' => 'text',
217+
'conditionType' => 'like',
218+
],
197219
'visible' => true
198220
]
199221
]

app/code/Magento/Customer/Ui/Component/Listing/AttributeRepository.php

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,14 +11,16 @@
1111
use Magento\Customer\Api\CustomerMetadataManagementInterface;
1212
use Magento\Customer\Api\Data\AttributeMetadataInterface;
1313
use Magento\Customer\Api\MetadataManagementInterface;
14+
use Magento\Customer\Model\AttributeMetadataDataProvider;
1415
use Magento\Customer\Model\Indexer\Attribute\Filter;
16+
use Magento\Framework\App\ObjectManager;
1517

1618
/**
1719
* Attribute Repository Managment
1820
*/
1921
class AttributeRepository
2022
{
21-
const BILLING_ADDRESS_PREFIX = 'billing_';
23+
public const BILLING_ADDRESS_PREFIX = 'billing_';
2224

2325
/**
2426
* @var array
@@ -50,25 +52,34 @@ class AttributeRepository
5052
*/
5153
protected $attributeFilter;
5254

55+
/**
56+
* @var AttributeMetadataDataProvider
57+
*/
58+
private $attributeMetadataDataProvider;
59+
5360
/**
5461
* @param CustomerMetadataManagementInterface $customerMetadataManagement
5562
* @param AddressMetadataManagementInterface $addressMetadataManagement
5663
* @param CustomerMetadataInterface $customerMetadata
5764
* @param AddressMetadataInterface $addressMetadata
5865
* @param Filter $attributeFiltering
66+
* @param AttributeMetadataDataProvider|null $attributeMetadataDataProvider
5967
*/
6068
public function __construct(
6169
CustomerMetadataManagementInterface $customerMetadataManagement,
6270
AddressMetadataManagementInterface $addressMetadataManagement,
6371
CustomerMetadataInterface $customerMetadata,
6472
AddressMetadataInterface $addressMetadata,
65-
Filter $attributeFiltering
73+
Filter $attributeFiltering,
74+
?AttributeMetadataDataProvider $attributeMetadataDataProvider = null
6675
) {
6776
$this->customerMetadataManagement = $customerMetadataManagement;
6877
$this->addressMetadataManagement = $addressMetadataManagement;
6978
$this->customerMetadata = $customerMetadata;
7079
$this->addressMetadata = $addressMetadata;
7180
$this->attributeFilter = $attributeFiltering;
81+
$this->attributeMetadataDataProvider = $attributeMetadataDataProvider
82+
?? ObjectManager::getInstance()->get(AttributeMetadataDataProvider::class);
7283
}
7384

7485
/**
@@ -111,6 +122,7 @@ protected function getListForEntity(array $metadata, $entityTypeCode, MetadataMa
111122
/** @var AttributeMetadataInterface $attribute */
112123
foreach ($metadata as $attribute) {
113124
$attributeCode = $attribute->getAttributeCode();
125+
$attributeModel = $this->attributeMetadataDataProvider->getAttribute($entityTypeCode, $attributeCode);
114126
if ($entityTypeCode == AddressMetadataInterface::ENTITY_TYPE_ADDRESS) {
115127
$attributeCode = self::BILLING_ADDRESS_PREFIX . $attribute->getAttributeCode();
116128
}
@@ -127,6 +139,7 @@ protected function getListForEntity(array $metadata, $entityTypeCode, MetadataMa
127139
AttributeMetadataInterface::VALIDATION_RULES => $attribute->getValidationRules(),
128140
AttributeMetadataInterface::REQUIRED => $attribute->isRequired(),
129141
'entity_type_code' => $entityTypeCode,
142+
'grid_filter_condition_type' => $attributeModel->getGridFilterConditionType()
130143
];
131144
}
132145

app/code/Magento/Customer/Ui/Component/Listing/Columns.php

Lines changed: 68 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
*/
66
namespace Magento\Customer\Ui\Component\Listing;
77

8+
use Magento\Customer\Ui\Component\Listing\Filter\FilterConfigProviderInterface;
89
use Magento\Framework\View\Element\UiComponent\ContextInterface;
910
use Magento\Customer\Ui\Component\ColumnFactory;
1011
use Magento\Customer\Api\Data\AttributeMetadataInterface as AttributeMetadata;
@@ -48,26 +49,35 @@ class Columns extends \Magento\Ui\Component\Listing\Columns
4849
'date' => 'dateRange',
4950
];
5051

52+
/**
53+
* @var FilterConfigProviderInterface[]
54+
*/
55+
private $filterConfigProviders;
56+
5157
/**
5258
* @param ContextInterface $context
5359
* @param ColumnFactory $columnFactory
5460
* @param AttributeRepository $attributeRepository
5561
* @param InlineEditUpdater $inlineEditor
5662
* @param array $components
5763
* @param array $data
64+
* @param FilterConfigProviderInterface[] $filterConfigProviders
5865
*/
5966
public function __construct(
6067
ContextInterface $context,
6168
ColumnFactory $columnFactory,
6269
AttributeRepository $attributeRepository,
6370
InlineEditUpdater $inlineEditor,
6471
array $components = [],
65-
array $data = []
72+
array $data = [],
73+
array $filterConfigProviders = []
6674
) {
6775
parent::__construct($context, $components, $data);
6876
$this->columnFactory = $columnFactory;
6977
$this->attributeRepository = $attributeRepository;
7078
$this->inlineEditUpdater = $inlineEditor;
79+
$this->filterConfigProviders = $filterConfigProviders;
80+
$this->updateComponentsFilters($components);
7181
}
7282

7383
/**
@@ -133,7 +143,10 @@ public function addColumn(array $attributeData, $columnName)
133143
{
134144
$config['sortOrder'] = ++$this->columnSortOrder;
135145
if ($attributeData[AttributeMetadata::IS_FILTERABLE_IN_GRID]) {
136-
$config['filter'] = $this->getFilterType($attributeData[AttributeMetadata::FRONTEND_INPUT]);
146+
$config['filter'] = $this->getFilterConfig(
147+
$attributeData,
148+
$this->getFilterType($attributeData[AttributeMetadata::FRONTEND_INPUT])
149+
);
137150
}
138151
$column = $this->columnFactory->create($attributeData, $columnName, $this->getContext(), $config);
139152
$column->prepare();
@@ -163,7 +176,10 @@ public function updateColumn(array $attributeData, $newAttributeCode)
163176
]
164177
);
165178
if ($attributeData[AttributeMetadata::IS_FILTERABLE_IN_GRID]) {
166-
$config['filter'] = $this->getFilterType($attributeData[AttributeMetadata::FRONTEND_INPUT]);
179+
$config['filter'] = $this->getFilterConfig(
180+
$attributeData,
181+
$this->getFilterType($attributeData[AttributeMetadata::FRONTEND_INPUT])
182+
);
167183
}
168184
$component->setData('config', $config);
169185
}
@@ -216,4 +232,53 @@ protected function getFilterType($frontendInput)
216232
{
217233
return $this->filterMap[$frontendInput] ?? $this->filterMap['default'];
218234
}
235+
236+
/**
237+
* Update components filters configurations
238+
*
239+
* @param UiComponentInterface[] $components
240+
* @return void
241+
*/
242+
private function updateComponentsFilters(array $components): void
243+
{
244+
$attributes = $this->attributeRepository->getList();
245+
foreach ($components as $name => $component) {
246+
if (isset($attributes[$name])) {
247+
$config = $component->getData('config');
248+
if (isset($config['filter'])) {
249+
$filterConfig = !is_array($config['filter'])
250+
? ['filterType' => $config['filter']]
251+
: $config['filter'];
252+
253+
if (is_string($filterConfig['filterType'])) {
254+
$filterConfig += $this->getFilterConfig(
255+
$attributes[$name],
256+
$filterConfig['filterType']
257+
);
258+
$config['filter'] = $filterConfig;
259+
}
260+
}
261+
$component->setData('config', $config);
262+
}
263+
}
264+
}
265+
266+
/**
267+
* Returns the filter config
268+
*
269+
* @param array $attributeData
270+
* @param string $filterType
271+
* @return array
272+
*/
273+
private function getFilterConfig(array $attributeData, string $filterType): array
274+
{
275+
$filterConfig = [
276+
'filterType' => $filterType
277+
];
278+
if (isset($this->filterConfigProviders[$filterType])) {
279+
$filterConfigProvider = $this->filterConfigProviders[$filterType];
280+
$filterConfig = array_merge($filterConfig, $filterConfigProvider->getConfig($attributeData));
281+
}
282+
return $filterConfig;
283+
}
219284
}
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
<?php
2+
/**
3+
* Copyright © Magento, Inc. All rights reserved.
4+
* See COPYING.txt for license details.
5+
*/
6+
declare(strict_types=1);
7+
8+
namespace Magento\Customer\Ui\Component\Listing\Filter;
9+
10+
interface FilterConfigProviderInterface
11+
{
12+
/**
13+
* Returns filter configuration for given attribute
14+
*
15+
* @param array $attributeData
16+
* @return array
17+
*/
18+
public function getConfig(array $attributeData): array;
19+
}

0 commit comments

Comments
 (0)