<?php

declare(strict_types=1);

namespace App\Entity;

use ApiPlatform\Doctrine\Orm\Filter\DateFilter;
use ApiPlatform\Doctrine\Orm\Filter\SearchFilter;
use ApiPlatform\Metadata\ApiFilter;
use ApiPlatform\Metadata\ApiResource;
use ApiPlatform\Metadata\Delete;
use ApiPlatform\Metadata\Get;
use ApiPlatform\Metadata\GetCollection;
use ApiPlatform\Metadata\Patch;
use ApiPlatform\Metadata\Post;
use App\Repository\MileageAllowanceRepository;
use App\State\MileageAllowanceAmountReceiptDownloadProvider;
use App\State\MileageAllowanceAmountReceiptUploadProcessor;
use App\State\MileageAllowanceDeleteProcessor;
use App\State\MileageAllowanceReceiptDownloadProvider;
use App\State\MileageAllowanceReceiptUploadProcessor;
use DateTimeImmutable;
use Doctrine\ORM\Mapping as ORM;
use Symfony\Component\Serializer\Attribute\Groups;

#[ApiResource(
    operations: [
        new Get(
            security: "is_granted('ROLE_ADMIN')"
        ),
        new GetCollection(
            security: "is_granted('ROLE_ADMIN')"
        ),
        new Post(
            security: "is_granted('ROLE_ADMIN')"
        ),
        new Patch(
            security: "is_granted('ROLE_ADMIN')"
        ),
        new Delete(
            security: "is_granted('ROLE_ADMIN')",
            processor: MileageAllowanceDeleteProcessor::class,
        ),
        new Post(
            uriTemplate: '/mileage_allowances/{id}/receipt',
            security: "is_granted('ROLE_ADMIN')",
            deserialize: false,
            processor: MileageAllowanceReceiptUploadProcessor::class,
        ),
        new Get(
            uriTemplate: '/mileage_allowances/{id}/receipt',
            security: "is_granted('ROLE_ADMIN')",
            provider: MileageAllowanceReceiptDownloadProvider::class,
        ),
        new Post(
            uriTemplate: '/mileage_allowances/{id}/amount-receipt',
            security: "is_granted('ROLE_ADMIN')",
            deserialize: false,
            processor: MileageAllowanceAmountReceiptUploadProcessor::class,
        ),
        new Get(
            uriTemplate: '/mileage_allowances/{id}/amount-receipt',
            security: "is_granted('ROLE_ADMIN')",
            provider: MileageAllowanceAmountReceiptDownloadProvider::class,
        ),
    ],
    normalizationContext: [
        'groups'          => ['mileage_allowance:read', 'employee:read'],
        'datetime_format' => 'Y-m-d',
    ],
    denormalizationContext: [
        'groups'          => ['mileage_allowance:write'],
        'datetime_format' => 'Y-m-d',
    ],
    order: ['month' => 'DESC'],
    paginationEnabled: false,
)]
#[ApiFilter(DateFilter::class, properties: ['month'])]
#[ApiFilter(SearchFilter::class, properties: ['employee' => 'exact'])]
#[ORM\Entity(repositoryClass: MileageAllowanceRepository::class)]
#[ORM\Table(name: 'mileage_allowances')]
class MileageAllowance
{
    #[ORM\Id]
    #[ORM\GeneratedValue]
    #[ORM\Column(type: 'integer')]
    #[Groups(['mileage_allowance:read'])]
    private ?int $id = null;

    #[ORM\ManyToOne(targetEntity: Employee::class)]
    #[ORM\JoinColumn(nullable: false)]
    #[Groups(['mileage_allowance:read', 'mileage_allowance:write'])]
    private ?Employee $employee = null;

    #[ORM\Column(type: 'date_immutable')]
    #[Groups(['mileage_allowance:read', 'mileage_allowance:write'])]
    private ?DateTimeImmutable $month = null;

    #[ORM\Column(type: 'float')]
    #[Groups(['mileage_allowance:read', 'mileage_allowance:write'])]
    private float $kilometers = 0;

    #[ORM\Column(type: 'float', options: ['default' => 0])]
    #[Groups(['mileage_allowance:read', 'mileage_allowance:write'])]
    private float $amount = 0;

    #[ORM\Column(type: 'text', nullable: true)]
    #[Groups(['mileage_allowance:read', 'mileage_allowance:write'])]
    private ?string $comment = null;

    #[ORM\Column(type: 'string', length: 255, nullable: true)]
    #[Groups(['mileage_allowance:read'])]
    private ?string $receiptPath = null;

    #[ORM\Column(type: 'string', length: 255, nullable: true)]
    #[Groups(['mileage_allowance:read'])]
    private ?string $receiptName = null;

    #[ORM\Column(type: 'string', length: 255, nullable: true)]
    #[Groups(['mileage_allowance:read'])]
    private ?string $amountReceiptPath = null;

    #[ORM\Column(type: 'string', length: 255, nullable: true)]
    #[Groups(['mileage_allowance:read'])]
    private ?string $amountReceiptName = null;

    #[ORM\Column(type: 'datetime_immutable')]
    #[Groups(['mileage_allowance:read'])]
    private DateTimeImmutable $createdAt;

    public function __construct()
    {
        $this->createdAt = new DateTimeImmutable();
    }

    public function getId(): ?int
    {
        return $this->id;
    }

    public function getEmployee(): ?Employee
    {
        return $this->employee;
    }

    public function setEmployee(?Employee $employee): self
    {
        $this->employee = $employee;

        return $this;
    }

    public function getMonth(): ?DateTimeImmutable
    {
        return $this->month;
    }

    public function setMonth(?DateTimeImmutable $month): self
    {
        $this->month = $month;

        return $this;
    }

    public function getKilometers(): float
    {
        return $this->kilometers;
    }

    public function setKilometers(float $kilometers): self
    {
        $this->kilometers = $kilometers;

        return $this;
    }

    public function getAmount(): float
    {
        return $this->amount;
    }

    public function setAmount(float $amount): self
    {
        $this->amount = $amount;

        return $this;
    }

    public function getComment(): ?string
    {
        return $this->comment;
    }

    public function setComment(?string $comment): self
    {
        $this->comment = $comment;

        return $this;
    }

    public function getReceiptPath(): ?string
    {
        return $this->receiptPath;
    }

    public function setReceiptPath(?string $receiptPath): self
    {
        $this->receiptPath = $receiptPath;

        return $this;
    }

    public function getReceiptName(): ?string
    {
        return $this->receiptName;
    }

    public function setReceiptName(?string $receiptName): self
    {
        $this->receiptName = $receiptName;

        return $this;
    }

    public function getAmountReceiptPath(): ?string
    {
        return $this->amountReceiptPath;
    }

    public function setAmountReceiptPath(?string $amountReceiptPath): self
    {
        $this->amountReceiptPath = $amountReceiptPath;

        return $this;
    }

    public function getAmountReceiptName(): ?string
    {
        return $this->amountReceiptName;
    }

    public function setAmountReceiptName(?string $amountReceiptName): self
    {
        $this->amountReceiptName = $amountReceiptName;

        return $this;
    }

    public function getCreatedAt(): DateTimeImmutable
    {
        return $this->createdAt;
    }
}
