<?php

namespace Mailbox\Application;

use Mailbox\Domain\MailBox\Contracts\MailBoxCriteriaInterface;
use Mailbox\Domain\Message\Contracts\MessageAttachmentCriteriaInterface;
use Mailbox\Domain\Message\Contracts\MessageCriteriaInterface;
use Repo\Concrete\AbstractCriteria;

/**
 *
 * Class SearchCriteria
 * @package Mailbox\Application
 */
final class MessageSearchCriteria extends AbstractCriteria implements
    MessageCriteriaInterface,
    MessageAttachmentCriteriaInterface
{

    protected $filterByUid;

    protected $filterById;

    protected $sortedById;

    /**
     * @var array
     */
    protected $filterByFromEmails;

    /**
     * @var string
     */
    protected $searchBySubject;

    /**
     * @var string
     */
    protected $filterByMailBoxName;

    /**
     * @var array
     */
    protected $filterByAttachmentExt = [];

    /**
     * @var
     */
    protected $filterByAttachmentRegexp;

    /**
     * @var string
     */
    protected $searchByAttachmentName;


    protected $searchByFileInArchive;

    /**
     * @var int
     */
    protected $limit = 100;

    /**
     * @var \DateTime
     */
    protected $filterByDatetimeTo;

    /**
     * @var \DateTime
     */
    protected $filterByDatetimeFrom;

    /**
     * вытаскивать с вложениями
     * @var bool
     */
    protected $withAttachments = false;

    /**
     * помечать письмо прочтенными если найдено
     * @var bool
     */
    protected $markSeenIfFound = true;

    public static function create()
    {
        return new self();
    }

    /**
     * @return int|null
     */
    public function getFilterByUid(): ?int
    {
        return $this->filterByUid;
    }

    /**
     * @param $uid
     * @return $this
     */
    public function setFilterByUid($uid)
    {
        $this->filterByUid = $uid;
        return $this;
    }


    /**
     * @return mixed
     */
    public function getSearchByFileInArchive(): ?string
    {
        return $this->searchByFileInArchive;
    }

    /**
     * @param string $searchByFileInArchive
     * @return $this
     */
    public function setSearchByFileInArchive(string $searchByFileInArchive): MessageSearchCriteria
    {
        $this->searchByFileInArchive = $searchByFileInArchive;
        return $this;
    }




    /**
     * @return mixed
     */
    public function getFilterByAttachmentRegexp(): ?string
    {
        return $this->filterByAttachmentRegexp;
    }

    /**
     * @param mixed $filterByAttachmentRegexp
     * @return MessageSearchCriteria
     */
    public function setFilterByAttachmentRegexp(string $filterByAttachmentRegexp): MessageSearchCriteria
    {
        $this->filterByAttachmentRegexp = $filterByAttachmentRegexp;
        $this->withAttachments = true;
        return $this;
    }

    /**
     * @return array
     */
    public function getFilterByAttachmentExt(): ?array
    {
        return $this->filterByAttachmentExt;
    }

    /**
     * @param array $filterByAttachmentExt
     * @return MessageSearchCriteria
     */
    public function setFilterByAttachmentExt(array $filterByAttachmentExt): MessageSearchCriteria
    {
        $this->filterByAttachmentExt = $filterByAttachmentExt;
        $this->withAttachments = true;
        return $this;
    }

    /**
     * @return string
     */
    public function getFilterByFromEmail(): ?string
    {
        return isset($this->filterByFromEmails[0]) ? $this->filterByFromEmails[0] : null;
    }

    /**
     * @return array
     */
    public function getFilterByFromEmails(): ?array
    {
        return $this->filterByFromEmails;
    }

    /**
     * @return bool
     */
    public function isMarkSeenIfFound(): bool
    {
        return $this->markSeenIfFound;
    }

    /**
     * @param bool $markSeenIfFound
     * @return MessageSearchCriteria
     */
    public function setMarkSeenIfFound(bool $markSeenIfFound): MessageSearchCriteria
    {
        $this->markSeenIfFound = $markSeenIfFound;
        return $this;
    }


    /**
     * @param string $filterByFromEmails
     * @return MessageSearchCriteria
     */
    public function setFilterByFromEmails(string $filterByFromEmails): MessageSearchCriteria
    {
        $filterByFromEmailsAr = array_map('strtolower', explode('|', $filterByFromEmails));
        $this->filterByFromEmails = $filterByFromEmailsAr;
        return $this;
    }

    /**
     * @return string
     */
    public function getSearchBySubject(): ?string
    {
        return $this->searchBySubject;
    }

    /**
     * @param string $searchBySubject
     * @return MessageSearchCriteria
     */
    public function setSearchBySubject(string $searchBySubject): MessageSearchCriteria
    {
        $this->searchBySubject = $searchBySubject;
        return $this;
    }

    /**
     * @return string
     */
    public function getFilterByMailBoxName(): ?string
    {
        return $this->filterByMailBoxName;
    }

    /**
     * @param string $filterByMailBoxName
     * @return MessageSearchCriteria
     */
    public function setFilterByMailBoxName(string $filterByMailBoxName): MessageSearchCriteria
    {
        $this->filterByMailBoxName = $filterByMailBoxName;
        return $this;
    }

    /**
     * @return string
     */
    public function getSearchByAttachmentName(): ?string
    {
        return $this->searchByAttachmentName;
    }

    /**
     * @param string $searchByAttachmentName
     * @return MessageSearchCriteria
     */
    public function setSearchByAttachmentName(string $searchByAttachmentName): MessageSearchCriteria
    {
        $this->searchByAttachmentName = $searchByAttachmentName;
        $this->withAttachments = true;
        return $this;
    }


    /**
     * @return \DateTime
     */
    public function getfilterByDatetimeTo(): ?\DateTime
    {
        return $this->filterByDatetimeTo;
    }

    /**
     * @param \DateTime $filterByDatetimeTo
     * @return MessageSearchCriteria
     */
    public function setfilterByDatetimeTo(\DateTime $filterByDatetimeTo): MessageSearchCriteria
    {
        $this->filterByDatetimeTo = $filterByDatetimeTo;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getfilterByDatetimeFrom(): ?\DateTime
    {
        return $this->filterByDatetimeFrom;
    }

    /**
     * @param mixed $filterByDatetimeFrom
     * @return MessageSearchCriteria
     */
    public function setfilterByDatetimeFrom($filterByDatetimeFrom): MessageSearchCriteria
    {
        $this->filterByDatetimeFrom = $filterByDatetimeFrom;
        return $this;
    }

    /**
     * @return bool
     */
    public function withAttachments(): bool
    {
        return $this->withAttachments;
    }

    /**
     * @param bool $withAttachments
     * @return MessageSearchCriteria
     */
    public function setWithAttachments(bool $withAttachments): MessageSearchCriteria
    {
        $this->withAttachments = $withAttachments;
        return $this;
    }

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

    public function sortById(?string $sort)
    {
        return $this->sortedById;
    }
}
