Question

I'm using the following code to remember shopping carts per session. The code works just fine, but the problem is that the cart is not emptied on checkout complete, but shows the contents of the completed order. So the session needs to be cleared on checkout completion so that a new empty order will be created. How do I accomplish this?

function mymodule_commerce_cart_order_id($uid = 0) {    
  $key = $uid . '-' . session_id(); 
  $carts = variable_get('mymodule_carts', array());
  if ( isset($carts[$key]) ) {
    return intval($carts[$key]);
  } else {
    // create a new cart for this session
    $order = commerce_cart_order_new($uid);
    $order->data['last_cart_refresh'] = REQUEST_TIME;
    $order_id = intval($order->order_id);

    // save the new order id to the module settings cache
    $carts[$key] = $order_id;
    variable_set('mymodule_carts', $carts);

    return $order_id;
    }
}
Was it helpful?

Solution 2

I took some ideas form the commerce_cart_order_id() function and changed the code, seems to work like I want it to now:

function mymodule_commerce_cart_order_id($uid = 0) {

 $status_ids = array_keys(commerce_order_statuses(array('cart' => TRUE)));

 // If a customer uid was specified...
 if ($uid) {
   // Look for the user's most recent shopping cart order, although they
   // should never really have more than one.
   $cart_order_ids[$uid] = db_query('SELECT order_id FROM {commerce_order} WHERE uid = :uid AND status IN (:status_ids) ORDER BY order_id DESC', array(':uid' => $uid, ':status_ids' => $status_ids))->fetchField();
 } else {
   // Otherwise look for a shopping cart order ID in the session.
   if (commerce_cart_order_session_exists()) {
     // We can't trust a user's IP address to remain the same, especially since
     // it may be derived from a proxy server and not the actual client. As of
     // Commerce 1.4, this query no longer restricts order IDs based on IP
     // address, instead trusting Drupal to prevent session hijacking.
     $cart_order_ids[$uid] = db_query('SELECT order_id FROM {commerce_order} WHERE order_id IN (:order_ids) AND uid = 0 AND status IN (:status_ids) ORDER BY order_id DESC', array(':order_ids' => commerce_cart_order_session_order_ids(), ':status_ids' => $status_ids))->fetchField();
   }
   else {
     $cart_order_ids[$uid] = FALSE;
   }
 }

 if($cart_order_ids[$uid]) {
   return $cart_order_ids[$uid];
 } else {
     // create a new cart for this session
     $order = commerce_cart_order_new($uid);
     $order->data['last_cart_refresh'] = REQUEST_TIME;
     $order_id = intval($order->order_id);

     return $order_id;
  }
}

OTHER TIPS

I figured out a solution, but I'm not sure if it's the best solution yet. I modified the code so that it creates a new order if the $uid of the order doesn't match and order is placed.

function mymodule_commerce_cart_order_id($uid = 0) {
   $key = $uid . '-' . session_id();

   $carts = variable_get('mymodule_carts', array());
   if ( isset($carts[$key]) ) {
     $order = commerce_order_load(intval($carts[$key]));
   }

   if ( isset($order) && $uid == $order->uid && $order->placed == '0') {
      return intval($carts[$key]);
   } else {
       // create a new cart for this session
       $order = commerce_cart_order_new($uid);
       $order->data['last_cart_refresh'] = REQUEST_TIME;
       $order_id = intval($order->order_id);

       // save the new order id to the module settings cache
       $carts[$key] = $order_id;
       variable_set('mymodule_carts', $carts);

       return $order_id;
   }
 }
Licensed under: CC-BY-SA with attribution
Not affiliated with drupal.stackexchange
scroll top