1

関数 getRooms() でブロックを作成しました。部屋のコレクションを返す必要があります。しかし、検索条件が多いので、他のテーブルで joinLeft クエリを作成する必要があります。

public function getRooms(){

    $rooms = array();

    $productId = $this->getRequest()->getParam('product'); 

    $from = $this->getRequest()->getParam('from');
    $to = $this->getRequest()->getParam('to');

    $fromStamp = strtotime( $from );
    $toStamp = strtotime( $to );

    $rooms = Mage::getModel('reservation/roomtypes')->getCollection();

    $newInventoryTable = $rooms->getTable('reservation/newinventory');

    $datefilters =  array('filter1'=>$fromStamp, 'filter2'=>$toStamp );
    $dateconditions = array( 'filter1' => $cond1, 'filter2' => array('from'=>'ni.date_from','to'=>'ni.date_to') );

    $datecond = "({$fromStamp} >= ni.date_from and {$fromStamp} <= ni.date_to) or ({$toStamp} >= ni.date_from and {$toStamp} <= ni.date_to) OR ni.date_from is NULL";
    $rooms = $rooms
                    ->addFieldToSelect('id')
                    ->addFieldToSelect('room_type')
                    ->addFieldToSelect('room_price_per_night')
                    ->addFieldToSelect('second_night_price')
                    ->addFieldToSelect('room_quantity')
                    ->addFieldToFilter("main_table.entity_id", $productId )
                    ->getSelect()
                    ->where( $datecond )
                    ->joinLeft( array("ni"=>$newInventoryTable), "main_table.id = ni.room_type_id", "SUM(ni.rooms_count)  AS rooms_reserved" )
                    ->group("main_table.id")
                    ->having("((`room_quantity`-`rooms_reserved`) > 0) OR (`rooms_reserved` is NULL) ");



$rooms = $rooms->query();
$rooms = $rooms->FetchAll();
    return $rooms;
}

適切に sql-query を作成しましたが、FetchAll() によって Array() が返されます。低レベルの Zend db API に行ったからです。Varien Collection を取得し、その魔法の getField() 機能を使用します。

つまり、Magento レベルにとどまりたいということです。では、Magento アプローチを使用する演算子を使用して、leftJoin、group を書き換えるにはどうすればよいでしょうか?

4

2 に答える 2

2

このドキュメントを見てみてください: http://www.magentocommerce.com/wiki/1_-_installation_and_configuration/using_collections_in_magento

使うべきではないと思いますaddFieldToSelect()が、addFieldToFilter()

これは結合の例です

$collection = Mage::getModel('module/model_name')->getCollection();
$collection->getSelect()->join( array('table_alias'=>$this->getTable('module/table_name')), 'main_table.foreign_id = table_alias.primary_key', array('table_alias.*'), 'schema_name_if_different');
于 2012-10-17T16:39:14.587 に答える
1

その単純なトリックに陥るのは非常に簡単です。これを行ったときに変数にZend_Db_Selectインスタンスを割り当てたことを除いて、すべてを正しく実行しました。$room

$rooms = $rooms
                ....
                ->getSelect()
                ....

代わりに行うべきだったのは、フィルターをに割り当てることです$selectが、それ自体で操作し$collectionます。ところで、フィルターを適用するためにコレクションをそれ自体に再割り当てする必要はありません。これを行う方法は次のとおりです。

$rooms = Mage::getModel('reservation/roomtypes')->getCollection();

$newInventoryTable = $rooms->getTable('reservation/newinventory');

$datefilters =  array('filter1'=>$fromStamp, 'filter2'=>$toStamp );
$dateconditions = array( 'filter1' => $cond1, 'filter2' => array('from'=>'ni.date_from','to'=>'ni.date_to') );

$datecond = "({$fromStamp} >= ni.date_from and {$fromStamp} <= ni.date_to) or ({$toStamp} >= ni.date_from and {$toStamp} <= ni.date_to) OR ni.date_from is NULL";
$rooms->addFieldToSelect('id')
                ->addFieldToSelect('room_type')
                ->addFieldToSelect('room_price_per_night')
                ->addFieldToSelect('second_night_price')
                ->addFieldToSelect('room_quantity')
                ->addFieldToFilter("main_table.entity_id", $productId );
$rooms->getSelect()
                ->where( $datecond )
                ->joinLeft( array("ni"=>$newInventoryTable), "main_table.id = ni.room_type_id", "SUM(ni.rooms_count)  AS rooms_reserved" )
                ->group("main_table.id")
                ->having("((`room_quantity`-`rooms_reserved`) > 0) OR (`rooms_reserved` is NULL) ");
return $rooms;

load返品する前に収集する必要がない理由をいくつか説明します。コレクションを操作する場合、Magento には遅延読み込みの原則があります。foreach選択フィルターと内部フィルターに関するすべての情報が含まれていますが、ループのように、データを出力する必要があるまさにその場所までクエリを DB にフェッチしません。次に、メソッドloadがトリガーされ、保護されたプロパティ_itemsがオブジェクトで満たされます。Blockこのようにして、フィルターを追加または削除し、オブジェクトまたはテンプレートで選択したオブジェクトを変更することができます。.phtmlこれはもちろん推奨されませんが、最速かつ最も簡単な方法です。

そのため、 foreach ループに挿入して目的の配列のような動作を得るためにqueryorfetchまたはcollection を実行する必要はありません(Iterator インターフェースのおかげです)。load

于 2012-10-17T22:12:02.817 に答える