getObjectManager(); if (!$em instanceof EntityManagerInterface) { return; } $uow = $em->getUnitOfWork(); $actorProfileId = $this->resolveActorProfileId(); $this->processLinkChanges($em, $uow, $actorProfileId); } protected function supports(object $entity): bool { return $entity instanceof Machine; } protected function entityType(): string { return 'machine'; } protected function hasCollectionTracking(): bool { return true; } protected function getOwnerFromCustomFieldValue(CustomFieldValue $cfv): ?object { $owner = $cfv->getMachine(); return $owner instanceof Machine ? $owner : null; } protected function snapshotEntity(object $entity): array { $customFieldValues = []; foreach ($entity->getCustomFieldValues() as $cfv) { $customFieldValues[] = [ 'id' => $cfv->getId(), 'fieldName' => $cfv->getCustomField()?->getName(), 'fieldId' => $cfv->getCustomField()?->getId(), 'value' => $cfv->getValue(), ]; } $componentLinks = []; foreach ($entity->getComponentLinks() as $link) { $componentLinks[] = [ 'id' => $link->getId(), 'composantId' => $link->getComposant()?->getId(), 'composantName' => $link->getComposant()?->getName(), 'modelTypeId' => $link->getModelType()?->getId(), ]; } $pieceLinks = []; foreach ($entity->getPieceLinks() as $link) { $pieceLinks[] = [ 'id' => $link->getId(), 'pieceId' => $link->getPiece()?->getId(), 'pieceName' => $link->getPiece()?->getName(), 'quantity' => $link->getQuantity(), 'modelTypeId' => $link->getModelType()?->getId(), ]; } $productLinks = []; foreach ($entity->getProductLinks() as $link) { $productLinks[] = [ 'id' => $link->getId(), 'productId' => $link->getProduct()?->getId(), 'productName' => $link->getProduct()?->getName(), 'modelTypeId' => $link->getModelType()?->getId(), ]; } return [ 'id' => $entity->getId(), 'name' => $this->safeGet($entity, 'getName'), 'reference' => $this->safeGet($entity, 'getReference'), 'prix' => $this->safeGet($entity, 'getPrix'), 'site' => $this->normalizeValue($this->safeGet($entity, 'getSite')), 'constructeurIds' => array_map( fn ($link) => [ 'id' => $link->getConstructeur()->getId(), 'name' => $link->getConstructeur()->getName(), 'supplierReference' => $link->getSupplierReference(), ], $entity->getConstructeurLinks()->toArray(), ), 'customFieldValues' => $customFieldValues, 'componentLinks' => $componentLinks, 'pieceLinks' => $pieceLinks, 'productLinks' => $productLinks, 'version' => $this->safeGet($entity, 'getVersion'), ]; } private function processLinkChanges(EntityManagerInterface $em, UnitOfWork $uow, ?string $actorProfileId): void { $machineChanges = []; // Detect inserted links foreach ($uow->getScheduledEntityInsertions() as $entity) { $info = $this->extractLinkInfo($entity, 'added'); if (null === $info) { continue; } $machineId = (string) $info['machine']->getId(); if ('' === $machineId) { continue; } $machineChanges[$machineId] ??= ['machine' => $info['machine'], 'diffs' => []]; $machineChanges[$machineId]['diffs'][$info['diffKey']] = [ 'from' => null, 'to' => $info['diffValue'], ]; } // Detect deleted links foreach ($uow->getScheduledEntityDeletions() as $entity) { $info = $this->extractLinkInfo($entity, 'removed'); if (null === $info) { continue; } $machineId = (string) $info['machine']->getId(); if ('' === $machineId) { continue; } $machineChanges[$machineId] ??= ['machine' => $info['machine'], 'diffs' => []]; $machineChanges[$machineId]['diffs'][$info['diffKey']] = [ 'from' => $info['diffValue'], 'to' => null, ]; } // Create audit logs for each affected machine foreach ($machineChanges as $machineId => $change) { $machine = $change['machine']; $diff = $change['diffs']; if ([] === $diff) { continue; } $version = $this->incrementEntityVersion($machine, $em, $uow); $snapshot = $this->snapshotEntity($machine); $this->persistAuditLog( $em, new AuditLog('machine', $machineId, 'update', $diff, $snapshot, $actorProfileId, $version), ); } } /** * @return null|array{machine: Machine, diffKey: string, diffValue: array{id: string, name: string}} */ private function extractLinkInfo(object $entity, string $action): ?array { if ($entity instanceof MachineComponentLink) { return [ 'machine' => $entity->getMachine(), 'diffKey' => $action.'Component', 'diffValue' => [ 'id' => $entity->getComposant()?->getId() ?? $entity->getModelType()?->getId(), 'name' => $entity->getComposant()?->getName() ?? $entity->getModelType()?->getName() ?? 'Catégorie seule', ], ]; } if ($entity instanceof MachinePieceLink) { return [ 'machine' => $entity->getMachine(), 'diffKey' => $action.'Piece', 'diffValue' => [ 'id' => $entity->getPiece()?->getId() ?? $entity->getModelType()?->getId(), 'name' => $entity->getPiece()?->getName() ?? $entity->getModelType()?->getName() ?? 'Catégorie seule', ], ]; } if ($entity instanceof MachineProductLink) { return [ 'machine' => $entity->getMachine(), 'diffKey' => $action.'Product', 'diffValue' => [ 'id' => $entity->getProduct()?->getId() ?? $entity->getModelType()?->getId(), 'name' => $entity->getProduct()?->getName() ?? $entity->getModelType()?->getName() ?? 'Catégorie seule', ], ]; } return null; } }