Join single item from related table based on min o

2019-09-07 00:21发布

I have an Item model which has the following associations:

public $hasOne = array(
    'Project' => array(
        'className' => 'Project',
        'foreignKey' => 'item_id'
    )
);
public $hasMany = array(
    'ItemPic' => array(
        'className' => 'ItemPic',
        'foreignKey' => 'item_id',
        'dependent' => false
    )
);

I am wanting custom data for different views of Item. It seems like CakePHP automatically includes Project data (maybe because it is hasOne?) and does not include the ItemPic data. In the index I really don't even want the Project data... however, I do want the ItemPic data. For each Item record pulled, I want a single ItemPic record joined to it. This ItemPic should be basically ItemPic.item_id = Item.id and ORDER BY ItemPic.rank LIMIT 1.

The purpose of this is basically so that in the index I can show a list of Items and a picture associated with each item. I would like all of the images along with the Project data in the view for a single Item, but not in the list/index.

I was told I could use containable like this:

// In the model
public $actsAs = array('Containable');

// In the controller
$this->paginate = array(
    'conditions' => $conditions,
    'contain' => array(
        'ItemPic' => array(
            'fields' => array('file_name'),
            'order' => 'rank',
            'limit' => 1
        )
    )
);

The above actually works how I want... however, I was also told that doing this would cause an extra query to be ran for every single Item... which I feel I should avoid.

I tried doing this, but I get duplicate data and it doesn't attach any ItemPic data:

    $this->paginate = array(
            'conditions' => $conditions,
            'joins' =>  array(
                    array(
                            'table' => 'item_pics',
                            'alias' => 'ItemPic',
                            'type' => 'LEFT',
                            'conditions' => array(
                                    'ItemPic.item_id = Item.id'
                            ),
                            'order' => 'rank ASC',
                            'limit' => 1
                    )

            )
    );
    $paginated = $this->Paginator->paginate();

1条回答
叛逆
2楼-- · 2019-09-07 00:52

Can you please try this:

$this->paginate = array(
        'conditions' => $conditions,
        'joins' =>  array(
                array(
                        'table' => 'item_pics',
                        'alias' => 'ItemPic',
                        'type' => 'LEFT',
                        'conditions' => array(
                                'ItemPic.item_id = Item.id'
                        ),
                        'order' => 'rank ASC',
                        'limit' => 1
                )

        ),
    'fields' => array('Item.*','Project.*','ItemPic.*') 
    );

In the fileds section you may or may not assign "Item" , "Project" according to your requirment.

Thanks

查看更多
登录 后发表回答