2010-03-01 5 views
5

ÜBERARBEITETE FRAGE: Wir haben dies auf eine benutzerdefinierte Add-to-Cart-Methode nachverfolgt. Ich habe die Frage komplett überarbeitet.Magento benutzerdefinierte in den Warenkorb Prozess funktioniert nicht

Ich arbeite an einer Website, die Magento ver verwendet. 1.3.2.4 als seine eCommerce-Plattform. Wir haben einen benutzerdefinierten "Zum Einkaufswagen hinzufügen" -Prozess erstellt, der über eine AJAX-Anfrage mehrere Artikel zum Warenkorb hinzufügt. Nach dieser Anfrage wird im Browser eine Nachbearbeitung von viw JavaScript durchgeführt, bevor auf die "Warenkorb anzeigen" Seite umgeleitet wird. 99% der Zeit scheint dieser Prozess in Firefox und Safari korrekt zu funktionieren, aber in IE8 schlägt der Prozess fehl. Wenn Sie einen Artikel in den Warenkorb legen, nachdem er auf die Seite "Ihr Warenkorb" umgeleitet wurde, ist der Warenkorb leer.

Nicht alle Elemente auf der Website werden über diesen AJAX-Prozess hinzugefügt. Dieses Problem tritt nur auf, wenn der Einkaufswagen leer ist, bevor die Artikel über AJAX hinzugefügt werden. Das heißt, wenn ein Element, das über den normalen Magento-Prozess hinzugefügt wird, zu der Katze zuerst hinzugefügt wird, dann sind die AJAX-Anfragen zum Einkaufswagen immer erfolgreich. Blu-Clearing-Cookies und der Versuch, über AJAX hinzuzufügen, werden auf IE8 regelmäßig fehlschlagen.

Server ist ein Apache/PHP Server mit PHP 5.2.9, eAccelerator und Suhosin. Bitte fordern Sie zusätzliche Informationen an und ich werde es Ihnen gerne zur Verfügung stellen. Wir speichern Sitzungen in einer MySQL-Datenbank.

Hier ist der Code für unsere benutzerdefinierte Add-to-Cart-Methode. Dieser Code wird in /app/code/core/Mage/Checkout/controllers/CartController.php befindet:

public function ajaxaddAction() 
{ 
    $result = array('success' => true); 

    try 
    { 
     $session = $this->_getSession(); 
     $cart = $this->_getCart(); 

     $products = json_decode($_POST['products'],true); 

     if(!is_array($products)) 
     { 
      throw new Exception("Products data not sent"); 
     } 

     foreach ($products as $product_data) 
     { 
      $product = $this->_initProduct($product_data['id']); 

      if(!$product) 
       throw new Exception("Product id {$product_data['id']} not found"); 

      $info = array('qty' => $product_data['qty']); 

      if($product_data['options']) 
       $info['options'] = $product_data['options']; 

      $cart->addProduct($product,$info); 
     } 

     $cart->save(); 

     $this->_getSession()->setCartWasUpdated(true); 

     /** 
     * @todo remove wishlist observer processAddToCart 
     */ 
     Mage::dispatchEvent('checkout_cart_add_product_complete', 
      array('product' => $products[0], 'request' => $this->getRequest(), 'response' => $this->getResponse()) 
     ); 

     $cartItems = $cart->getQuote()->getAllItems(); 

     $result['cart'] = array(); 

     foreach($cartItems as $item) 
      $result['cart'][] = json_decode($item->toJson()); 
    } 
    catch (Mage_Core_Exception $e) 
    { 
     if ($this->_getSession()->getUseNotice(true)) { 
      $this->_getSession()->addNotice($e->getMessage()); 
     } else { 
      $messages = array_unique(explode("\n", $e->getMessage())); 
      foreach ($messages as $message) { 
       $this->_getSession()->addError($message); 
      } 
     } 
     $result['success'] = false; 
     $result['exception'] = $e->getMessage(); 
    } 

    catch (Exception $e) { 
     $this->_getSession()->addException($e, $this->__('Can not add item to shopping cart')); 
     $result['success'] = false; 
     $result['exception'] = $e->getMessage(); 
    } 

    header('Content-Type: application/json',true); 

    ob_end_clean(); 

    echo json_encode($result); 

    exit(); 
} 

Bitte antworten Sie nicht mit "den Code an das /app/code/local/ Verzeichnis verschieben". Ich verstehe, dass es ein besserer Ort dafür ist, und werde es in Zukunft dorthin bringen, aber wenn Ihre Antwort das Problem nicht löst, schreiben Sie einfach einen Kommentar. Um eine schnellere Antwort zu erhalten, starte ich ein Bounty und möchte gute Antworten auf dieses spezielle Problem, nicht nur Tipps für bessere Möglichkeiten, diesen Code zu integrieren.

