<?php

namespace backend\controllers;

use /** @noinspection PhpMethodOrClassCallIsNotCaseSensitiveInspection */
    Yii;
use common\models\InventoryItem;
use backend\models\InventoryItemSearch;
use yii\base\Exception;
use yii\db\Query;
use yii\web\Controller;
use yii\web\NotFoundHttpException;
use yii\filters\VerbFilter;
use backend\models\InventoryItemForm;
use common\models\Inventory;
use yii\helpers\Url;
use common\models\Product;
use yii\web\NotAcceptableHttpException;

/**
 * InventoryItemController implements the CRUD actions for InventoryItem model.
 */
class InventoryItemController extends Controller
{
    public function behaviors()
    {
        return [
            'verbs' => [
                'class' => VerbFilter::className(),
                'actions' => [
                    'delete' => ['post'],
                ],
            ],
        ];
    }

    /**
     * Lists all InventoryItem models.
     * @param $id
     * @return mixed
     * @throws NotFoundHttpException
     */
    public function actionIndex($id)
    {
        $inventory = Inventory::findOne($id);

        if (!isset($inventory)) {
            throw new NotFoundHttpException("Leltár nem található");
        }

        $searchModel = new InventoryItemSearch(['inventory' => $inventory]);
        $dataProvider = $searchModel->search(Yii::$app->request->queryParams);

        $productOptions = Product::buildProductAndInventoryGroupList();

        if ($searchModel->output == 'xls') {
            $this->downloadIndexXls($dataProvider);
        } else {
            Url::remember(Url::current(), "inventory-item-index");
        }


        return $this->render('index', [
            'model' => $inventory,
            'searchModel' => $searchModel,
            'dataProvider' => $dataProvider,
            'productOptions' => $productOptions
        ]);
    }


    /**
     * @param $dataProvider
     */
    protected function downloadIndexXls($dataProvider)
    {
        $defs = [['item_created_at', 'Létrehozva'],
            ['item_name', 'Termék/Termék csoport'],
            ['user_username', 'Felhasználó'],
            ['item_count_prev', 'Előző leltár (db)'],
            ['item_count_sold', 'Eladott mennyiség (db)'],
            ['item_count_in', 'Beszerzett mennyiség (db)'],
            ['item_count', 'Leltározott mennyiség (db)'],
            ['item_purchase_price_net', 'Nettó beszerezési ár (Ft)'],
            ['item_net_stock_money', 'Nettó készlet érték (Ft)'],
            ['item_stock_missing_count', 'Különbség (db)'],
            ['item_price_brutto', 'Bruttó eladási ár (Ft)'],
            ['item_stock_missing_money', 'Leltár hiány (Ft)'],
            ['item_count_system', 'Rendszer szerinti mennyiség (db)'],
        ];
        $cols = ['A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P'];

        /** @noinspection PhpUndefinedMethodInspection */
        $models = $dataProvider->getModels();
        /** @noinspection PhpUndefinedClassInspection */
        $objPHPExcel = new \PHPExcel ();

        $sheet = $objPHPExcel->setActiveSheetIndex(0);
        /**
         * Termék azonosító Termék neve Termék szám Termék vonalkód Termék raktáron Termék eladva
         */
        $row = 1;
        $col = 0;
        foreach ($defs as $def) {
            $sheet->setCellValue($cols [$col] . $row, $def [1]);
            $col++;
        }

        foreach ($models as $model) {
            $row++;
            $col = 0;
            foreach ($defs as $def) {
                $sheet->setCellValue($cols [$col] . $row, $model[$def [0]]);
                $col++;
            }
        }

        $styleArray = array(
            'font' => array(
                'bold' => true
            )
        );
        // 'color' => array('rgb' => 'FF0000'),
        // 'size' => 15,
        // 'name' => 'Verdana'


        foreach (range('A', 'N') as $columnID) {
            $sheet->getColumnDimension($columnID)->setAutoSize(true);
            $sheet->getStyle($columnID . '1')->applyFromArray($styleArray);
        }

        $sheet->freezePane( "N2" );

        // Redirect output to a client’s web browser (Excel5)
        header('Content-Type: application/vnd.ms-excel');
        header('Content-Disposition: attachment;filename="leltar.xls"');
        header('Cache-Control: max-age=0');
        // If you're serving to IE 9, then the following may be needed
        header('Cache-Control: max-age=1');
        // If you're serving to IE over SSL, then the following may be needed
        header('Expires: Mon, 26 Jul 1997 05:00:00 GMT'); // Date in the past
        header('Last-Modified: ' . gmdate('D, d M Y H:i:s') . ' GMT'); // always modified
        header('Cache-Control: cache, must-revalidate'); // HTTP/1.1
        header('Pragma: public'); // HTTP/1.0
        /** @noinspection PhpUndefinedClassInspection */
        $objWriter = \PHPExcel_IOFactory::createWriter($objPHPExcel, 'Excel5');
        $objWriter->save('php://output');
        exit ();
    }

    /**
     * Displays a single InventoryItem model.
     * @param integer $id
     * @return mixed
     */
    public function actionView($id)
    {
        return $this->render('view', [
            'model' => $this->findModel($id),
        ]);
    }

