src/EventSubscriber/Expediting/ShipmentScheduler.php line 39
<?php
namespace App\EventSubscriber\Expediting;
use App\Doctrine\Type\Expediting\ShipmentType;
use App\Doctrine\Type\Expediting\ShippingSegmentStatus;
use App\Doctrine\Type\Expediting\TransportMode;
use App\Entity\Expediting\ShippingSegment;
use App\Entity\Scheduler\Task;
use App\Event\Expediting\ShipmentBookingEvent;
use App\Event\Expediting\ShipmentStatusUpdateEvent;
use App\Repository\Scheduler\TaskRepository;
use Doctrine\ORM\EntityManagerInterface;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
readonly class ShipmentScheduler implements EventSubscriberInterface
{
public function __construct(
private EntityManagerInterface $entityManager,
private TaskRepository $taskRepository,
) {}
public static function getSubscribedEvents(): array
{
return [
ShipmentBookingEvent::IDENTIFIER => ['schedulePickup', 90],
ShipmentStatusUpdateEvent::IDENTIFIER => ['scheduleArrival', 90],
];
}
public function schedulePickup(ShipmentBookingEvent $event): void
{
$segment = $event->getShippingSegment();
$departureTask = $this->getDepartureTask($segment);
$this->entityManager->persist($departureTask);
$this->entityManager->flush();
}
public function scheduleArrival(ShipmentStatusUpdateEvent $event): void
{
$segment = $event->getShippingSegment();
if (ShippingSegmentStatus::STARTED !== $segment->getStatus()) {
return;
}
$arrivalTask = $this->getArrivalTask($segment);
$this->entityManager->persist($arrivalTask);
$this->entityManager->flush();
}
private function getDepartureTask(ShippingSegment $segment): Task
{
if (in_array(ShipmentType::PICKUP, $segment->getTypes())) {
return $this->taskRepository->getPickupTask($segment, createIfNull: true);
}
return match ($segment->getTransportMode()) {
TransportMode::AIR => $this->taskRepository->getAirShipmentDepartureTask($segment, createIfNull: true),
TransportMode::ROAD => $this->taskRepository->getRoadShipmentDepartureTask($segment, createIfNull: true),
TransportMode::SEA => $this->taskRepository->getSeaShipmentDepartureTask($segment, createIfNull: true),
TransportMode::TRAIN => $this->taskRepository->getTrainShipmentDepartureTask($segment, createIfNull: true),
};
}
private function getArrivalTask(ShippingSegment $segment): Task
{
if (in_array(ShipmentType::HUB_DELIVERY, $segment->getTypes())) {
return $this->taskRepository->getHubDeliveryTask($segment, createIfNull: true);
}
return match ($segment->getTransportMode()) {
TransportMode::AIR => $this->taskRepository->getAirShipmentDeliveryTask($segment, createIfNull: true),
TransportMode::ROAD => $this->taskRepository->getRoadShipmentDeliveryTask($segment, createIfNull: true),
TransportMode::SEA => $this->taskRepository->getSeaShipmentDeliveryTask($segment, createIfNull: true),
TransportMode::TRAIN => $this->taskRepository->getTrainShipmentDeliveryTask($segment, createIfNull: true),
};
}
}