diff --git a/src/Controller/InfoProviderController.php b/src/Controller/InfoProviderController.php index 1236dba3..4c27dffe 100644 --- a/src/Controller/InfoProviderController.php +++ b/src/Controller/InfoProviderController.php @@ -29,7 +29,6 @@ use App\Form\InfoProviderSystem\PartSearchType; use App\Services\InfoProviderSystem\PartInfoRetriever; use App\Services\InfoProviderSystem\ProviderRegistry; use Doctrine\ORM\EntityManagerInterface; -use Doctrine\ORM\QueryBuilder; use Psr\Log\LoggerInterface; use Symfony\Bridge\Doctrine\Attribute\MapEntity; use Symfony\Bundle\FrameworkBundle\Controller\AbstractController; @@ -62,12 +61,26 @@ class InfoProviderController extends AbstractController ]); } + /** + * Looks for parts in the local database that match the results from the info provider, so the user doesn't + * accidentally add a duplicate + * + * @param array $partsList Array of Arrays. Outer Array contains one entry per search result from the info Provider + * Inner array contains one entry "dto" for the dto from the info provider + * and one entry "localPart" where the local Part will be put if it exists + * Form: [["dto" => dto from provider, "localPart" => null]["dto" => dto from provider, "localPart" => null]] + * This function might modify the original array, not sure + * @return array Same format as the input array, but for parts that exist locally null will be replaced by a Part + */ private function matchResultsToKnownParts(array $partsList): array { + //we need a manufacturer object to look for a manufacturer $manufacturerQb = $this->em->getRepository(Manufacturer::class)->createQueryBuilder("manufacturer"); $manufacturerQb->where($manufacturerQb->expr()->like("LOWER(manufacturer.name)", "LOWER(:manufacturer_name)")); + //check if both manufacturer and Manufacturer part namber matches. If so, it must be the same part + //use LOWER to make the search independent of case $mpnQb = $this->em->getRepository(Part::class)->createQueryBuilder("part"); $mpnQb->where($mpnQb->expr()->like("LOWER(part.manufacturer_product_number)", "LOWER(:mpn)")); $mpnQb->andWhere($mpnQb->expr()->eq("part.manufacturer", ":manufacturer")); @@ -85,6 +98,7 @@ class InfoProviderController extends AbstractController if(!$localParts) { continue; } + //We only use the first matching part. If a user already has duplicate parts they will get a random one $partsList[$index]["localPart"] = $localParts[0]; } return $partsList; @@ -119,6 +133,9 @@ class InfoProviderController extends AbstractController //Log the exception $exceptionLogger->error('Error during info provider search: ' . $e->getMessage(), ['exception' => $e]); } + // modify the array to an array of arrays that has a field for a matching local Part + // the advantage to use that format even when we don't look for local parts is that we + // always work with the same interface $results = array_map(function ($result) {return ["dto" => $result,"localPart" => null];}, $results); if(!$update_target) { $results = $this->matchResultsToKnownParts($results);