<?php

namespace KupShop\ProductSetsBundle\Tests;

use KupShop\DevelopmentBundle\Util\Tests\CartTestTrait;

class OrderCreateListenerTest extends \DatabaseTestCase
{
    use CartTestTrait;

    public function testOrderInsertSplitSet()
    {
        $item = [
            'id_product' => 325,
            'note' => [
                'sets' => [
                    1 => [
                        'id_product' => 2,
                        'id_variation' => 10,
                    ],
                    2 => [
                        'id_product' => 4,
                        'id_variation' => null,
                    ],
                ],
            ],
            'pieces' => 1,
        ];

        $user = \User::createFromId(1);
        $user->activateUser();

        $this->createCart();
        $cart = $this->cart;
        $cart->createFromDB();

        $cart->addItem($item);
        $cart->setDeliveryAndPayment(3, 3);

        $cart->save();
        $cart->load();
        $order = $cart->submitOrder();

        $orderObj = new \Order();
        $orderObj->createFromDB($order->id);
        $orderObj->fetchItems();

        /*
            setový produkt - 5000
            první produkt - základní cena - 5000 - 66,6666666%
            druhý produkt - základní cena - 2500 - 33,3333333%

            první setový produkt - 3333,33333
            druhý setový produkt - 1666.66666
        */
        $item = reset($orderObj->items);
        $this->assertEquals($item['id_product'], 2);
        $this->assertEquals($item['id_variation'], 10);
        $this->assertEquals(3333.33, $item['piece_price']['value_with_vat']->asFloat());

        $item = end($orderObj->items);
        $this->assertEquals($item['id_product'], 4);
        $this->assertEquals($item['id_variation'], null);
        $this->assertEquals(1666.67, $item['piece_price']['value_with_vat']->asFloat());
        $this->assertEquals(count($orderObj->items), 2);
    }

    public function testOrderInsertSplitDoubleSet()
    {
        $item = [
            'id_product' => 325,
            'note' => [
                'sets' => [
                    1 => [
                        'id_product' => 2,
                        'id_variation' => 10,
                    ],
                    2 => [
                        'id_product' => 4,
                        'id_variation' => null,
                    ],
                ],
            ],
            'pieces' => 2,
        ];

        $user = \User::createFromId(1);
        $user->activateUser();

        $this->createCart();
        $cart = $this->cart;
        $cart->createFromDB();

        $cart->addItem($item);
        $cart->setDeliveryAndPayment(3, 3);

        $cart->save();
        $cart->load();
        $order = $cart->submitOrder();

        $orderObj = new \Order();
        $orderObj->createFromDB($order->id);
        $orderObj->fetchItems();

        /*
            setový produkt - 5000
            první produkt - základní cena - 5000 - 66,6666666%
            druhý produkt - základní cena - 2500 - 33,3333333%

            první setový produkt - 3333,33333
            druhý setový produkt - 1666.66666
        */
        $item = reset($orderObj->items);
        $this->assertEquals($item['id_product'], 2);
        $this->assertEquals($item['pieces'], 2);
        $this->assertEquals($item['id_variation'], 10);
        $this->assertEquals(3333.33, $item['piece_price']['value_with_vat']->asFloat());
        $this->assertEquals(6666.67, $item['total_price']['value_with_vat']->asFloat());

        $item = end($orderObj->items);
        $this->assertEquals($item['id_product'], 4);
        $this->assertEquals($item['pieces'], 2);
        $this->assertEquals($item['id_variation'], null);
        $this->assertEquals(1666.67, $item['piece_price']['value_with_vat']->asFloat());
        $this->assertEquals(3333.33, $item['total_price']['value_with_vat']->asFloat());

        $this->assertEquals(count($orderObj->items), 2);
    }

