Artikel (Mage_Sales_Model_Order) mit der gleichen ID "X" existiert bereits

12

Nach dem Erstellen einer Sendung im Administrationsbereich von Magento wird im var/reportOrdner (nach einer Standard-Absturzseite von Magento) beim Anzeigen der Bestellgitterseite für Administratoren der folgende Fehler angezeigt :

Item (Mage_Sales_Model_Order) with the same id "1234" already exist

Ich kann diesen Fehler beseitigen, indem ich eine DISTINCT-Klausel zum varien-Objektselektor in app/code/core/Mage/Eav/Model/Entity/Collection/Abstact.phpZeile 662 hinzufüge. Ich möchte dies jedoch aus verschiedenen Gründen (tödlich langsame Abfragen, Bearbeiten von Kerndateien usw.) nicht tun.

Was ist der beste Weg, um dies zu lösen und gleichzeitig die Datenintegrität zu gewährleisten? Soll ich die Bestellung löschen? Ich würde mich über konstruktive Beiträge freuen, insbesondere darüber, was diesen Konflikt überhaupt auslösen würde. Vielen Dank.

- bearbeiten -

Hier ist der vollständige Stack-Trace, um meine Dummheit zu verdeutlichen:

a:5:{i:0;s:67:"Item (Mage_Sales_Model_Order) with the same id "1234" already exist";i:1;s:4829:"#0 lib/Varien/Data/Collection/Db.php(576): Varien_Data_Collection->addItem(Object(Mage_Sales_Model_Order))
#1 app/code/core/Mage/Adminhtml/Block/Widget/Grid.php(533): Varien_Data_Collection_Db->load()
#2 app/code/core/Mage/Adminhtml/Block/Sales/Order/Grid.php(61): Mage_Adminhtml_Block_Widget_Grid->_prepareCollection()
#3 app/code/core/Mage/Adminhtml/Block/Widget/Grid.php(626): Mage_Adminhtml_Block_Sales_Order_Grid->_prepareCollection()
#4 app/code/core/Mage/Adminhtml/Block/Widget/Grid.php(632): Mage_Adminhtml_Block_Widget_Grid->_prepareGrid()
#5 app/code/core/Mage/Core/Block/Abstract.php(862): Mage_Adminhtml_Block_Widget_Grid->_beforeToHtml()
#6 app/code/core/Mage/Core/Block/Abstract.php(582): Mage_Core_Block_Abstract->toHtml()
#7 app/code/core/Mage/Core/Block/Abstract.php(526): Mage_Core_Block_Abstract->_getChildHtml('grid', true)
#8 app/code/core/Mage/Adminhtml/Block/Widget/Grid/Container.php(77): Mage_Core_Block_Abstract->getChildHtml('grid')
#9 app/design/adminhtml/default/default/template/widget/grid/container.phtml(36): Mage_Adminhtml_Block_Widget_Grid_Container->getGridHtml()
#10 app/code/core/Mage/Core/Block/Template.php(241): include('/var/www/html/m...')
#11 app/code/core/Mage/Core/Block/Template.php(272): Mage_Core_Block_Template->fetchView('adminhtml/defau...')
#12 app/code/core/Mage/Core/Block/Template.php(286): Mage_Core_Block_Template->renderView()
#13 app/code/core/Mage/Adminhtml/Block/Template.php(81): Mage_Core_Block_Template->_toHtml()
#14 app/code/core/Mage/Adminhtml/Block/Widget/Container.php(308): Mage_Adminhtml_Block_Template->_toHtml()
#15 app/code/core/Mage/Core/Block/Abstract.php(863): Mage_Adminhtml_Block_Widget_Container->_toHtml()
#16 app/code/core/Mage/Core/Block/Text/List.php(43): Mage_Core_Block_Abstract->toHtml()
#17 app/code/core/Mage/Core/Block/Abstract.php(863): Mage_Core_Block_Text_List->_toHtml()
#18 app/code/core/Mage/Core/Block/Abstract.php(582): Mage_Core_Block_Abstract->toHtml()
#19 app/code/core/Mage/Core/Block/Abstract.php(526): Mage_Core_Block_Abstract->_getChildHtml('content', true)
#20 app/design/adminhtml/default/default/template/page.phtml(74): Mage_Core_Block_Abstract->getChildHtml('content')
#21 app/code/core/Mage/Core/Block/Template.php(241): include('/var/www/html/m...')
#22 app/code/core/Mage/Core/Block/Template.php(272): Mage_Core_Block_Template->fetchView('adminhtml/defau...')
#23 app/code/core/Mage/Core/Block/Template.php(286): Mage_Core_Block_Template->renderView()
#24 app/code/core/Mage/Adminhtml/Block/Template.php(81): Mage_Core_Block_Template->_toHtml()
#25 app/code/core/Mage/Core/Block/Abstract.php(863): Mage_Adminhtml_Block_Template->_toHtml()
#26 app/code/core/Mage/Core/Model/Layout.php(555): Mage_Core_Block_Abstract->toHtml()
#27 app/code/core/Mage/Core/Controller/Varien/Action.php(390): Mage_Core_Model_Layout->getOutput()
#28 app/code/core/Mage/Adminhtml/controllers/Sales/OrderController.php(95): Mage_Core_Controller_Varien_Action->renderLayout()
#29 app/code/core/Mage/Core/Controller/Varien/Action.php(419): Mage_Adminhtml_Sales_OrderController->indexAction()
#30 app/code/core/Mage/Core/Controller/Varien/Router/Standard.php(250): Mage_Core_Controller_Varien_Action->dispatch('index')
#31 app/code/core/Mage/Core/Controller/Varien/Front.php(176): Mage_Core_Controller_Varien_Router_Standard->match(Object(Mage_Core_Controller_Request_Http))
#32 app/code/core/Mage/Core/Model/App.php(354): Mage_Core_Controller_Varien_Front->dispatch()
#33 app/Mage.php(683): Mage_Core_Model_App->run(Array)
#34 index.php(71): Mage::run('base', 'website')
#35 {main}";s:3:"url";s:72:"/index.php/admin/sales_order/index/key/0b7375aca52608483edc0cf879bd4361/";s:11:"script_name";s:10:"/index.php";s:4:"skin";s:5:"admin";}
Jongosi
quelle
8
FWIW Ich hasse diesen blöden Fehler und habe mehr Zeit darauf verwendet, ihn zu debuggen, als mir lieb ist.
Philwinkle
Können Sie Ihre Sammlungsabfrage oder Ihren PHP-Code angeben?
Sukeshini

Antworten:

10

Sie haben der Auflistung etwas hinzugefügt, wodurch dem Abfrageergebnis Duplikate hinzugefügt werden.

Was magento mit dem Abfrageergebnis macht, ist, aus jeder Zeile ein Objekt zu generieren und diese Elemente dann der Sammlung hinzuzufügen. Wenn das Element bereits vorhanden ist, wird dieser Fehler ausgelöst.

Lösung: Unabhängig davon, welchen Join Sie hinzugefügt haben, prüfen Sie, ob Ihr Ergebnis eindeutig ist.

Wenn Sie neben den Feldern von weitere Felder hinzugefügt haben sales_flat_order, können sich diese Felder voneinander unterscheiden. Daher werden sie mit dem Symbol für die Notiz gefiltert DISTINCT.

Fabian Blechschmidt
quelle
6

Ich füge eine Antwort hinzu, da ich noch keinen Kommentar hinzufügen konnte. Ich bin mit @fabian einverstanden. Ich rate jedoch von der Verwendung von DISTINCTund ab GROUP BY. Normalerweise können Sie Ihren Join nach einem bestimmten Ergebnis filtern, wenn Sie richtig planen.

Zum Beispiel (ich weiß, dass dies ein triviales Beispiel ist):

Wenn Sie eine Bestellung über abholen sales/flat_orderund sich der Adresse des Kunden anschließen, werden zwei Datensätze gespeichert, eine Rechnungsadresse und eine Lieferadresse . Um dieses Problem zu beheben, können Sie angeben, welchem ​​Adresstyp sie beitreten möchten.

Das klingt ähnlich wie in Ihrer Situation, außer in diesem Szenario.

Asche
quelle
3

Wir haben auch ein Problem in unserem System. Wir haben das Problem analysiert und meinen gefunden Grid.php(Beispiel: /namespace/modulename/Block/Adminhtml/Sales/Order/Grid.php)

Wir haben eine _prepareCollection()Funktion in der Grid.phpDatei gefunden.

Fehlercodierungen sind:

//Error coding
$collection->join(array('payment' => 'sales/order_payment'), 'main_table.entity_id = parent_id', 'method')
            ->getSelect()
            ->where("`payment`.`method` like '%paypal%'");

Lösung:

//Solution coding
$collection->join(array('payment' => 'sales/order_payment'), 'main_table.entity_id = parent_id', 'method')
            ->getSelect()
            ->where("`payment`.`method` like '%paypal%'")
            ->group('method');

Wir haben Gebrauch ->group('value')in der Filterfunktion. Jetzt funktioniert es gut ... !!!

Sankar_k
quelle
3

Ich weiß, dass dies eine alte Frage ist und sie bereits beantwortet wurde, aber ich möchte meine Antwort hinzufügen, da ich der Meinung bin, dass sie anderen helfen könnte, die sich ähnlichen Problemen gegenübersehen. Ich versuche, die allgemeinen Ursachen für diese Art von Fehler zu erklären.

So starten Sie mit, Mage_Sales_Model_Orderin einer Standard - Installation Magento sollte nie geben einen solchen Fehler. Daher vermute ich, dass dieser Fehler durch eine Erweiterung eines Drittanbieters (Beobachter, Hook-Methode, Umschreiben usw.) oder eine falsche Code-Anpassung verursacht wurde, durch die Daten an erster Stelle beschädigt wurden. Wenn es sich um Kernkomponenten handelt, die "seltsam" wirken, sollte es die distinctLösung nicht einmal geben, da Daten niemals von Anfang an verfälscht worden sein sollten! Korrigieren Sie die Daten lieber zuerst selbst, als den Code zu ändern.

Beim Erstellen eines benutzerdefinierten EAV-Entitätstyps trat ein ähnliches Problem auf und alles funktionierte einwandfrei, bis ich eine der Entitäten bearbeitete. Irgendwie ergab die Bearbeitung einen doppelten Wert für eines der Textattribute der Entität, dh zwei Zeilen in der Textwertetabelle für dasselbe Attribut derselben Entität. Die reine Abfrage nur der custom_entity-Tabelle sah perfekt aus, ohne Duplikate (wie könnte es sein, dass die Primärschlüsselbeschränkung bereits die Integrität sicherstellte), sodass das Problem an einer anderen Stelle lag.

Wie Sie möglicherweise bereits beim Laden der Auflistung erraten haben, wurden aufgrund der zum Abrufen der Zeilen aus der Datenbank verwendeten Joins und der Annahme, dass für dasselbe Attribut einer Entität zwei gleiche Textwerte vorhanden waren, zwei Zeilen mit demselben entity_idWert, aber unterschiedlich abgerufen value_id.

Wenn ein solcher Fehler auftritt, sollten Sie in der Regel den Verdacht haben, dass entweder die Daten in der Datenbank bereits beschädigt wurden oder dass die Verknüpfungen, die in der letzten Abfrage ausgeführt werden, zwei nahezu exakte Zeilen aus der Datenbank abrufen und die eindeutige Kennung der Sammlung duplizieren Artikel.

Hoffe das hilft.

PS: Um herauszufinden, warum der doppelte EAV-Textwert in meinem Fall vorhanden ist, lesen Sie Marius 'Kommentar hier: http://inchoo.net/magento/creating-an-eav-based-models-in-magento/

adjco
quelle
0

Dies ist mein Code hat gut funktioniert, nachdem ich das gleiche Problem bekommen habe:

    $collection = Mage::getResourceModel('sales/order_grid_collection');
    $prefix = Mage::getConfig()->getTablePrefix();  

    $collection->getSelect()->joinleft(array('order'=> $prefix.'sales_flat_order'),'order.entity_id=main_table.entity_id',array('pdeliverydate'));   

    $collection->getSelect()->joinleft(array('address'=> $prefix.'sales_flat_order_address'),'address.parent_id=main_table.entity_id',array('telephone'))->group('entity_id');

    $this->setCollection($collection);
    return parent::_prepareCollection();

Ich habe add -> group ('entity_id'), um das Problem zu lösen.

Peter
quelle
Bereits vor 1 Jahr vorgeschlagen ( magento.stackexchange.com/a/139898/46249 ) ... -1.
Sv3n
-1

Sie müssen versuchen zu überschreiben, Mage_Sales_Model_Resource_Order_Grid_Collection::addItemwas diese Ausnahme auslöst:

<?php
class Fixed_Order_Grid_Collection extends Mage_Sales_Model_Resource_Order_Grid_Collection{

    public function addItem(Varien_Object $item)
    {
        $itemId = $this->_getItemId($item);

        if (!is_null($itemId)) {
            if (isset($this->_items[$itemId])) {
                //throw new Exception('Item ('.get_class($item).') with the same id "'.$item->getId().'" already exist');
            }
            $this->_items[$itemId] = $item;
        } else {
            $this->_addItem($item);
        }
        return $this;
    }
}
class MyCompony_MyExtention_Block_Adminhtml_OrderGrid extends Mage_Adminhtml_Block_Widget_Grid
{
     public function __construct()
    {
        parent::__construct();
        $this->setId('sales_order_grid');
        $this->setUseAjax(true);
        $this->setDefaultSort('created_at');
        $this->setDefaultDir('DESC');
        $this->setSaveParametersInSession(true);
    }
    protected function _getCollectionClass()
    {
        return 'sales/order_grid_collection';
    }

    protected function _prepareCollection()
    {
        $collection = new Fixed_Order_Grid_Collection();
        $select = $collection->getSelect();
        $select->join('sales_flat_order_item AS order_item', 'order_item.order_id=main_table.entity_id','quote_item_id',NULL);
        $select->distinct();
        $this->setCollection($collection);
        return parent::_prepareCollection();
    }
...
Sajjad Shirazy
quelle
1
Dies ist keine Lösung, sondern lediglich eine Möglichkeit, die Fehlermeldung zu beseitigen.
Niels
1
Das Beheben von Fehlern ist nicht gleichbedeutend mit dem Beheben von Fehlern. Fügen Sie die Verknüpfungsabfrage zu Ihrem Erfassungsergebnis hinzu oder gruppieren Sie sie nach einem Feld.
DWils