From ba4b8d072fc2aee18fc895b431b1bdbb03777abf Mon Sep 17 00:00:00 2001 From: MayNiklas Date: Sun, 25 Jan 2026 23:09:15 +0100 Subject: [PATCH] feat: add supplier SPN lookup for BOM import Add automatic part linking via supplier part numbers (SPNs) in the BOM importer. When a Part-DB ID is not provided, the importer now searches for existing parts by matching supplier SPNs from the CSV with orderdetail records in the database. This allows automatic part linking when KiCad schematic BOMs contain supplier information like LCSC SPN, Mouser SPN, etc., improving the import workflow for users who track parts by supplier part numbers. --- .../ImportExportSystem/BOMImporter.php | 40 ++++++++++++++++++- 1 file changed, 39 insertions(+), 1 deletion(-) diff --git a/src/Services/ImportExportSystem/BOMImporter.php b/src/Services/ImportExportSystem/BOMImporter.php index 33a402cb..8a91c825 100644 --- a/src/Services/ImportExportSystem/BOMImporter.php +++ b/src/Services/ImportExportSystem/BOMImporter.php @@ -277,8 +277,11 @@ class BOMImporter // Fetch suppliers once for efficiency $suppliers = $this->entityManager->getRepository(\App\Entity\Parts\Supplier::class)->findAll(); $supplierSPNKeys = []; + $suppliersByName = []; // Map supplier names to supplier objects foreach ($suppliers as $supplier) { - $supplierSPNKeys[] = $supplier->getName() . ' SPN'; + $supplierName = $supplier->getName(); + $supplierSPNKeys[] = $supplierName . ' SPN'; + $suppliersByName[$supplierName] = $supplier; } foreach ($csv->getRecords() as $offset => $entry) { @@ -356,6 +359,41 @@ class BOMImporter } } + // Try to link existing part based on supplier part number if no Part-DB ID is given + if ($part === null) { + // Check all available supplier SPN fields + foreach ($suppliersByName as $supplierName => $supplier) { + $supplier_spn = null; + + if (isset($mapped_entry[$supplierName . ' SPN']) && !empty(trim($mapped_entry[$supplierName . ' SPN']))) { + $supplier_spn = trim($mapped_entry[$supplierName . ' SPN']); + } + + if ($supplier_spn !== null) { + // Query for orderdetails with matching supplier and SPN + $orderdetail = $this->entityManager->getRepository(\App\Entity\PriceInformations\Orderdetail::class) + ->findOneBy([ + 'supplier' => $supplier, + 'supplierpartnr' => $supplier_spn, + ]); + + if ($orderdetail !== null && $orderdetail->getPart() !== null) { + $part = $orderdetail->getPart(); + $name = $part->getName(); // Update name with actual part name + + $this->logger->info('Linked BOM entry to existing part via supplier SPN', [ + 'supplier' => $supplierName, + 'supplier_spn' => $supplier_spn, + 'part_id' => $part->getID(), + 'part_name' => $part->getName(), + ]); + + break; // Stop searching once a match is found + } + } + } + } + // Create unique key for this entry (name + part ID) $entry_key = $name . '|' . ($part ? $part->getID() : 'null');