how can I get the value of a custom attribute from an order item by SQL?
I don't want to use the collection.
Here is my try:
$this->getSelect()->reset()
->from(
array('order_items' => $this->getTable('sales/order_item')),
array(
'ordered_qty' => 'SUM(order_items.qty_ordered)',
'order_items_name' => 'order_items.name',
'price' => 'order_items.price',
'cost' => 'order_items.base_cost',
'vendor' => 'attrval.value',
'total_price' => '(order_items.qty_ordered * order_items.price)',
'total_profit' => '(order_items.qty_ordered * order_items.price) - (order_items.qty_ordered * order_items.base_cost)',
'sku' => 'order_items.sku'
))
->joinLeft(array('p' => 'catalog_product_entity'), 'order_items.product_id = p.entity_id')
->joinLeft(array('eav' => 'eav_attribute'), 'p.entity_type_id = eav.entity_type_id')
->joinLeft(array('attr' =>'eav_attribute_option'), 'attr.attribute_id = eav.attribute_id')
->joinLeft(array('attrval' =>'eav_attribute_option_value'), 'attrval.option_id = attr.option_id')
->where("eav.attribute_code='vendor'")
->where("order_items.created_at BETWEEN '".$from."' AND '".$to."'")
->where('parent_item_id IS NULL')
->group('order_items.product_id')
->having('SUM(order_items.qty_ordered) > ?', 0)
->order(
array(
'SUM(order_items.qty_ordered) DESC'
));
In SQL it is:
SELECT SUM(order_items.qty_ordered) AS `ordered_qty`, `order_items`.`name` AS `order_items_name`, `order_items`.`price`, `order_items`.`base_cost` AS `cost`, `attrval`.`value` AS `vendor`, (order_items.qty_ordered * order_items.price) AS `total_price`, (order_items.qty_ordered * order_items.price) - (order_items.qty_ordered * order_items.base_cost) AS `total_profit`, `order_items`.`sku`, `p`.*, `eav`.*, `attr`.*, `attrval`.* FROM `sales_flat_order_item` AS `order_items` LEFT JOIN `catalog_product_entity` AS `p` ON order_items.product_id = p.entity_id LEFT JOIN `eav_attribute` AS `eav` ON p.entity_type_id = eav.entity_type_id LEFT JOIN `eav_attribute_option` AS `attr` ON attr.attribute_id = eav.attribute_id LEFT JOIN `eav_attribute_option_value` AS `attrval` ON attrval.option_id = attr.option_id WHERE (eav.attribute_code='vendor') AND (order_items.created_at BETWEEN '2014-04-30 22:00:00' AND '2014-05-31 21:59:59') AND (parent_item_id IS NULL) GROUP BY `order_items`.`product_id` HAVING (SUM(order_items.qty_ordered) > 0) ORDER BY SUM(order_items.qty_ordered) DESCSELECT SUM(order_items.qty_ordered) AS `ordered_qty`, `order_items`.`name` AS `order_items_name`, `order_items`.`price`, `order_items`.`base_cost` AS `cost`, `attrval`.`value` AS `vendor`, (order_items.qty_ordered * order_items.price) AS `total_price`, (order_items.qty_ordered * order_items.price) - (order_items.qty_ordered * order_items.base_cost) AS `total_profit`, `order_items`.`sku`, `p`.*, `eav`.*, `attr`.*, `attrval`.* FROM `sales_flat_order_item` AS `order_items` LEFT JOIN `catalog_product_entity` AS `p` ON order_items.product_id = p.entity_id LEFT JOIN `eav_attribute` AS `eav` ON p.entity_type_id = eav.entity_type_id LEFT JOIN `eav_attribute_option` AS `attr` ON attr.attribute_id = eav.attribute_id LEFT JOIN `eav_attribute_option_value` AS `attrval` ON attrval.option_id = attr.option_id WHERE (eav.attribute_code='vendor') AND (order_items.created_at BETWEEN '2014-04-30 22:00:00' AND '2014-05-31 21:59:59') AND (parent_item_id IS NULL) GROUP BY `order_items`.`product_id` HAVING (SUM(order_items.qty_ordered) > 0) ORDER BY SUM(order_items.qty_ordered) DESC
With this code I get always the same value for my attribute 'vendor'.
Furthermore the order_qty sum is wrong. If I delete the following lines the sum is correct:
'vendor' => 'attrval.value',
->joinLeft(array('p' => 'catalog_product_entity'), 'order_items.product_id = p.entity_id')
->joinLeft(array('eav' => 'eav_attribute'), 'p.entity_type_id = eav.entity_type_id')
->joinLeft(array('attr' =>'eav_attribute_option'), 'attr.attribute_id = eav.attribute_id')
->joinLeft(array('attrval' =>'eav_attribute_option_value'), 'attrval.option_id = attr.option_id')
->where("eav.attribute_code='vendor'")
EDIT:
I changed the code on the top to this:
$this->_reset()
->addAttributeToSelect('*')
->addOrderedQty($from, $to)
->setOrder('ordered_qty', self::SORT_ORDER_DESC);
Now I get the correct values.
But how can I calculate the other columns (e.g. 'total_profit' => '(order_items.qty_ordered * order_items.price) – (order_items.qty_ordered * order_items.base_cost)')?
Best Answer
I have solved it by changing the addOrderedQty() function: