In sales_order_place_before event i am loading all order collection which used po_number as the payment method . From the collection I am getting customer id after loading order data using parent id in a for each loop . Using customer id I am using a helper to get a salesforce id which is in a custom table . and once I get all , I am checking the customer ids are same or saleseforce ids are same i am throwing a throw new CouldNotSaveException and returning false . All these conditions are working except the return false part . It is not preventing to place order, instead order is getting placed . Is there any other way which I can achieve this ? Please help . My events.xml is inside etc/webapi_rest folder. I even tried placing it directly inside etc which also did not help.

Here is my code :


namespace Ecs\UniquePo\Observer;

use \Magento\Framework\Event\Observer;
use \Magento\Framework\Event\ObserverInterface;
use Magento\Framework\App\Config\ScopeConfigInterface;
use Magento\Store\Model\ScopeInterface;
use Magento\Framework\Exception\CouldNotSaveException;
use \Ecs\SalesForceOverride\Helper\SalesforceHelper;

class UniquePo implements ObserverInterface
    private $_postData;
    private $_messageManager;
    private $_responseFactory;
    private $_url;
    protected $_customerSession;
    protected $_emailHelper;
    protected $_request;
    protected $salesforceHelper;
    protected $paymentCollectionFactory;
    protected $_order;

    public function __construct(
        \Magento\Framework\App\RequestInterface $request,
        \Magento\Framework\Message\ManagerInterface $messageManager,
        \Magento\Framework\App\ResponseFactory $responseFactory,
        \Magento\Framework\UrlInterface $url,
        ScopeConfigInterface $scopeConfig,
        \Magento\Customer\Model\Session $customerSession,
      \Magento\Customer\Model\CustomerFactory $customerFactory,
      \Magento\Sales\Model\ResourceModel\Order\Payment\CollectionFactory $paymentCollectionFactory,
      \Magento\Sales\Model\OrderFactory $_order,
      SalesforceHelper $salesforceHelper

        $this->_request = $request;
        $this->_postData = $this->_request->getPostValue();
        $this->_customerSession = $customerSession;
        $this->_messageManager = $messageManager;
        $this->_responseFactory = $responseFactory;
        $this->_url = $url;
        $this->scopeConfig = $scopeConfig;
    $this->_customerFactory = $customerFactory;
    $this->paymentCollectionFactory = $paymentCollectionFactory;
    $this->_order = $_order;
    $this->salesforceHelper = $salesforceHelper;


    public function execute(Observer $observer)

         //$method_instance = $observer->getEvent()->getMethodInstance();

        $customerData = $this->_customerSession->getCustomer();
      $customerId = $customerData->getId();
        $paymentData = json_decode(file_get_contents('php://input'), true);
        $type= 'Account';
         $salesforceid = $this->salesforceHelper->getSalesforceId($customerId, $type);
        $orderCollecion = $this->paymentCollectionFactory->create()->addFieldToSelect('*');    
        $orderCollecion->addAttributeToFilter('po_number', ['eq'=>$poNumber]); 
        foreach ($orderCollecion as $parentId) {
            $order_Id =  $parentId->getParentId();
                $order = $this->_order->create()->load($order_Id);  
                $cid =  $order->getCustomerId();

                    throw new CouldNotSaveException(__('This PO Number is used already.'));
                    return false;
                 $salesforcecid = $this->salesforceHelper->getSalesforceId($cid, $type);
                if(isset($salesforcecid) == isset($salesforceid)){
                    throw new CouldNotSaveException(__('This PO Number is used already.'));
                    return false;
            } catch (\Exception $e) {
                echo $e->getMessage();




1 Answer 1


You can use sales_model_service_quote_submit_before event. I have tried example following way:


<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Event/etc/events.xsd">
    <event name="sales_model_service_quote_submit_before">
        <observer name="sr_sales_model_service_quote_submit_before" instance="SR\StackExchange\Observer\QuoteSubmitBefore" />


namespace SR\StackExchange\Observer;

use Magento\Framework\Event\ObserverInterface;
use Magento\Framework\Event\Observer;
use Magento\Framework\Exception\PaymentException;

class QuoteSubmitBefore implements ObserverInterface
    public function execute(Observer $observer)
        throw new PaymentException(__('This PO Number is used already.'));
  • its not coming to my custom observer
    – Melvin
    Commented Oct 17, 2018 at 20:09
  • Did you check using sales_model_service_quote_submit_before? I have tested it's working great.
    – Sohel Rana
    Commented Oct 18, 2018 at 4:33
  • no need of return or exit ?how can i stop placing the order
    – Melvin
    Commented Oct 18, 2018 at 8:33
  • 1
    Just throw an exception, that's it. System will take care others. You can check using my example without adding your logic.
    – Sohel Rana
    Commented Oct 18, 2018 at 9:45
  • this is working as expected now but not when admin is trying to order place from dashboard
    – Melvin
    Commented Oct 18, 2018 at 11:40

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.