    /**
     * Creates a new InventoryItem model.
     * If creation is successful, the browser will be redirected to the 'view' page.
     * @param Integer $id the item id
     * @return mixed
     * @throws \Exception
     */
    public function actionCreate($id)
    {
        $model = new InventoryItemForm([
            'id_inventory' => $id
        ]);

        $model->read();

        if ($model->load(Yii::$app->request->post()) && $model->save()) {
            return $this->redirect(['inventory-item/index', 'id' => $model->inventory->id_inventory]);
        } else {
            return $this->render('create', [
                'model' => $model,
            ]);
        }
    }

    /**
     * Updates an existing InventoryItem model.
     * If update is successful, the browser will be redirected to the 'view' page.
     * @param integer $id
     * @return mixed
     * @throws NotAcceptableHttpException
     * @throws NotFoundHttpException
     */
    public function actionUpdate($id)
    {
        $model = $this->findModel($id);
        $inventory = Inventory::findOne($model->id_inventory);
        if (!$inventory->isOpen()) {
            throw new NotAcceptableHttpException("A leltár elem nem található");
        }
        if ($model->load(Yii::$app->request->post()) && $model->validate()) {
            $model->save(false);
            \Yii::$app->session->setFlash('success', "Mennyiség elmentve: " . $model->productName . ' - ' .$model->count . ' db');
            $next = InventoryItem::findNextItemAlphabetical($model->id_inventory_item);
            if (  isset($_POST['_next'])  && isset($next)){
                return $this->redirect(['inventory-item/update', 'id' => $next]);
            }else{
                return $this->redirect(['index', 'id' => $inventory->id_inventory]);
            }
        } else {
            return $this->render('update', [
                'model' => $model,
                'inventory' => $inventory,
            ]);
        }
    }

    /**
     * @param null $idInventory     the id of the inventory
     * @param  integer $id the inventory item id
     * @return string
     * @throws Exception
     * @throws NotAcceptableHttpException
     */
    public function actionUpdateItem($idInventory = null,$id = null)
    {

        if ( !isset($idInventory ) && !isset($id)){
            \Yii::error("Neither inventory id nor inventory item id");
        }

        if ( isset($id)){
            $model = $this->findModel($id);
            $inventory = Inventory::findOne($model->id_inventory);
        }else{
            $inventory = Inventory::findOne($idInventory);
            $model = new InventoryItem();
        }

        if (!$inventory->isOpen()) {
            throw new NotAcceptableHttpException("A leltár elem nem található");
        }


        if (Yii::$app->request->getIsAjax()) {
            $arr = [
                'id_inventory_item' => $model->id_inventory_item,
                'productName' => $model->productName,
                'count' => $model->count,
                'type' => $model->type
            ];

            return json_encode($arr);
        } else {
            if (Yii::$app->request->isPost && $model->isNewRecord ){
                \Yii::error("Failed to save inventory-item: post , but no item id");
                throw new Exception("Hiba történt mentés közben");
            }

            if ($model->load(Yii::$app->request->post()) && $model->validate()) {


                if ( $model->save(false) ){
                    \Yii::$app->session->setFlash('success', "Mennyiség elmentve: " . $model->productName . ' - ' .$model->count . ' db');
                }else{
                    \Yii::error("Nem sikerült elmenteni a leltár element.");
                    throw new Exception("Nem sikerült elmenteni a leltár element");
                }

                if ( isset($_POST['_next'])){
                    return $this->redirect(['update-item', 'idInventory' => $inventory->id_inventory]);
                }else{
                    return $this->redirect(['index', 'id' => $inventory->id_inventory]);
                }

            }


            $query = new  Query();
            $query->select([
                'product.id_product as product_id_product',
                'product.name as product_name',
                'account.name as account_name',
                'product_category.name as product_category_name',
                'inventory_item.id_inventory_item as inventory_item_id_inventory_item',
            ]);
            $query->from(['product']);

           $query
                ->innerJoin("product_category", "product_category.id_product_category = product.id_product_category")
                ->innerJoin("account", "product.id_account = account.id_account")
                ->innerJoin("inventory_item", "inventory_item.id_product = product.id_product")
                ->andWhere(["inventory_item.id_inventory" => $inventory->id_inventory])->all();
            $productsRaw = $query->all();


            $products = [];
            foreach ($productsRaw as $product ){
                $arr = [];
                $arr['id_inventory_item'] = $product['inventory_item_id_inventory_item'];
                $arr['id_product'] = $product['product_id_product'];
                $arr['name'] =   $product['product_name']   ."( ". $product['account_name'].")";
                $arr['product_name'] = $product['account_name'] ;
                $products[]  = $arr;
            }



            return $this->render("update_item", [
                'model' => $model,
                'inventory' => $inventory,
                'products' => $products
            ]);
        }

    }


    /**
     * Deletes an existing InventoryItem model.
     * If deletion is successful, the browser will be redirected to the 'index' page.
     * @param integer $id
     * @return mixed
     */
    public function actionDelete($id)
    {
        $item = $this->findModel($id);
        $id_inventory = $item->id_inventory;
        $item->delete();

        return $this->redirect(['index', 'id' => $id_inventory]);
    }

    /**
     * Finds the InventoryItem model based on its primary key value.
     * If the model is not found, a 404 HTTP exception will be thrown.
     * @param integer $id
     * @return InventoryItem the loaded model
     * @throws NotFoundHttpException if the model cannot be found
     */
    protected function findModel($id)
    {
        if (($model = InventoryItem::findOne($id)) !== null) {
            return $model;
        } else {
            throw new NotFoundHttpException('The requested page does not exist.');
        }
    }
}
