Skip to content

Commit c1a48d3

Browse files
committed
ACP2E-3090: Handling Category Filters in GraphQL: includeDirectChildrenOnly and category_uid
1 parent fe2e144 commit c1a48d3

File tree

2 files changed

+80
-2
lines changed

2 files changed

+80
-2
lines changed

app/code/Magento/CatalogGraphQl/Model/Resolver/Products.php

Lines changed: 34 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@
1515
use Magento\Framework\GraphQl\Schema\Type\ResolveInfo;
1616
use Magento\Catalog\Model\Layer\Resolver;
1717
use Magento\CatalogGraphQl\DataProvider\Product\SearchCriteriaBuilder;
18+
use Magento\Framework\GraphQl\Query\Uid;
19+
use Magento\Framework\App\ObjectManager;
1820

1921
/**
2022
* Products field resolver, used for GraphQL request processing.
@@ -31,17 +33,23 @@ class Products implements ResolverInterface
3133
*/
3234
private $searchApiCriteriaBuilder;
3335

36+
/** @var Uid */
37+
private $uidEncoder;
38+
3439
/**
3540
* @param ProductQueryInterface $searchQuery
3641
* @param SearchCriteriaBuilder|null $searchApiCriteriaBuilder
42+
* @param Uid|null $uidEncoder
3743
*/
3844
public function __construct(
3945
ProductQueryInterface $searchQuery,
40-
SearchCriteriaBuilder $searchApiCriteriaBuilder = null
46+
SearchCriteriaBuilder $searchApiCriteriaBuilder = null,
47+
Uid $uidEncoder = null
4148
) {
4249
$this->searchQuery = $searchQuery;
4350
$this->searchApiCriteriaBuilder = $searchApiCriteriaBuilder ??
44-
\Magento\Framework\App\ObjectManager::getInstance()->get(SearchCriteriaBuilder::class);
51+
ObjectManager::getInstance()->get(SearchCriteriaBuilder::class);
52+
$this->uidEncoder = $uidEncoder ?: ObjectManager::getInstance()->get(Uid::class);
4553
}
4654

4755
/**
@@ -80,6 +88,10 @@ public function resolve(
8088
'layer_type' => isset($args['search']) ? Resolver::CATALOG_LAYER_SEARCH : Resolver::CATALOG_LAYER_CATEGORY,
8189
];
8290

91+
if (isset($args['filter']['category_uid'])) {
92+
$args['filter']['category_id'] = $this->getFilterCategoryIdFromCategoryUid($args['filter']['category_uid']);
93+
}
94+
8395
if (isset($args['filter']['category_id'])) {
8496
$data['categories'] = $args['filter']['category_id']['eq'] ?? $args['filter']['category_id']['in'];
8597
$data['categories'] = is_array($data['categories']) ? $data['categories'] : [$data['categories']];
@@ -88,6 +100,26 @@ public function resolve(
88100
return $data;
89101
}
90102

103+
/**
104+
* Get filter category_id by category_uid
105+
*
106+
* @param array $filterCategoryUid
107+
* @return array|null
108+
*/
109+
private function getFilterCategoryIdFromCategoryUid(array $filterCategoryUid): ?array
110+
{
111+
$filterCategoryId = null;
112+
if (isset($filterCategoryUid['eq'])) {
113+
$filterCategoryId['eq'] = $this->uidEncoder
114+
->decode((string)$filterCategoryUid['eq']);
115+
} elseif (!empty($filterCategoryUid['in'])) {
116+
foreach ($filterCategoryUid['in'] as $uid) {
117+
$filterCategoryId['in'][] = $this->uidEncoder->decode((string) $uid);
118+
}
119+
}
120+
return $filterCategoryId;
121+
}
122+
91123
/**
92124
* Validate input arguments
93125
*

dev/tests/api-functional/testsuite/Magento/GraphQl/Catalog/CategoriesQuery/CategoryAggregationsTest.php

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,10 @@
77

88
namespace Magento\GraphQl\Catalog\CategoriesQuery;
99

10+
use Magento\Catalog\Test\Fixture\Category as CategoryFixture;
11+
use Magento\Catalog\Test\Fixture\Product as ProductFixture;
12+
use Magento\TestFramework\Fixture\DataFixture;
13+
use Magento\TestFramework\Fixture\DataFixtureStorageManager;
1014
use Magento\TestFramework\TestCase\GraphQlAbstract;
1115

1216
/**
@@ -65,4 +69,46 @@ function ($a) {
6569
$this->assertEquals(2, $optionsAttribute1[1]['count']);
6670
$this->assertEquals(3, $optionsAttribute1[2]['count']);
6771
}
72+
73+
/**
74+
* Test to return category aggregations filtered by category_uid
75+
*/
76+
#[
77+
DataFixture(CategoryFixture::class, ['name' => 'Category 1', 'parent_id' => '2'], 'c1'),
78+
DataFixture(CategoryFixture::class, ['name' => 'Category 1-1', 'parent_id' => '$c1.id$'], 'c11'),
79+
DataFixture(CategoryFixture::class, ['name' => 'Category 1-1-1', 'parent_id' => '$c11.id$'], 'c111'),
80+
DataFixture(
81+
ProductFixture::class,
82+
[
83+
'sku' => 'product1',
84+
'category_ids' => ['$c111.id$']
85+
],
86+
),
87+
]
88+
public function testCategoryAggregationFilteredByCategoryUid(): void
89+
{
90+
$fixtures = DataFixtureStorageManager::getStorage();
91+
$categoryId = $fixtures->get('c1')->getId();
92+
$categoryUid = base64_encode((string) $categoryId);
93+
$query = <<<QUERY
94+
{
95+
products(filter: {category_uid: {eq: "{$categoryUid}"}}) {
96+
aggregations{
97+
label
98+
attribute_code
99+
count
100+
options{
101+
label
102+
value
103+
count
104+
}
105+
}
106+
}
107+
}
108+
QUERY;
109+
$response = $this->graphQlQuery($query);
110+
$this->assertArrayNotHasKey('errors', $response);
111+
$this->assertArrayHasKey('products', $response);
112+
$this->assertArrayHasKey('aggregations', $response['products']);
113+
}
68114
}

0 commit comments

Comments
 (0)