<?php

namespace Autogedal\Extend\Controller\Product;

use Magento\Framework\Controller\Result\Redirect;
use Magento\Framework\Controller\ResultFactory;
use Magediary\ProductQuestion\Model\Question;
use \Magento\Framework\Escaper;
use Magento\Framework\Validator\EmailAddress;

class Post extends \Magediary\ProductQuestion\Controller\Product\Post
{
    protected $escaper;
    protected $emailValidator;

    /**
     * @param \Magento\Framework\App\Action\Context $context
     * @param \Magento\Framework\Registry $coreRegistry
     * @param \Magento\Customer\Model\Session $customerSession
     * @param \Magento\Catalog\Api\CategoryRepositoryInterface $categoryRepository
     * @param \Psr\Log\LoggerInterface $logger
     * @param \Magento\Catalog\Api\ProductRepositoryInterface $productRepository
     * @param \Magediary\ProductQuestion\Model\QuestionFactory $questionFactory
     * @param \Magento\Catalog\Model\Design $catalogDesign
     * @param \Magento\Framework\Session\Generic $questionSession
     * @param \Magediary\ProductQuestion\Helper\Data $helperData
     * @param \Magento\Store\Model\StoreManagerInterface $storeManager
     * @param \Magento\Framework\Data\Form\FormKey\Validator $formKeyValidator
     */
    public function __construct(
        \Magento\Framework\App\Action\Context $context,
        \Magento\Framework\Registry $coreRegistry,
        \Magento\Customer\Model\Session $customerSession,
        \Magento\Catalog\Api\CategoryRepositoryInterface $categoryRepository,
        \Psr\Log\LoggerInterface $logger,
        \Magento\Catalog\Api\ProductRepositoryInterface $productRepository,
        \Magediary\ProductQuestion\Model\QuestionFactory $questionFactory,
        \Magento\Catalog\Model\Design $catalogDesign,
        \Magento\Framework\Session\Generic $questionSession,
        \Magediary\ProductQuestion\Helper\Data $helperData,
        \Magento\Store\Model\StoreManagerInterface $storeManager,
        \Magento\Framework\Data\Form\FormKey\Validator $formKeyValidator,
        Escaper $escaper,
        EmailAddress $emailValidator
    ) {
        $this->escaper = $escaper;
        $this->emailValidator = $emailValidator;
        parent::__construct(
            $context,
            $coreRegistry,
            $customerSession,
            $categoryRepository,
            $logger,
            $productRepository,
            $questionFactory,
            $catalogDesign,
            $questionSession,
            $helperData,
            $storeManager,
            $formKeyValidator
        );
    }

    /**
     * Submit new question action
     *
     * @return Redirect
     * @SuppressWarnings(PHPMD.CyclomaticComplexity)
     * @SuppressWarnings(PHPMD.NPathComplexity)
     */
    public function execute()
    {
        /** @var Redirect $resultRedirect */
        $resultRedirect = $this->resultFactory->create(ResultFactory::TYPE_REDIRECT);
        if (!$this->formKeyValidator->validate($this->getRequest())) {
            $resultRedirect->setUrl($this->_redirect->getRefererUrl());
            return $resultRedirect;
        }

        $data = $this->questionSession->getFormData(true);
        if (!$data) {
            $data = $this->getRequest()->getPostValue();
        }

        $allowedFields = ['form_key', 'nickname', 'email', 'detail'];
        $data = array_intersect_key($data, array_flip($allowedFields));

        $data['detail'] = $this->escaper->escapeHtml(trim($data['detail']));
        $data['nickname'] = $this->escaper->escapeHtml(trim($data['nickname']));

        if(isset($data['email']) && !empty($data['email'])) {
            $email = trim($data['email']);
            if (!$this->emailValidator->isValid($email)) {
                $this->messageManager->addErrorMessage(__('Please enter a valid email address.'));
                $resultRedirect->setUrl($this->_redirect->getRefererUrl());
                return $resultRedirect;
            }
        }
        
            
        if (($product = $this->initProduct()) && !empty($data)) {
            $question = $this->questionFactory->create()->setData($data);
            $question->unsetData('question_id');

            $validate = $question->validate();
            if ($validate === true) {
                try {
                    $type = Question::TYPE_GUEST;
                    if ($this->customerSession->getCustomerId()) {
                        $type = Question::TYPE_CUSTOMER;
                    }

                    $status = Question::STATUS_PENDING;
                    if ($this->_helperData->getConfig('question/question/auto_approval')) {
                        $status = Question::STATUS_APPROVED;
                    }

                    if (!$question->getEmail()) {
                        $question->setEmail($this->customerSession->getCustomer()->getEmail());
                    }

                    $question->setProductId($product->getId())
                        ->setStatus($status)
                        ->setType($type)
                        ->setCustomerId($this->customerSession->getCustomerId())
                        ->setStoreId($this->storeManager->getStore()->getId())
                        ->save();

                    $data['id'] = $question->getId();

                    $this->messageManager->addSuccessMessage(
                        __('Question posted successfully. Will notify you when someone answers your question.')
                    );
                } catch (\Exception $e) {
                    $this->questionSession->setFormData($data);
                    $this->messageManager->addExceptionMessage(
                        $e,
                        __('We can\'t post your question right now.')
                    );
                    $this->_objectManager->get(\Psr\Log\LoggerInterface::class)->critical($e);
                }
            } else {
                $this->questionSession->setFormData($data);
                if (is_array($validate)) {
                    foreach ($validate as $errorMessage) {
                        $this->messageManager->addErrorMessage($errorMessage);
                    }
                } else {
                    $this->messageManager->addErrorMessage(__('We can\'t post your question right now.'));
                }
            }
        }
        $redirectUrl = $this->questionSession->getRedirectUrl(true);
        $resultRedirect->setUrl($redirectUrl ?: $this->_redirect->getRedirectUrl());
        return $resultRedirect;
    }
}
