<?php

declare(strict_types=1);

/*
 * Chill is a software for social workers
 *
 * For the full copyright and license information, please view
 * the LICENSE file that was distributed with this source code.
 */

namespace Chill\BudgetBundle\Calculator;

use Chill\BudgetBundle\Entity\Charge;
use Chill\BudgetBundle\Entity\Resource;

class CalculatorManager
{
    /**
     * @var array<string, CalculatorInterface>
     */
    private array $calculators = [];

    /**
     * @var string[]
     */
    private array $defaultCalculator = [];

    public function addCalculator(CalculatorInterface $calculator, bool $default)
    {
        $this->calculators[$calculator->getAlias()] = $calculator;

        if ($default) {
            $this->defaultCalculator[] = $calculator->getAlias();
        }
    }

    /**
     * @param array<resource|Charge> $elements
     *
     * @return CalculatorResult[]
     */
    public function calculateDefault(array $elements)
    {
        $results = [];

        foreach ($this->defaultCalculator as $alias) {
            $result = $this->getCalculator($alias)->calculate($elements);

            if (null !== $result) {
                $results[$alias] = $result;
            }
        }

        return $results;
    }

    public function getCalculator(string $alias): CalculatorInterface
    {
        if (false === \array_key_exists($alias, $this->calculators)) {
            throw new \OutOfBoundsException("The calculator with alias '{$alias}' does ".'not exists. Possible values are '.\implode(', ', \array_keys($this->calculators)));
        }

        return $this->calculators[$alias];
    }
}