    public function testGiftInSetItem()
    {
        $this->removeModule('products_sets', 'calculate_price');
        $dbcfg = \Settings::getDefault();
        $dbcfg['products_sets'] = ['split' => 'price_default'];
        $dbcfg->saveToDB();

        $item = [
            'id_product' => 325,
            'note' => [
                'sets' => [
                    1 => [
                        'id_product' => 2,
                        'id_variation' => 10,
                    ],
                    2 => [
                        'id_product' => 5,
                        'id_variation' => null,
                    ],
                ],
            ],
            'pieces' => 2,
        ];

        $user = \User::createFromId(1);
        $user->activateUser();

        $this->createCart();
        $cart = $this->cart;
        $cart->createFromDB();

        $cart->addItem($item);
        $cart->setDeliveryAndPayment(3, 3);

        $cart->save();
        $cart->load();
        $order = $cart->submitOrder();

        $orderObj = new \Order();
        $orderObj->createFromDB($order->id);

        /*
            setový produkt - 5000
            první produkt - základní cena - 5000 - 66,6666666%
            druhý produkt - základní cena - 2500 - 33,3333333%

            první setový produkt - 3333,33333
            druhý setový produkt - 1666.66666
        */

        $items = $orderObj->fetchItems();
        $item = array_shift($items);
        $this->assertEquals($item['id_product'], 2);
        $this->assertEquals($item['pieces'], 2);
        $this->assertEquals($item['id_variation'], 10);
        $this->assertEquals(3333.33, $item['piece_price']['value_with_vat']->asFloat());
        $this->assertEquals(6666.67, $item['total_price']['value_with_vat']->asFloat());

        $item = array_shift($items);
        $this->assertEquals($item['id_product'], 5);
        $this->assertEquals($item['pieces'], 2);
        $this->assertEquals($item['id_variation'], null);
        $this->assertEquals(1666.67, $item['piece_price']['value_with_vat']->asFloat());
        $this->assertEquals(3333.33, $item['total_price']['value_with_vat']->asFloat());

        $item = array_shift($items);
        $this->assertEquals($item['id_product'], 6);
        $this->assertEquals($item['pieces'], 2);
        $this->assertEquals($item['id_variation'], null);
        $this->assertEquals(0, $item['piece_price']['value_with_vat']->asFloat());
        $this->assertEquals(0, $item['total_price']['value_with_vat']->asFloat());

        $this->assertEquals(count($orderObj->items), 3);
    }

    public function testSetWithDifferentVats()
    {
        $this->removeModule('products_sets', 'calculate_price');

        $item = [
            'id_product' => 3654,
            'note' => [
                'sets' => [
                    1 => [
                        'id_product' => 82,
                        'id_variation' => null,
                    ],
                    2 => [
                        'id_product' => 1060,
                        'id_variation' => null,
                    ],
                    3 => [
                        'id_product' => 1294,
                        'id_variation' => null,
                    ],
                ],
            ],
            'pieces' => 1,
        ];

        $this->loginUser(1);
        $this->createCart();

        $this->cart->setDeliveryAndPayment(3, 3);
        $this->cart->addItem($item);

        $this->saveCart();
        $orderObj = $this->submitOrder();

        $items = $orderObj->fetchItems();
        $item = array_shift($items);
        $this->assertEquals(6608.74, $item['piece_price']['value_with_vat']->asFloat());

        $item = array_shift($items);
        $this->assertEquals(3560.56, $item['piece_price']['value_with_vat']->asFloat());

        $item = array_shift($items);
        $this->assertEquals(530.71, $item['piece_price']['value_with_vat']->asFloat());

        $this->assertEquals(count($orderObj->items), 3);
    }

    public function testSetWithOriginalProductPricesAndDiscountItem()
    {
        $dbcfg = \Settings::getDefault();
        $dbcfg->saveValue('multisets', [
            'discount_display_type' => 'discountItem',
        ]);
        \Settings::clearCache(true);

        $item = [
            'id_product' => 325,
            'note' => [
                'sets' => [
                    1 => [
                        'id_product' => 2,
                        'id_variation' => 10,
                    ],
                    2 => [
                        'id_product' => 4,
                        'id_variation' => null,
                    ],
                ],
            ],
            'pieces' => 1,
        ];

        $user = \User::createFromId(1);
        $user->activateUser();

        $this->createCart();
        $cart = $this->cart;
        $cart->createFromDB();

        $cart->addItem($item);
        $cart->setDeliveryAndPayment(3, 3);

        $cart->save();
        $cart->load();
        $order = $cart->submitOrder();

        $orderObj = new \Order();
        $orderObj->createFromDB($order->id);
        $orderObj->fetchItems();

        /*
            setový produkt - 5000
            první produkt - základní cena - 5000 - 66,6666666%
            druhý produkt - základní cena - 2500 - 33,3333333%
            základní cena obou produktů - 7500

            první setový produkt - 3333,33333
            druhý setový produkt - 1666.66666
            cena setu - 4999.999
            sleva - 2500
        */
        $item = array_shift($orderObj->items);
        $this->assertEquals(2, $item['id_product']);
        $this->assertEquals(10, $item['id_variation']);
        $this->assertEquals(5000, $item['piece_price']['value_with_vat']->asFloat());

        $item = array_shift($orderObj->items);
        $this->assertEquals(4, $item['id_product']);
        $this->assertEquals(null, $item['id_variation']);
        $this->assertEquals(2500, $item['piece_price']['value_with_vat']->asFloat());

        $item = array_shift($orderObj->items);
        $this->assertEquals(null, $item['id_product']);
        $this->assertEquals(null, $item['id_variation']);
        $this->assertEquals(-2500, $item['piece_price']['value_with_vat']->asFloat());
        $this->assertEquals(0, count($orderObj->items));
    }

    public function getDataSet()
    {
        return $this->getJsonDataSetFromFile();
    }
}
