Magento 2 - sales_order_place_after not returning Order ID
This is an old question but given I have just faced the same problem myself I thought I would give my take on the answer. sales_order_place_after
is triggered before the order is saved to db so at the point your code is running the order entity ID doesn't exist. There are few options to work around this:
You could use sales_order_save_after
which is triggered after the order is actually persisted to db. This will allow you to have access to the order ID. This approach has risks however as it can be triggered again after the order is created. If you only want to run your code only once when the order is first placed, using this observer may have unexpected side effects.
Alternatively rather than using an observer you could create a plugin around Magento\Sales\Api\OrderManagementInterface::place
. This will allow you to do what I suspect you are trying to do with sales_order_place_after
.
As a rough example your modules etc/di.xml
would look something like this:
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
<type name="Magento\Sales\Api\OrderManagementInterface">
<plugin name="my-module-order-service" type="My\Module\Plugin\OrderServicePlugin" sortOrder="5"/>
</type>
</config>
And your plugin class like this:
<?php
namespace My\Module\Plugin;
class OrderServicePlugin
{
public function aroundPlace(\Magento\Sales\Model\Service\OrderService $subject, \Closure $proceed, \Magento\Sales\Api\Data\OrderInterface $order)
{
$return = $proceed($order);
$orderId = $order->getEntityId();
// your custom code
return $return;
}
}
It is better to avoid around plugin unless necessary . Use after plugin or Magento\Sales\Api\OrderManagementInterface::place
etc/di.xml
<?xml version="1.0" ?>
<config>
<type name="Magento\Sales\Api\OrderManagementInterface">
<plugin name="MyOrderPlaceAfterPlugin" type="My\Module\Plugin\Order\PlaceAfterPlugin" sortOrder="99" />
</type>
</config>
My\Module\Plugin\Order\PlaceAfterPlugin.php
//namespace My\Module\Plugin\Order;
class PlaceAfterPlugin {
/**
* @param \Magento\Sales\Api\OrderManagementInterface $orderManagementInterface
* @param \Magento\Sales\Model\Order\Interceptor $order
* @return $order
*/
public function afterPlace(\Magento\Sales\Api\OrderManagementInterface $orderManagementInterface , $order)
{
$orderId = $order->getId();
// do something with order object (Interceptor )
return $order;
}
}
In Magento 2 observer I used this code, you get the order data like this,
use Magento\Framework\Event\ObserverInterface;
class YOUROBSERVERCLASS implements ObserverInterface
{
protected $orderFactory;
public function __construct(\Magento\Quote\Model\QuoteFactory $quoteFactory,
\Magento\Sales\Model\Order $orderFactory)
{
$this->orderFactory = $orderFactory;
}
public function execute(\Magento\Framework\Event\Observer $observer)
{
$orderIds = $observer->getEvent()->getOrderIds();
$lastorderId = $orderIds[0];
$order = $this->orderFactory->load($lastorderId);
}
}