This commit is contained in:
team 1
2026-05-05 14:15:49 +02:00
parent d3fab6e84a
commit 913616a3df
3 changed files with 75 additions and 160 deletions

View File

@@ -31,6 +31,7 @@ final class ShopSearchService
private readonly ShopwareCriteriaBuilder $criteriaBuilder,
private readonly StoreApiClient $storeApiClient,
private readonly ShopServiceConfig $shopConfig,
private readonly ProductRoleResolver $productRoleResolver,
private readonly LoggerInterface $logger,
private readonly bool $enabled = true,
private readonly int $maxResults = 25,
@@ -1330,80 +1331,24 @@ final class ShopSearchService
private function isAccessoryLikeProduct(ShopProductResult $product): bool
{
$primaryRole = $this->resolvePrimaryShopProductRole($product);
if ($primaryRole === 'accessory_or_consumable') {
return true;
}
if ($primaryRole === 'main_device') {
return false;
}
return $this->containsAnyShopKeyword(
$this->buildNormalizedProductCorpus($product),
$this->shopConfig->getAccessoryProductKeywords()
return $this->productRoleResolver->isAccessoryLikeProduct(
product: $product,
accessoryKeywords: $this->shopConfig->getAccessoryProductKeywords(),
deviceKeywords: $this->shopConfig->getDeviceProductKeywords(),
normalize: fn(string $value): string => $this->normalizeForMatching($value)
);
}
private function isDeviceLikeProduct(ShopProductResult $product): bool
{
$primaryRole = $this->resolvePrimaryShopProductRole($product);
if ($primaryRole === 'main_device') {
return true;
}
if ($primaryRole === 'accessory_or_consumable') {
return false;
}
return $this->containsAnyShopKeyword(
$this->buildNormalizedProductCorpus($product),
$this->shopConfig->getDeviceProductKeywords()
return $this->productRoleResolver->isDeviceLikeProduct(
product: $product,
accessoryKeywords: $this->shopConfig->getAccessoryProductKeywords(),
deviceKeywords: $this->shopConfig->getDeviceProductKeywords(),
normalize: fn(string $value): string => $this->normalizeForMatching($value)
);
}
private function resolvePrimaryShopProductRole(ShopProductResult $product): string
{
$primaryText = $this->buildNormalizedPrimaryProductIdentity($product);
if ($primaryText === '') {
return 'unknown';
}
$isAccessoryLike = $this->containsAnyShopKeyword(
$primaryText,
$this->shopConfig->getAccessoryProductKeywords()
);
$isDeviceLike = $this->containsAnyShopKeyword(
$primaryText,
$this->shopConfig->getDeviceProductKeywords()
);
if ($isAccessoryLike && !$isDeviceLike) {
return 'accessory_or_consumable';
}
if ($isDeviceLike && !$isAccessoryLike) {
return 'main_device';
}
if ($isAccessoryLike && $isDeviceLike) {
return 'ambiguous_mixed_role';
}
return 'unknown';
}
private function buildNormalizedPrimaryProductIdentity(ShopProductResult $product): string
{
return $this->normalizeForMatching(implode(' ', array_filter([
$product->name,
$product->url,
])));
}
/**
* @param string[] $keywords
*/