CakePHP: pagination using search logic in a model

I'm having trouble paginating search results. My setup is as follows.

I have a search form in myapp.com/searches/productswith a view (has a search form) .../app/views/searches/products.ctp. I am using a controller Searchesthat uses a model Productfor this search query. Producthas an action search()with search logic ( $this->find(...)). The search result is displayed below the form in the view.

How do I do something similar to $this->paginate()what usually runs in the controller? In addition, I would like to know that something is wrong with my setup, especially with a view that includes both the form and the search result.

0
source share
2 answers

One way to keep the search logic in the model and still paginate in the controller:

Explanation:

Instead of returning actual results from the model, just return all / all search parameters, then paginate as usual. For some examples, such as this simple below, this may seem redundant, but it leaves room for the addition of many more opportunities find(), such as contain, order, group, joins, conditions... etc. etc. And it remains more in accordance with the mantra "Fat models, skinny controllers."

find() , - , .

:

/* CONTROLLER
*/
$opts = array('paginate' => true, 'limit'=>20);
$paginateOptions = $this->Event->getEvents($opts);
$this->paginate = $paginateOptions;
$data = $this->paginate('Event');

/* MODEL
*/
public function getProducts($opts = null) {

    $params = array();

    //limit
    $params['limit'] = 50; //default
    if(!empty($opts['limit'])) $params['limit'] = $opts['limit'];

    //paginate option
    $paginate = false;
    if(isset($opts['paginate'])) {
        if($opts['paginate']) $paginate = true;
    }

    //either return the options just created (paginate)
    if($paginate) {
        return $qOpts;

    //or return the events data
    } else {
        $data = $this->find('all', $qOpts);
        return $data;
    }
}

/ , , .

( .)

+3

, .

function indexbystatus() {
    $this->set('title_for_layout','List Assets by Status');
    $this->Session->write('sender',array('controller'=>'assets','action'=>'indexbystatus'));
    $searchkey=$this->Session->read('Searchkey.status');
    $conditions='';
    if($searchkey) {
        $conditions=array('Asset.status_id'=>$searchkey);
    }
    if(!empty($this->data)) {
        // if user has sent anything by the searchform set conditions and
        // store it to the session but if it is empty we delete the stored
        // searchkey (this way we can reset the search)
        if($this->data['Asset']['status_id']!='') {
            $conditions=array('Asset.status_id'=>$this->data['Asset']['status_id']);
            $this->Session->write('Searchkey.status',$this->data['Asset']['status_id']);
        } else {
            $this->Session->delete('Searchkey.status');
            $conditions=null;
        }
    } else if($searchkey) {
        // if no data from the searchform we set the stored one
        // from the session if any
        $this->data['Asset']['status_id']=$searchkey;
    }
    $this->paginate=array(
                        'limit'=>25,
                        'order'=>array('Asset.status_id'=>'asc'),
                        'conditions'=>$conditions,
                        );
    $this->set('assets',$this->paginate());
    $statuses=$this->Asset->Status->find('list');
    $this->set('statuses',$statuses);
}

, .

0

All Articles