Wenn es irgendwelche Informationen gibt, die ich zur Verfügung stellen kann, bitte lass es mich wissen. Wir sind unter einem engen Termin ...

+0

verliere ich meine Prämie, auch wenn ich meine eigene Antwort akzeptieren. Und meine eigene Antwort beantwortet die Frage nicht vollständig. Will niemand 550 Rep-Punkte? ;-) – Josh

+0

@Josh, Wenn du die Hälfte deines Kopfgelds zurückhaben willst, upvote es jemandes Antwort, akzeptiere nichts, wenn diese Antwort +2 Upvotes bekommt, und wenn du nichts akzeptierst, wirst du und er teilen Kopfgeld halb/halb, wenn das Kopfgeld endet. http://stackoverflow.com/faq – YOU

+0

@ S.Mark: Nun, ich möchte eine Antwort mehr als meine Kopfgeld Punkte. Aber selbst wenn ich das tat, was du sagst, bekomme ich nicht die Hälfte zurück. Aus den FAQ: In jedem Fall werden Sie immer die Reputation aufgeben, die in der Kopfgeldausgabe angegeben ist. Wenn Sie also eine Kopfgeldprämie starten, achten Sie darauf, die beste Antwort zu erhalten und zu akzeptieren! – Josh

Antwort

4

Ich habe über 10 Stunden damit verbracht. Für den Moment glaube ich, ich habe eine Teillösung. Aber ich bin mir nicht sicher, warum diese Lösung funktioniert ...

Es scheint, dass Magento eine Umleitung erfordert, um den Add-to-Cart-Prozess abzuschließen. Also statt

header('Content-Type: application/json',true); 
ob_end_clean(); 
echo json_encode($result); 
exit(); 

Ich speichere meine JSON in der Sitzung und Umleitung auf einen neuen Wagen Aktion:

$this->_getSession()->setCartJsonResult(json_encode($result)); 
$this->_redirect('checkout/cart/postajaxadd'); 

Diese Aktion dann Dumps die JSON-Daten

public function postajaxaddAction() 
{ 
    $session = $this->_getSession(); 

    header('Content-Type: application/json',true); 
    ob_end_clean(); 
    echo $this->_getSession()->getCartJsonResult(); 
    exit(); 
} 

Diese immer noch nicht manchmal; Allerdings erhält mein JavaScript-Code jetzt nicht die erwarteten JSON-Daten und kann die Anfrage wiederholen. Die zweite Anfrage ist häufiger erfolgreich als die erste ... Es gibt jedoch immer noch Fälle, in denen die AJAX-Anfragen fehlschlagen, egal was passiert.

+0

Wie wäre es mit 'text/plain' anstelle von' application/json', ich glaube, dass einige Browser diesen Inhaltstyp nicht kennen. – YOU

+0

Ich benutze Prototyp und es erwartet Anwendung/JSON ... Auch dies hat keinen Einfluss darauf, ob der Artikel in den Warenkorb hinzugefügt wird. Trotzdem danke! – Josh

1

Wir haben Probleme beim Hinzufügen von Dingen in den Warenkorb, wenn Sitzungsspeicher abläuft und neue Sitzungen nicht erstellt werden können. Wenn Sie Sitzungen auf Festplatte oder in Memcache speichern, überprüfen Sie, ob Sie genügend Speicherplatz zugewiesen haben.

+0

Danke für den Rat. Das ist ein guter Punkt. Ich speichere Sitzungen in der Datenbank, und der Platz ist in Ordnung. – Josh

3

Nicht sicher, ob dies die Probleme verursacht, auf die Sie stoßen, aber eine bessere Möglichkeit, eine JSON-Antwort auszuführen, wäre, den vorhandenen "Magento/Zend-Weg" dafür zu verwenden.

Statt:

header('Content-Type: application/json',true); 

ob_end_clean(); 

echo json_encode($result); 

exit(); 

Verwendung:

$this->getResponse()->setHeader('Content-Type', 'application/json', true)->setBody(json_encode($result)); 
+0

Schön. Das hat das Problem nicht gelöst, aber es ist ein besserer Weg, es zu handhaben als mein Weg. Danke vielmals! – Josh

+0

Ich habe diesen Code implementiert - es ist viel klarer, aber das Problem besteht immer noch. – Josh

Verwandte Themen