使用自定义路径在CakePHP中进行排序

问题描述 投票:0回答:3

我试图在线(一如既往)找到一个解决方案但显然没有提出任何建议。

我正在使用CakePHP,我需要在一些控制器中添加一些排序。我还想为此创建自定义路由。所以这是我的代码不起作用(分页工作,排序nope):

RatesController.php:

public $paginate = array(
    'Rate' => array(
            'limit' => 10,
            'order' => array(
                    'Rate.created' => 'desc'
            ),
            'conditions' => array( 'Rate.accepted' => 1 ),
            //'fields' => array('Rate.*', 'User.username')
    ),
    'Airline' => array(
            'limit' => 50,
            /*'order' => array(
                    'Airline.rate' => 'desc',
                    'Airline.name' => 'asc'
            ),*/
            'conditions' => array(
                'Airline.rate >' => 0
            ),
            'fields' => array('Airline.id', 'Airline.name', 'Airline.image_id', 'Airline.rate', 'Image.*')
    )
);

function index($category = 'airlines'){ 
    pr($this->request);
    $data = $this->paginate('Airline');
    pr($data);
}

在视图中:

$this->Paginator->options(array(
    'url' => array(
        'controller' => 'rates',
        'action' => 'index',
        'category' => $category
    )
));

echo $this->Paginator->first('«', array('escape' => false), null, array('class' => 'disabled', 'escape' => false));  
echo $this->Paginator->prev('<', array('escape' => false), null, array('class' => 'disabled', 'escape' => false));

echo $this->Paginator->numbers(array(
    'modulus' => 6,
    'separator' => false
));

echo $this->Paginator->next('>', array('escape' => false), null, array('class' => 'disabled', 'escape' => false));
echo $this->Paginator->last('»', array('escape' => false), null, array('class' => 'disabled', 'escape' => false));
echo' sort by ';
echo $this->Paginator->sort('Airline.rate');
echo' or by ';
echo $this->Paginator->sort('Airline.name');

路线:

Router::connectNamed(array('page'), array('default' => false, 'greedy' => false));
Router::connectNamed(array('sort', 'direction'), array('default' => false, 'greedy' => false));

Router::connect('/rate-airlines', array('controller' => 'rates', 'action' => 'index', 'category' => 'airlines'));
/*
Router::connect(
    '/rate-airlines/:page/',
    array('controller' => 'rates', 'action' => 'index', 'category' => 'airlines'),
    array(
        'named' => array('page' => '[a-z]+')
    )
);
Router::connect(
    '/rate-airlines/:page/:sort/:direction',
    array('controller' => 'rates', 'action' => 'index', 'category' => 'airlines'),
    array(
        'pass' => array('page', 'sort', 'direction'),
        //'id' => '[0-9]+',
        'named' => array('page' => '[\d]+', 'sort', 'direction')
    ) 
);*/
Router::connect(
    '/rate-airlines/:sort/:direction',
    array('controller' => 'rates', 'action' => 'index', 'category' => 'airlines'),
    array(
        'named' => array('sort', 'direction')
    )
);

我真的不知道为什么它不起作用,我已经花了好几个小时试图让它工作,寻求答案。

PS。无论我做了什么,我都无法将:sort和:指向请求中的命名数组:

CakeRequest Object
(
    [params] => Array
        (
            [plugin] => 
            [controller] => rates
            [action] => index
            [named] => Array
                (
                )

            [pass] => Array
                (
                )

            [sort] => Airline.rate
            [direction] => asc
            [category] => airlines
            [isAjax] => 
        )
        ...
)

有什么想法吗?

麦克风

sorting cakephp pagination cakephp-2.3 paginator
3个回答
1
投票

你真的不应该使用路由参数进行排序。这是一个糟糕的主意,CakePHP已经将它们放入即将发布的3.x版本中。

而是使用查询字符串参数。这正是他们的目的:操纵单个视图。如果你有一个列表,那么传递'sort'和'direction'等参数。

