<?php

declare(strict_types=1);

namespace MonsieurBiz\SyliusSearchPlugin\Model\Document;

use Elastica\ResultSet as ElasticaResultSet;
use JoliCode\Elastically\Result;
use MonsieurBiz\SyliusSearchPlugin\Adapter\ResultSetAdapter;
use Pagerfanta\Pagerfanta;
use Pagerfanta\PagerfantaInterface;

class ResultSet implements ResultSetInterface
{
    private Pagerfanta $pager;

    public function __construct(
        private readonly int $maxItems,
        private readonly int $page,
        private readonly FiltersAwareInterface $filters,
        private readonly FilterAwareInterface $taxonFilter,
        private readonly FilterAwareInterface $mainTaxonFilter,
        private readonly RangeFilterAwareInterface $priceFilter,
        ?ElasticaResultSet $resultSet = null,
        private ?int $totalHits = 0,
        private array $results = [],
    ) {
        // Empty result set
        if (null === $resultSet) {
            $this->totalHits = 0;
            $this->results = [];
        } else {
            /** @var Result $result */
            foreach ($resultSet as $result) {
                $this->results[] = $result->getModel();
            }
            $this->totalHits = $resultSet->getTotalHits();
        }

        $this->initPager();
    }

    /**
     * Init pager with Pager Fanta.
     */
    private function initPager(): void
    {
        $adapter = new ResultSetAdapter($this);
        $this->pager = new Pagerfanta($adapter);
        $this->pager->setMaxPerPage($this->maxItems);
        $this->pager->setCurrentPage($this->page);
    }

    /**
     * @return Result[]
     */
    public function getResults(): array
    {
        return $this->results;
    }

    public function getFilters(): array
    {
        return $this->filters->getFilters();
    }

    public function getTotalHits(): int
    {
        return $this->totalHits;
    }

    public function getPager(): PagerfantaInterface
    {
        return $this->pager;
    }

    public function getTaxonFilter(): ?FilterInterface
    {
        return $this->taxonFilter->getFilter();
    }

    public function getMainTaxonFilter(): ?FilterInterface
    {
        return $this->mainTaxonFilter->getFilter();
    }

    public function getPriceFilter(): ?RangeFilterInterface
    {
        return $this->priceFilter->getFilter();
    }
}
