<?php
namespace App\Entity;
use App\Entity\Enum\TransactionStatus;
use App\Entity\Traits\Identifiable;
use App\Entity\Traits\Timestampable;
use App\Repository\BenefactorTransactionRepository;
use Doctrine\ORM\Mapping as ORM;
use InvalidArgumentException;
#[ORM\Entity(repositoryClass: BenefactorTransactionRepository::class)]
#[ORM\InheritanceType('SINGLE_TABLE')]
#[ORM\DiscriminatorColumn('type', 'string')]
#[ORM\DiscriminatorMap(self::TYPE_CLASSES)]
class BenefactorTransaction
{
use Identifiable;
use Timestampable;
public const TYPE_DEFAULT = 'default';
public const TYPE_CARD = 'card';
public const TYPE_CARD_SINGLE = 'card_single';
public const TYPE_CHECK = 'check';
public const TYPE_CASH = 'cash';
public const TYPE_WIRE = 'wire';
public const TYPE_CLASSES = [
self::TYPE_DEFAULT => BenefactorTransaction::class,
self::TYPE_CARD => BenefactorTransactionCard::class,
self::TYPE_CARD_SINGLE => BenefactorTransactionCardSingle::class,
self::TYPE_CHECK => BenefactorTransactionCheck::class,
self::TYPE_CASH => BenefactorTransactionCash::class,
self::TYPE_WIRE => BenefactorTransactionWire::class,
];
public const TYPE_NAMES = [
self::TYPE_DEFAULT => 'Paiement',
self::TYPE_CARD_SINGLE => 'Par carte',
self::TYPE_CHECK => 'Par chèques',
self::TYPE_CASH => 'En espèces',
self::TYPE_WIRE => 'Par virement',
];
public const PUBLIC_TYPES = [
self::TYPE_CARD_SINGLE,
self::TYPE_CHECK,
self::TYPE_CASH,
self::TYPE_WIRE,
];
#[ORM\Column(type: 'float')]
private $amount;
#[ORM\Column(type: 'float')]
private $amountPayed = 0;
#[ORM\Column(type: 'string', length: 20, enumType: TransactionStatus::class)]
private $status = TransactionStatus::Created;
#[ORM\Column(type: 'string', length: 255, nullable: true)]
private $comment;
#[ORM\ManyToOne(inversedBy: 'transactions')]
#[ORM\JoinColumn(nullable: false)]
private ?Donation $donation = null;
#[ORM\Column(type: 'string', length: 255, nullable: true)]
private $cancelReason;
public static function createFromType(string $type): self
{
if (!array_key_exists($type, self::TYPE_CLASSES)) {
throw new InvalidArgumentException(
sprintf('type must be one of "%s"', implode(', ', array_keys(self::TYPE_CLASSES)))
);
}
return new (self::TYPE_CLASSES[$type]);
}
public function getType(?bool $slug = false): string
{
if ($slug) {
return array_search(get_class($this), self::TYPE_CLASSES);
}
return self::TYPE_NAMES[array_search(get_class($this), self::TYPE_CLASSES)];
}
public function getName(): string
{
return self::getNameByClass(static::class) ?? '';
}
public static function getNameByClass($class): ?string
{
$key = array_search($class, self::TYPE_CLASSES, true);
if ($key && (self::TYPE_NAMES[$key] ?? null)) {
return self::TYPE_NAMES[$key];
}
return null;
}
public static function getPublicClasses(): array
{
$publicTypes = self::PUBLIC_TYPES;
return array_filter(self::TYPE_CLASSES, static fn($key) => in_array($key, $publicTypes), ARRAY_FILTER_USE_KEY);
}
public function getAmount(): ?float
{
return $this->amount;
}
public function setAmount(float $amount): self
{
$this->amount = $amount;
return $this;
}
public function getAmountPayed(): ?float
{
return $this->amountPayed;
}
public function setAmountPayed(float $amountPayed): self
{
$this->amountPayed = $amountPayed;
return $this;
}
public function getStatus(): ?TransactionStatus
{
return $this->status;
}
public function setStatus(TransactionStatus $status): self
{
$this->status = $status;
return $this;
}
public function getDonation(): ?Donation
{
return $this->donation;
}
public function setDonation(?Donation $donation): self
{
$this->donation = $donation;
return $this;
}
public function getComment(): ?string
{
return $this->comment;
}
public function setComment(?string $comment): self
{
$this->comment = $comment;
return $this;
}
public function getCancelReason(): ?string
{
return $this->cancelReason;
}
public function setCancelReason(?string $cancelReason): self
{
$this->cancelReason = $cancelReason;
return $this;
}
}