假设您有一个像http://example.com/rates/?sort=name&direction=asc这样的URL,然后您可以在控制器中解析它,如下所示:

<?php
class RatesController extends AppController {

    public function index() {
        $sort = isset($this->request->query['sort']) ? $this->request->query['sort'] : 'created';
        $direction = isset($this->request->query['direction']) ? $this->request->query['direction'] : 'desc';

        $this->Paginator->settings = array(
            'order' => array($sort => $direction)
        );

        $rates = $this->paginate('Rate');

        $this->set(compact('rates'));
    }
}

我还想更进一步,使用查询字符串进行分页......

<?php
class AppController extends Controller {

    public $paginate = array(
        'paramType' => 'querystring'
    );
}

......但那只是个人偏好。

以上是在漫长的一天写的。在考虑之后,CakePHP处理开箱即用的分页。您无需手动指定包含名称参数的路由。

只要您使用Pagination组件和Paginator帮助程序(就像您所做的那样),并为控制器操作定义了单个路由,您就不需要执行任何其他操作。在您的情况下,您的控制器看起来像:

<?php
class RatesController extends AppController {

    public function index() {
        $rates = $this->paginate('Rate');
        $this->set(compact('rates'));
    }

}

你的观点看起来像:

<?php echo $this->Paginator->sort('Airline.name'); ?>

如果你想重写/率/航空公司,那么你的单一​​航线将如下所示:

<?php
Router::connect('/rates-airlines', array(
    'controller' => 'rates',
    'action' => 'index',
));

有了上述内容,paginate调用将考虑要排序的列和方向。

对不起上面的错综复杂的答案!


0
投票

谢谢你的回复。问题是我真的需要自定义路由以进行分页,所以我终于使用以下代码实现了我想要的目标:

在AppController.php中(请注意,所有$ this-> request-> query [...]变量都是因为我还想通过GET方法使用表单来使用排序接口)

function beforeFilter() {

    if (isset($this->request->params['page'])) {

        $this->request->params['named']['page'] = $this->request->params['page'];

    }elseif( isset($this->request->query['page']) ){

        $this->request->params['named']['page'] = $this->request->query['page'];

    } 
    if (isset($this->request->params['sort'])) {

        $this->request->params['named']['sort'] = $this->request->params['sort'];

    }elseif (isset($this->request->query['sort'])) {

        $this->request->params['named']['sort'] = $this->request->query['sort'];

    }  
    if (isset($this->request->params['direction'])) {

        $this->request->params['named']['direction'] = $this->request->params['direction'];

    }elseif (isset($this->request->query['direction'])) {

        $this->request->params['named']['direction'] = $this->request->query['direction'];

    }

在routes.php中

Router::connect('/rates-airlines', array('controller' => 'rates', 'action' => 'index', 'airlines'));
Router::connect(
    '/rates-airlines/:page',
    array('controller' => 'rates', 'action' => 'index', 'airlines'),
    array(
        'named' => array('page' => '[\d]+')
    )
); 
Router::connect(
    '/rates-airlines/:page/:sort/:direction',
    array('controller' => 'rates', 'action' => 'index', 'airlines'),
    array(
        'named' => array('page' => '[\d]+', 'sort', 'direction')
    )
);
Router::connect(
    '/rates-airlines/:sort/:direction',
    array('controller' => 'rates', 'action' => 'index', 'airlines'),
    array(
        'named' => array('sort', 'direction')
    )
);

希望有人会觉得这很有用!

麦克风


0
投票

有一种更简单的方法。只需添加一个带'/ *'的路线:

Router::connect('/rates-airlines', array('controller' => 'rates', 'action' => 'index', 'airlines'));
Router::connect('/rates-airlines/*', array('controller' => 'rates', 'action' => 'index', 'airlines'));

一切都会正常工作。

© www.soinside.com 2019 - 2024. All rights reserved.