<?php

namespace Lc\ShopBundle\Services\Order;


use Lc\ShopBundle\Context\OrderProductInterface;
use Lc\ShopBundle\Model\Product;
use Lc\ShopBundle\Model\ProductFamily;

trait OrderUtilsStockTrait
{
        public function deductAvailabilityProduct(\Lc\ShopBundle\Model\OrderShop $orderShop)
        {
                //TODO ne pas déduire des stocks les orderProduct marqué en relivraison

                foreach ($orderShop->getOrderProducts() as $orderProduct) {
                        switch ($orderProduct->getProduct()->getProductFamily()->getBehaviorCountStock()) {
                                case ProductFamily::BEHAVIOR_COUNT_STOCK_BY_MEASURE :

                                        //Disponibilité par unité de référence
                                        $oldAvailability = $orderProduct->getProduct()->getAvailableQuantityInherited();
                                        $newAvailability = $oldAvailability - ($orderProduct->getQuantityOrder() * ($orderProduct->getQuantityProduct() / $orderProduct->getUnit()->getCoefficient()));
                                        $orderProduct->getProduct()->getProductFamily()->setAvailableQuantity($newAvailability);

                                        $this->em->persist($orderProduct->getProduct()->getProductFamily());

                                        break;
                                case ProductFamily::BEHAVIOR_COUNT_STOCK_BY_PRODUCT_FAMILY :

                                        $oldAvailability = $orderProduct->getProduct()->getAvailableQuantityInherited();
                                        $newAvailability = $oldAvailability - $orderProduct->getQuantityOrder();
                                        $orderProduct->getProduct()->getProductFamily()->setAvailableQuantity($newAvailability);

                                        $this->em->persist($orderProduct->getProduct()->getProductFamily());

                                        break;
                                case ProductFamily::BEHAVIOR_COUNT_STOCK_BY_PRODUCT :
                                        $oldAvailability = $orderProduct->getProduct()->getAvailableQuantityInherited();
                                        $newAvailability = $oldAvailability - $orderProduct->getQuantityOrder();
                                        $orderProduct->getProduct()->setAvailableQuantity($newAvailability);

                                        $this->em->persist($orderProduct->getProduct());

                                        break;
                        }

                        $this->em->flush();
                }
        }

        public function isProductAvailable(Product $product, $quantityOrder = 0, $checkCart = false, $orderShop = null)
        {
                if(!$orderShop) {
                        $orderShop = $this->getCartCurrent() ;
                }
                $productFamily = $product->getProductFamily() ;
                $quantityAsked = $quantityOrder;

                if($productFamily->getBehaviorCountStock() == ProductFamily::BEHAVIOR_COUNT_STOCK_BY_MEASURE) {
                        if(!$quantityOrder) {
                                $quantityAsked = $this->getQuantityOrderByProduct($orderShop, $product, true) ;
                        }
                        else {
                                $quantityAsked = ($product->getQuantityInherited() / $product->getUnitInherited()->getCoefficient()) * $quantityOrder;
                        }

                        if($checkCart) {
                                $quantityAsked += $this->getQuantityOrderByProduct($orderShop, $product, true) ;
                        }
                }

                if(($productFamily->getBehaviorCountStock() == ProductFamily::BEHAVIOR_COUNT_STOCK_BY_PRODUCT_FAMILY
                        || $productFamily->getBehaviorCountStock() == ProductFamily::BEHAVIOR_COUNT_STOCK_BY_PRODUCT)) {

                        if(!$quantityOrder) {
                                $quantityAsked = $this->getQuantityOrderByProduct($orderShop, $product) ;
                        }

                        if($checkCart) {
                                $quantityAsked += $this->getQuantityOrderByProduct($orderShop, $product) ;
                        }
                }

                if ($product->getAvailableQuantityInherited() >= $quantityAsked
                        || $productFamily->getBehaviorCountStock() == ProductFamily::BEHAVIOR_COUNT_STOCK_UNLIMITED) {
                        return true;
                }
                else {
                        return false;
                }
        }

        public function isOneProductAvailableAddCart($products): bool
        {
                foreach($products as $product) {
                        if($this->isProductAvailable($product, 1, true)) {
                                return true ;
                        }
                }

                return false ;
        }

        public function isOrderProductAvailable(OrderProductInterface $orderProduct)
        {
                return $this->isProductAvailable($orderProduct->getProduct(), $orderProduct->getQuantityOrder()) ;
        }

        public function isOrderProductAvailableAddCart(OrderProductInterface $orderProduct, $orderShop = null)
        {
                $product = $orderProduct->getProduct() ;
                return $this->isProductAvailable($product, $orderProduct->getQuantityOrder(), true, $orderShop);
        }

        public function getQuantityOrderByProduct($orderShop, $product, $byWeight = false)
        {
                $quantity = 0 ;
                $productFamily = $product->getProductFamily() ;
                $behaviorCountStock = $productFamily->getBehaviorCountStock() ;

                if($orderShop) {
                        foreach($orderShop->getOrderProducts() as $orderProduct) {
                                if($orderProduct->getProduct()->getId() == $product->getId()
                                        || (    ($behaviorCountStock == ProductFamily::BEHAVIOR_COUNT_STOCK_BY_PRODUCT_FAMILY || $behaviorCountStock == ProductFamily::BEHAVIOR_COUNT_STOCK_BY_MEASURE)
                                                && $orderProduct->getProduct()->getProductFamily()->getId() == $productFamily->getId())) {

                                        if($byWeight) {
                                                $quantity += $orderProduct->getQuantityOrder() * ($orderProduct->getQuantityProduct() / $product->getUnitInherited()->getCoefficient()) ;
                                        }
                                        else {
                                                $quantity += $orderProduct->getQuantityOrder() ;
                                        }
                                }
                        }
                }

                return $quantity ;
        }

        public function getProductQuantityMaxAddCart($product)
        {
                $orderShop = $this->getCartCurrent() ;
                $productFamily = $product->getProductFamily() ;

                $byWeight = false ;
                if($productFamily->getBehaviorCountStock() == ProductFamily::BEHAVIOR_COUNT_STOCK_BY_MEASURE) {
                        $byWeight = true ;
                }

                return $product->getAvailableQuantityInherited() - $this->getQuantityOrderByProduct($orderShop, $product, $byWeight) ;
        }


}