<?php

namespace WordpressModels\ORM\Entity;

use Doctrine\Common\Collections\Collection;
use Doctrine\DBAL\Types\Types;
use Doctrine\ORM\Mapping as ORM;
use Doctrine\ORM\Mapping\OneToOne;
use Symfony\Component\Serializer\Annotation\Groups;
use Symfony\Component\Serializer\Annotation\SerializedName;
use Symfony\Component\Serializer\Attribute\Context;

/**
 * Entity mapping for WordPress term table.
 *
 * Serialization groups:
 * - read_term -- for reading terms.
 * - read_term_details -- for reading terms with details, like taxonomy relationship.
 */
#[
    ORM\Table('terms'),
    ORM\Index(['slug'], name: 'slug'),
    ORM\Index(['name'], name: 'name'),
    ORM\Entity,
    ORM\Cache(usage: 'NONSTRICT_READ_WRITE', region: 'wp_terms'),
]
class Term
{
    #[ORM\Column(name: 'term_id', type: Types::BIGINT, options: ['unsigned' => true])]
    #[ORM\Id]
    #[ORM\GeneratedValue(strategy: 'IDENTITY')]
    #[Groups(['read_term'])]
    private ?int $id = null;

    #[ORM\Column(name: 'name', type: Types::STRING, length: 200)]
    #[Groups(['read_term'])]
    private string $name = '';

    #[ORM\Column(name: 'slug', type: Types::STRING, length: 200)]
    #[Groups(['read_term'])]
    private string $slug = '';

    #[ORM\Column(name: 'term_group', type: Types::BIGINT)]
    #[Groups(['read_term'])]
    private int $group = 0;

    #[ORM\OneToMany(mappedBy: 'term', targetEntity: TermMeta::class, indexBy: 'key')]
    #[Context(normalizationContext: ['groups' => ['read_meta']])]
    #[Groups(['read_term_assoc', 'read_term_meta'])]
    private Collection $meta;

    /**
     * TermTaxonomy and Term are very closely bound, so we create an association with 'EAGER' fetching strategy and
     * 'ALL' cascading strategy, such that they almost act like a single entity.
     * @var TermTaxonomy|null
     */
    #[OneToOne(mappedBy: 'term', targetEntity: TermTaxonomy::class, cascade: ['ALL'], fetch: 'EAGER')]
    #[Groups(['read_term_assoc', 'read_term_term_taxonomy'])]
    private ?TermTaxonomy $termTaxonomy = null;


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

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

    public function getName(): string
    {
        return $this->name;
    }

    public function setName(string $name): Term
    {
        $this->name = $name;
        return $this;
    }

    public function getSlug(): string
    {
        return $this->slug;
    }

    public function setSlug(string $slug): Term
    {
        $this->slug = $slug;
        return $this;
    }

    public function getGroup(): int
    {
        return $this->group;
    }

    public function setGroup(int $group): Term
    {
        $this->group = $group;
        return $this;
    }

    public function getMeta(): Collection
    {
        return $this->meta;
    }

    public function setMeta(Collection $meta): Term
    {
        $this->meta = $meta;
        return $this;
    }

    public function getTermTaxonomy(): ?TermTaxonomy
    {
        return $this->termTaxonomy;
    }

    public function setTermTaxonomy(?TermTaxonomy $termTaxonomy): Term
    {
        $this->termTaxonomy = $termTaxonomy;
        return $this;
    }

    #[SerializedName('taxonomy')]
    #[Groups(['read_term'])]
    public function getTaxonomy()
    {
        return $this->termTaxonomy->getTaxonomy();
    }

}
