src/Order/Doctrine/Entity/Order.php line 47

Open in your IDE?
  1. <?php
  2. declare(strict_types=1);
  3. namespace App\Order\Doctrine\Entity;
  4. use ApiPlatform\Core\Annotation\ApiFilter;
  5. use ApiPlatform\Core\Annotation\ApiProperty;
  6. use ApiPlatform\Core\Annotation\ApiResource;
  7. use App\Order\Controller\Order\CreateController;
  8. use App\Order\Doctrine\Repository\OrderRepository;
  9. use App\Order\Filter\OrderFilter;
  10. use App\Point\Doctrine\Entity\Account;
  11. use App\Shop\Doctrine\Entity\Shop;
  12. use DateTimeImmutable;
  13. use Doctrine\Common\Collections\ArrayCollection;
  14. use Doctrine\Common\Collections\Collection;
  15. use Doctrine\ORM\Mapping\Column;
  16. use Doctrine\ORM\Mapping\Embedded;
  17. use Doctrine\ORM\Mapping\Entity;
  18. use Doctrine\ORM\Mapping\GeneratedValue;
  19. use Doctrine\ORM\Mapping\Id;
  20. use Doctrine\ORM\Mapping\JoinColumn;
  21. use Doctrine\ORM\Mapping\ManyToOne;
  22. use Doctrine\ORM\Mapping\OneToMany;
  23. use Doctrine\ORM\Mapping\Table;
  24. use Symfony\Component\Serializer\Annotation\Groups;
  25. use Symfony\Component\Validator\Constraints\Callback;
  26. use Symfony\Component\Validator\Constraints\Count;
  27. use Symfony\Component\Validator\Constraints\NotNull;
  28. use Symfony\Component\Validator\Constraints\Valid;
  29. use Symfony\Component\Validator\Context\ExecutionContextInterface;
  30. #[ApiResource(
  31.     collectionOperations: ['get''post' => ['controller' => CreateController::class]],
  32.     itemOperations: ['get' => ['security' => 'is_granted("item", object)']],
  33.     normalizationContext: ['groups' => ['read''product']],
  34.     denormalizationContext: ['groups' => ['write']],
  35.     attributes: [
  36.         'pagination_enabled' => false,
  37.         'order' => ['orderedAt' => 'DESC'],
  38.     ],
  39. )]
  40. #[Entity(repositoryClassOrderRepository::class)]
  41. #[ApiFilter(OrderFilter::class)]
  42. #[Table(name'`order`')]
  43. class Order
  44. {
  45.     #[Id]
  46.     #[Column(type'integer')]
  47.     #[GeneratedValue]
  48.     #[Groups(['read'])]
  49.     private ?int $id null;
  50.     #[Column(type'datetime_immutable')]
  51.     #[Groups(['read'])]
  52.     private DateTimeImmutable $orderedAt;
  53.     #[Column(type'datetime_immutable')]
  54.     #[Groups(['read'])]
  55.     private DateTimeImmutable $updatedAt;
  56.     #[ManyToOne(targetEntityAccount::class)]
  57.     #[JoinColumn(nullablefalseonDelete'CASCADE')]
  58.     #[ApiProperty(readableLinkfalsewritableLinkfalse)]
  59.     #[Groups(['read''write'])]
  60.     #[NotNull]
  61.     private Account $account;
  62.     #[ManyToOne(targetEntityShop::class)]
  63.     #[JoinColumn(nullablefalseonDelete'CASCADE')]
  64.     private Shop $shop;
  65.     #[Column]
  66.     #[Groups(['read'])]
  67.     private string $state 'pending';
  68.     #[Column(nullabletrue)]
  69.     #[Groups(['read'])]
  70.     private ?string $orderForm null;
  71.     /**
  72.      * @var array<array-key, array{state: string, date: string}>
  73.      */
  74.     #[Column(type'array')]
  75.     private array $history = [];
  76.     /**
  77.      * @var Collection<int, Line>
  78.      */
  79.     #[OneToMany(mappedBy'order'targetEntityLine::class, cascade: ['persist'])]
  80.     #[Count(min1)]
  81.     #[Valid]
  82.     #[Groups(['read''write'])]
  83.     private Collection $lines;
  84.     /**
  85.      * @var Collection<int, Detail>
  86.      */
  87.     #[OneToMany(mappedBy'order'targetEntityDetail::class, cascade: ['persist'])]
  88.     private Collection $details;
  89.     #[Embedded(class: Address::class)]
  90.     #[Valid]
  91.     #[Groups(['read''write'])]
  92.     private Address $deliveryAddress;
  93.     #[Embedded(class: Address::class)]
  94.     #[Valid]
  95.     #[Groups(['read''write'])]
  96.     private Address $billingAddress;
  97.     #[Embedded(class: Address::class)]
  98.     #[Valid]
  99.     #[Groups(['read''write'])]
  100.     private Address $mainAddress;
  101.     #[Column(nullabletrue)]
  102.     #[Groups(['read''write'])]
  103.     private ?string $comment null;
  104.     public function __construct()
  105.     {
  106.         $this->orderedAt = new DateTimeImmutable();
  107.         $this->updatedAt = new DateTimeImmutable();
  108.         $this->lines = new ArrayCollection();
  109.         $this->details = new ArrayCollection();
  110.         $this->deliveryAddress = new Address();
  111.         $this->billingAddress = new Address();
  112.         $this->mainAddress = new Address();
  113.         $this->addStateHistory('pending');
  114.     }
  115.     public function getId(): ?int
  116.     {
  117.         return $this->id;
  118.     }
  119.     public function getOrderedAt(): DateTimeImmutable
  120.     {
  121.         return $this->orderedAt;
  122.     }
  123.     public function getUpdatedAt(): DateTimeImmutable
  124.     {
  125.         return $this->updatedAt;
  126.     }
  127.     public function setUpdatedAt(DateTimeImmutable $updatedAt): void
  128.     {
  129.         $this->updatedAt $updatedAt;
  130.     }
  131.     public function getAccount(): Account
  132.     {
  133.         return $this->account;
  134.     }
  135.     public function setAccount(Account $account): void
  136.     {
  137.         $this->account $account;
  138.     }
  139.     public function getShop(): Shop
  140.     {
  141.         return $this->shop;
  142.     }
  143.     public function setShop(Shop $shop): void
  144.     {
  145.         $this->shop $shop;
  146.     }
  147.     public function getState(): string
  148.     {
  149.         return $this->state;
  150.     }
  151.     public function setState(string $state): void
  152.     {
  153.         $this->state $state;
  154.     }
  155.     /**
  156.      * @return array<array-key, array{state: string, date: string}>
  157.      */
  158.     public function getHistory(): array
  159.     {
  160.         return $this->history;
  161.     }
  162.     public function addStateHistory(string $state): void
  163.     {
  164.         $this->history[] = ['date' => date('Y-m-d H:i:s'), 'state' => $state];
  165.     }
  166.     /**
  167.      * @return Collection<int, Line>
  168.      */
  169.     public function getLines(): Collection
  170.     {
  171.         return $this->lines;
  172.     }
  173.     public function addLine(Line $line): void
  174.     {
  175.         $line->setOrder($this);
  176.         if (null === $line->getProduct()->getCurrentPrice()) {
  177.             throw new \Exception('Thisproduct has no current price.');
  178.         }
  179.         $line->setPrice($line->getProduct()->getCurrentPrice());
  180.         $this->lines->add($line);
  181.     }
  182.     public function removeLine(Line $line): void
  183.     {
  184.         $this->lines->removeElement($line);
  185.     }
  186.     /**
  187.      * @return Collection<int, Detail>
  188.      */
  189.     public function getDetails(): Collection
  190.     {
  191.         return $this->details;
  192.     }
  193.     public function getTotalPrice(): int
  194.     {
  195.         return intval(array_sum($this->getLines()->map(static fn (Line $line) => $line->getTotalPrice())->toArray()));
  196.     }
  197.     public function getTotalPoints(): int
  198.     {
  199.         return intval(array_sum($this->getLines()->map(static fn (Line $line) => $line->getTotalPoints())->toArray()));
  200.     }
  201.     public function getNumberOfProducts(): int
  202.     {
  203.         return intval(array_sum($this->getLines()->map(static fn (Line $line) => $line->getQuantity())->toArray()));
  204.     }
  205.     public function getReference(): string
  206.     {
  207.         return sprintf('BCB%02d-1%04d-%d',$this->account->getProfile()->getId(), $this->id$this->account->getId());
  208.     }
  209.     #[Callback]
  210.     public function validate(ExecutionContextInterface $context): void
  211.     {
  212.         if ($this->account->getBalance() < $this->getTotalPoints()) {
  213.             $context->buildViolation('Le montant de la commande est trop élevé.')->addViolation();
  214.         }
  215.     }
  216.     /**
  217.      * @return Collection<int, Detail>
  218.      */
  219.     public function getDetailsToCancel(): Collection
  220.     {
  221.         return $this
  222.             ->getDetails()
  223.             ->filter(static fn (Detail $detail) => $detail->getState() === 'in_progress' || $detail->getState() === 'waiting_for_shipment' || $detail->getState() === 'shipped' || $detail->getState() === 'delivered');
  224.     }
  225.     /**
  226.      * @return Collection<int, Detail>
  227.      */
  228.     public function getDetailsToProcess(): Collection
  229.     {
  230.         return $this
  231.             ->getDetails()
  232.             ->filter(static fn (Detail $detail) => 'in_progress' === $detail->getState());
  233.     }
  234.     /**
  235.      * @return Collection<int, Detail>
  236.      */
  237.     public function getDetailsToShip(): Collection
  238.     {
  239.         return $this
  240.             ->getDetails()
  241.             ->filter(static fn (Detail $detail) => 'waiting_for_shipment' === $detail->getState());
  242.     }
  243.     /**
  244.      * @return Collection<int, Detail>
  245.      */
  246.     public function getDetailsToDeliver(): Collection
  247.     {
  248.         return $this
  249.             ->getDetails()
  250.             ->filter(static fn (Detail $detail) => 'waiting_for_shipment' === $detail->getState()
  251.                 || 'shipped' === $detail->getState());
  252.     }
  253.     public function getDeliveryAddress(): Address
  254.     {
  255.         return $this->deliveryAddress;
  256.     }
  257.     public function setDeliveryAddress(Address $deliveryAddress): void
  258.     {
  259.         $this->deliveryAddress $deliveryAddress;
  260.     }
  261.     public function getBillingAddress(): Address
  262.     {
  263.         return $this->billingAddress;
  264.     }
  265.     public function setBillingAddress(Address $billingAddress): void
  266.     {
  267.         $this->billingAddress $billingAddress;
  268.     }
  269.     public function getMainAddress(): Address
  270.     {
  271.         return $this->mainAddress;
  272.     }
  273.     public function setMainAddress(Address $mainAddress): void
  274.     {
  275.         $this->mainAddress $mainAddress;
  276.     }
  277.     public function getTotalQuantity(): int
  278.     {
  279.         return array_sum($this->getLines()->map(static fn (Line $line) => $line->getQuantity())->toArray());
  280.     }
  281.     public function getOrderForm(): ?string
  282.     {
  283.         return $this->orderForm;
  284.     }
  285.     public function setOrderForm(?string $orderForm): void
  286.     {
  287.         $this->orderForm $orderForm;
  288.     }
  289.     public function getComment(): ?string
  290.     {
  291.         return $this->comment;
  292.     }
  293.     public function setComment(?string $comment): void
  294.     {
  295.         $this->comment $comment;
  296.     }
  297. }