1

I have modified product review form as popup modal, Now I have passed the form data through Ajax to my overrides controller, but it shows the below error.

{"0":"Source class \"\XXX\YYY\Controller\Index\Result\" for \"XXX\YYY\Controller\Index\ResultFactory\" generation does not exist.","1":"

Please provide me a solution

enter image description here

js file

define(['jquery', 'Magento_Ui/js/modal/modal'], function (jQuery, modal) {
    return function (config) {

        var customFunction = {
            ajaxSubmit: function () {
                var form_data = jQuery("#review-form").serialize();
                alert(form_data);
                var reviewurl = config.url;
                alert(reviewurl);
                jQuery.ajax({
                    url: reviewurl,
                    type: 'POST',

                    data: form_data,
                    success: function (response) {
                        alert("successful");
                    },
                    error: function (response) {
                        alert("failed");
                    }
                });
            },

            options: {
                type: 'popup',
                responsive: true,
                innerScroll: true,
                title: jQuery.mage.__('Product Review'),
                buttons: [{
                        text: jQuery.mage.__('submit'),
                        class: '',
                        click: function () {
                            //Ajax function call

                            customFunction.ajaxSubmit();
                            var close = this;
                            setTimeout(function () {
                                close.closeModal();

                            }, 3000);
                        }
                    }]
            }
        };
        jQuery(".product-reviews-summary").on('click', function () {

            modal(customFunction.options, jQuery('#popup-modal'));
            jQuery("#popup-modal").modal("openModal");

        });
        jQuery(".add-review").on('click', function () {

            modal(customFunction.options, jQuery('#popup-modal'));
            jQuery("#popup-modal").modal("openModal");

        });
        jQuery(".star-popup").on('click', function () {

            modal(customFunction.options, jQuery('#popup-modal'));
            jQuery("#popup-modal").modal("openModal");

        });
    };
});

Controller

namespace XXX\YYY\Controller\Index;

class Index extends \Magento\Review\Controller\Product\Post
{
    public function execute()
    {
        /** @var \Magento\Framework\Controller\Result\Redirect $resultRedirect */
        $resultRedirect = $this->resultFactory->create(ResultFactory::TYPE_REDIRECT);

        if (!$this->formKeyValidator->validate($this->getRequest())) {
            $resultRedirect->setUrl($this->_redirect->getRefererUrl());
            return $resultRedirect;
        }


        $data = $this->reviewSession->getFormData(true);
        print_r($data);

        if ($data) {
            $rating = [];

            if (isset($data['ratings']) && is_array($data['ratings'])) {
                $rating = $data['ratings'];
            }

        } else {
            $data = $this->getRequest()->getPostValue();
            $rating = $this->getRequest()->getParam('ratings', []);
        }
        if (($product = $this->initProduct()) && !empty($data)) {
            /** @var \Magento\Review\Model\Review $review */
            $review = $this->reviewFactory->create()->setData($data);
            $review->unsetData('review_id');

            $validate = $review->validate();
            if ($validate === true) {
                try {
                    $review->setEntityId($review->getEntityIdByCode(Review::ENTITY_PRODUCT_CODE))
                            ->setEntityPkValue($product->getId())
                            ->setStatusId(Review::STATUS_PENDING)
                            ->setCustomerId($this->customerSession->getCustomerId())
                            ->setStoreId($this->storeManager->getStore()->getId())
                            ->setStores([$this->storeManager->getStore()->getId()])
                            ->save();

                    foreach ($rating as $ratingId => $optionId) {
                        $this->ratingFactory->create()
                                ->setRatingId($ratingId)
                                ->setReviewId($review->getId())
                                ->setCustomerId($this->customerSession->getCustomerId())
                                ->addOptionVote($optionId, $product->getId());
                    }

                    $review->aggregate();
                    $this->messageManager->addSuccess(__('You submitted your review for moderation.'));
                } catch (\Exception $e) {
                    $this->reviewSession->setFormData($data);
                    $this->messageManager->addError(__('We can\'t post your review right now.'));
                }
            } else {
                $this->reviewSession->setFormData($data);
                if (is_array($validate)) {
                    foreach ($validate as $errorMessage) {
                        $this->messageManager->addError($errorMessage);
                    }
                } else {
                    $this->messageManager->addError(__('We can\'t post your review right now.'));
                }
            }
        }
        $redirectUrl = $this->reviewSession->getRedirectUrl(true);
        $resultRedirect->setUrl($redirectUrl ?: $this->_redirect->getRedirectUrl());
        return $resultRedirect;
    }

}
3
  • Please have a look in to the below post. It will help you to understand how this can be done, magento.stackexchange.com/questions/158541/…
    – MGento
    Dec 19, 2017 at 6:00
  • Thanks you, But in my scenario, the result is redirected, that causes issue, and here it is a overrided controller
    – Jaisa
    Dec 19, 2017 at 6:15
  • Hi @Jaisa could you please update the full code, I want to show the review form in popup
    – skm
    Mar 21, 2020 at 15:53

1 Answer 1

1

Please remove the alert function alert(reviewurl); from your js file and modify you controller file as follows and try,

namespace XXX\YYY\Controller\Index;
use Magento\Framework\Controller\ResultFactory;
class Index extends \Magento\Review\Controller\Product\Post
{
  public function execute()
  {
    $message = null;
    $status = null;  
    if (!$this->formKeyValidator->validate($this->getRequest())) {
        $message[] = "Invalid form key";
        $status = 'failed';
    }
    else 
    {
         $data = $this->reviewSession->getFormData(true);

         if ($data) {
            $rating = [];
            if (isset($data['ratings']) && is_array($data['ratings'])) {
                $rating = $data['ratings'];
            }
        } else {
            $data = $this->getRequest()->getPostValue();
            $rating = $this->getRequest()->getParam('ratings', []);
        }

        if (($product = $this->initProduct()) && !empty($data)) 
        {
            /** @var \Magento\Review\Model\Review $review */
            $review = $this->reviewFactory->create()->setData($data);
            $review->unsetData('review_id');

            $validate = $review->validate();
            if ($validate === true) {
                try {
                    $review->setEntityId($review->getEntityIdByCode(Review::ENTITY_PRODUCT_CODE))
                            ->setEntityPkValue($product->getId())
                            ->setStatusId(Review::STATUS_PENDING)
                            ->setCustomerId($this->customerSession->getCustomerId())
                            ->setStoreId($this->storeManager->getStore()->getId())
                            ->setStores([$this->storeManager->getStore()->getId()])
                            ->save();

                    foreach ($rating as $ratingId => $optionId) {
                        $this->ratingFactory->create()
                                ->setRatingId($ratingId)
                                ->setReviewId($review->getId())
                                ->setCustomerId($this->customerSession->getCustomerId())
                                ->addOptionVote($optionId, $product->getId());
                    }

                    $review->aggregate();
                    $message[] = __('You submitted your review for moderation.');
                    $status = 'success';
                } catch (\Exception $e) {
                    $this->reviewSession->setFormData($data);
                    $message[] = __('We can\'t post your review right now.');
                    $status = 'failed';
                }
            } else {
                $this->reviewSession->setFormData($data);
                if (is_array($validate)) {
                    foreach ($validate as $errorMessage) {
                        $message[] = $errorMessage;
                    }
                } else {
                    $message[] = __('We can\'t post your review right now.');
                }
                $status = 'failed';
            }
        }
    }

    $result = $this->resultFactory
->create(\Magento\Framework\Controller\ResultFactory::TYPE_JSON)
->setData([
    'messages' => $message,
    'status' => $status,
]);

 return $result;
  }
}
11
  • And it also shows resultfactory is unused statement
    – Jaisa
    Dec 19, 2017 at 7:15
  • It shows also 503 error
    – Jaisa
    Dec 19, 2017 at 9:03
  • check the error log and see whats the error. Also try to inject the result factory
    – MGento
    Dec 19, 2017 at 9:16
  • In error log in shows {"0":"Notice: Undefined variable: message
    – Jaisa
    Dec 19, 2017 at 9:20
  • I have updated the answer. Now make sure your form data is available in the controller and the data is saved. Try to log the activity in your controller. It will help you to debug
    – MGento
    Dec 19, 2017 at 9:24

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.