Skip to content

Commit f7bb102

Browse files
Merge branch 'release/2.29.0'
2 parents c931e1c + 4babba2 commit f7bb102

File tree

39 files changed

+249
-88
lines changed

39 files changed

+249
-88
lines changed

Api/Data/NodeInterface.php

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ interface NodeInterface
2626
const ADDITIONAL_DATA = 'additional_data';
2727
const SELECTED_ITEM_ID = 'selected_item_id';
2828
const CUSTOMER_GROUPS = 'customer_groups';
29+
const HIDE_IF_EMPTY = 'hide_if_empty';
2930

3031
/**
3132
* Get node id
@@ -316,4 +317,16 @@ public function setCustomerGroups($customerGroups);
316317
* @return bool
317318
*/
318319
public function isVisible($customerGroupId);
320+
321+
322+
/**
323+
* @return int
324+
*/
325+
public function getHideIfEmpty();
326+
327+
/**
328+
* @param int $hideIfEmpty
329+
* @return $this
330+
*/
331+
public function setHideIfEmpty($hideIfEmpty);
319332
}

Block/Adminhtml/Edit/Tab/Nodes.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -178,6 +178,7 @@ private function renderNodeList($level, $parent, $data)
178178
foreach ($nodes as $node) {
179179
$menu[] = [
180180
'is_active' => $node->getIsActive(),
181+
'hide_if_empty' => $node->getHideIfEmpty(),
181182
'is_stored' => true,
182183
'type' => $node->getType(),
183184
'content' => $node->getContent(),

Block/Menu.php

Lines changed: 47 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
class Menu extends Template implements DataObject\IdentityInterface
2525
{
2626
const XML_SNOWMENU_GENERAL_CUSTOMER_GROUPS = 'snowmenu/general/customer_groups';
27+
const XML_SNOWMENU_GENERAL_CACHE_TAGS = 'snowmenu/general/cache_tags';
2728

2829
/**
2930
* @var MenuRepositoryInterface
@@ -84,6 +85,11 @@ class Menu extends Template implements DataObject\IdentityInterface
8485
*/
8586
private $httpContext;
8687

88+
/**
89+
* @var array
90+
*/
91+
private $nodeTypeCaches = [];
92+
8793
/**
8894
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
8995
*/
@@ -97,6 +103,7 @@ public function __construct(
97103
ImageFile $imageFile,
98104
Escaper $escaper,
99105
Context $httpContext,
106+
array $nodeTypeCaches = [],
100107
array $data = []
101108
) {
102109
parent::__construct($context, $data);
@@ -110,6 +117,7 @@ public function __construct(
110117
$this->setTemplate($this->getMenuTemplate($this->_template));
111118
$this->submenuTemplate = $this->getSubmenuTemplate();
112119
$this->httpContext = $httpContext;
120+
$this->nodeTypeCaches = $nodeTypeCaches;
113121
}
114122

115123
/**
@@ -119,11 +127,22 @@ public function __construct(
119127
*/
120128
public function getIdentities()
121129
{
122-
return [
130+
$tags = [
123131
\Snowdog\Menu\Model\Menu::CACHE_TAG . '_' . $this->loadMenu()->getId(),
124132
Block::CACHE_TAG,
125133
\Snowdog\Menu\Model\Menu::CACHE_TAG
126134
];
135+
if (!$this->canGatherEntityCacheTags()) {
136+
return $tags;
137+
}
138+
$otherCacheTagsArrays = [];
139+
foreach ($this->nodeTypeCaches as $provider) {
140+
$entityCacheTags = $this->nodeTypeProvider->getProvider($provider)->getEntityCacheTags();
141+
if (!empty($entityCacheTags)) {
142+
$otherCacheTagsArrays[] = $entityCacheTags;
143+
}
144+
}
145+
return array_merge($tags, ...$otherCacheTagsArrays);
127146
}
128147

129148
protected function getCacheLifetime()
@@ -440,6 +459,9 @@ private function getSubmenuBlock($nodes, $parentNode, $level = 0)
440459
return $block;
441460
}
442461

462+
/**
463+
* @SuppressWarnings(PHPMD.NPathComplexity)
464+
*/
443465
private function fetchData()
444466
{
445467
$nodes = $this->nodeRepository->getByMenu($this->loadMenu()->getId());
@@ -464,16 +486,29 @@ private function fetchData()
464486
$result[$level][$parent] = [];
465487
}
466488
$result[$level][$parent][] = $node;
489+
$idx = array_key_last($result[$level][$parent]);
467490
$type = $node->getType();
468491
if (!isset($types[$type])) {
469492
$types[$type] = [];
470493
}
471-
$types[$type][] = $node;
494+
$types[$type][] = [
495+
'node' => $node,
496+
'path' => [$level, $parent, $idx]
497+
];
472498
}
473499
$this->nodes = $result;
474500

475501
foreach ($types as $type => $nodes) {
476-
$this->nodeTypeProvider->prepareData($type, $nodes);
502+
$this->nodeTypeProvider->prepareData($type, array_column($nodes, 'node'));
503+
}
504+
505+
foreach ($types['category'] ?? [] as $nodes) {
506+
$categoryProvider = $this->nodeTypeProvider->getProvider('category');
507+
$productCount = $categoryProvider->getCategoryProductCount($nodes['node']->getNodeId());
508+
if (empty($productCount) && $nodes['node']->getHideIfEmpty()) {
509+
[$level, $parent, $idx] = $nodes['path'];
510+
unset($this->nodes[$level][$parent][$idx]);
511+
}
477512
}
478513
}
479514

@@ -509,6 +544,15 @@ private function getSubmenuTemplate()
509544
return $this->getMenuTemplate($baseSubmenuTemplate);
510545
}
511546

547+
private function canGatherEntityCacheTags()
548+
{
549+
if (!$this->_scopeConfig->isSetFlag(self::XML_SNOWMENU_GENERAL_CACHE_TAGS)) {
550+
return false;
551+
}
552+
553+
return !empty($this->nodeTypeCaches);
554+
}
555+
512556
public function getCustomerGroupId()
513557
{
514558
return $this->httpContext->getValue(\Magento\Customer\Model\Context::CONTEXT_GROUP);

Block/NodeType/Category.php

Lines changed: 38 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,15 @@ class Category extends AbstractNode
4343
* @var array
4444
*/
4545
private $categories;
46+
/**
47+
* @var array
48+
*/
49+
private $cacheTags;
50+
51+
/**
52+
* @var array
53+
*/
54+
private $categoryProductCounts;
4655

4756
/**
4857
* Category constructor.
@@ -103,7 +112,14 @@ public function fetchData(array $nodes)
103112
{
104113
$storeId = $this->_storeManager->getStore()->getId();
105114

106-
list($this->nodes, $this->categoryUrls, $this->categories) = $this->_categoryModel->fetchData($nodes, $storeId);
115+
[
116+
$this->nodes,
117+
$this->categoryUrls,
118+
$this->categories,
119+
$this->categoryProductCounts,
120+
$this->cacheTags
121+
] = $this->_categoryModel->fetchData($nodes, $storeId);
122+
107123
}
108124

109125
/**
@@ -151,6 +167,22 @@ public function getCategoryUrl($nodeId, $storeId = null)
151167
return false;
152168
}
153169

170+
public function getCategoryProductCount($nodeId)
171+
{
172+
if (!isset($this->nodes[$nodeId])) {
173+
throw new \InvalidArgumentException('Invalid node identifier specified');
174+
}
175+
176+
$node = $this->nodes[$nodeId];
177+
$categoryId = (int) $node->getContent();
178+
179+
if (isset($this->categoryProductCounts[$categoryId])) {
180+
return $this->categoryProductCounts[$categoryId];
181+
}
182+
183+
return 0;
184+
}
185+
154186
/**
155187
* @param int $nodeId
156188
*
@@ -199,4 +231,9 @@ public function getLabel()
199231
{
200232
return __("Category");
201233
}
234+
235+
public function getEntityCacheTags()
236+
{
237+
return $this->cacheTags;
238+
}
202239
}

CHANGELOG.md

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,16 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.
66

77

88
## [Unreleased]
9+
### Added
10+
- Dynamic menu improvements ([#317](https://github.com/SnowdogApps/magento2-menu/discussions/317))
11+
### Changed
12+
- Long Node cache tag in graphql ([#364](https://github.com/SnowdogApps/magento2-menu/pull/364))
13+
### Removed
14+
- Frontend console log (SMM-46)
15+
- Unused variables from phtml files ([#357](https://github.com/SnowdogApps/magento2-menu/pull/357))
16+
### Fixed
17+
- PHP8.4 module compilation errors ([#365](https://github.com/SnowdogApps/magento2-menu/issues/365))
18+
- Database prefix errors ([#368](https://github.com/SnowdogApps/magento2-menu/pull/368))
919

1020
## [2.28.0] - 2025-03-25
1121
### Added

Console/Command/NodesValidatorCommand.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ public function __construct(
4444
ValidationAggregateError $validationAggregateError,
4545
State $state,
4646
TreeTrace $treeTrace,
47-
string $name = null
47+
?string $name = null
4848
) {
4949
$this->menuRepository = $menuRepository;
5050
$this->nodeRepository = $nodeRepository;

Model/GraphQl/Resolver/DataProvider/Node.php

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -113,7 +113,8 @@ private function convertData(NodeInterface $node): array
113113
NodeInterface::UPDATE_TIME => $node->getUpdateTime(),
114114
NodeInterface::ADDITIONAL_DATA => $node->getAdditionalData(),
115115
NodeInterface::SELECTED_ITEM_ID => $node->getSelectedItemId(),
116-
NodeInterface::CUSTOMER_GROUPS => $node->getCustomerGroups()
116+
NodeInterface::CUSTOMER_GROUPS => $node->getCustomerGroups(),
117+
NodeInterface::HIDE_IF_EMPTY => $node->getHideIfEmpty(),
117118
];
118119
}
119120

Model/GraphQl/Resolver/Menu.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,8 +33,8 @@ public function resolve(
3333
Field $field,
3434
$context,
3535
ResolveInfo $info,
36-
array $value = null,
37-
array $args = null
36+
?array $value = null,
37+
?array $args = null
3838
) {
3939
$storeId = (int) $context->getExtensionAttributes()->getStore()->getId();
4040
$identifiers = $this->getIdentifiers($args);

Model/GraphQl/Resolver/Menu/Field/Nodes.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,8 +27,8 @@ public function resolve(
2727
Field $field,
2828
$context,
2929
ResolveInfo $info,
30-
array $value = null,
31-
array $args = null
30+
?array $value = null,
31+
?array $args = null
3232
): array {
3333
if ($args === null) {
3434
$args = [];

Model/GraphQl/Resolver/Node.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,8 +33,8 @@ public function resolve(
3333
Field $field,
3434
$context,
3535
ResolveInfo $info,
36-
array $value = null,
37-
array $args = null
36+
?array $value = null,
37+
?array $args = null
3838
) {
3939
if (!isset($args['identifier'])) {
4040
throw new GraphQlInputException(__('Menu identifier must be specified.'));

0 commit comments

Comments
 (0)