<?php

namespace KupShop\BonusProgramBundle\Triggers;

use KupShop\BonusProgramBundle\Utils\BonusProvider;
use KupShop\KupShopBundle\Context\UserContext;
use KupShop\KupShopBundle\Query\JsonOperator;
use KupShop\OrderDiscountBundle\Triggers\AbstractTrigger;
use KupShop\OrderingBundle\Entity\Purchase\PurchaseState;
use Query\Operator;

class BonusPointsTrigger extends AbstractTrigger
{
    protected static $type = 'bonus_points';
    protected static $position = 65;
    protected $adminTemplate = 'triggers/bonus_points.tpl';
    protected $name = 'Body uživatele';
    protected $description = 'Zákazník má body ve věrnostním programu.';

    /** @var UserContext */
    private $userContext;

    /** @var BonusProvider */
    private $bonusProvider;

    /**
     * BonusPointsTrigger constructor.
     */
    public function __construct(UserContext $userContext, BonusProvider $bonusProvider)
    {
        $this->userContext = $userContext;
        $this->bonusProvider = $bonusProvider;
    }

    public function getDiscountFilterSpec(PurchaseState $purchaseState)
    {
        $specs = [
            Operator::equals(['odt.type' => static::getType()]),
        ];

        if ($user = $this->userContext->getActive()) {
            $active_points = $this->bonusProvider->getActivePointsAmount($user);
            $min = JsonOperator::value('odt.data', 'min', true);
            $max = JsonOperator::value('odt.data', 'max', true);

            $specs[] = Operator::not(
                Operator::andX(
                    "{$active_points} >= {$min} OR {$min} IS NULL",
                    "{$active_points} <= {$max} OR {$max} IS NULL"
                )
            );
        }

        return Operator::andX($specs);
    }

    public function checkValidity(&$data)
    {
        $data = array_filter($data, 'strlen');
        if (!empty($data)) {
            $min = $data['min'] ?? null;
            $max = $data['max'] ?? null;
            if (is_null($min) || is_null($max) || ($min <= $max)) {
                return true;
            }
        }

        throw new \Exception($this->getName().' ['.$this->getType().'] - data is not valid.');
    }
}
