Pager проблемы Yii 1.1

Это касается Yii 1.1

Непонятное поведение CActiveDataProvider с pagination и criteria.

В criteria определено свойство group

Непонятность заключается в том, что когда выводится количество страниц и записей оно не корректно, если включено разбиение по страницам,

то есть общее количество записей получается как будто не было учтено свойство group, хотя когда просматриваешь страницы

отображается корректное количество записей, если убрать разбиение по страницам то все отображается и работает корректно.

Может кто сталкивался с такой проблемой… интересно это в Yii в Zii или у меня где то косяк.

Заранее всем спасибо.

Покажите пример кода как вы используете.

Вот код :




....

        if ($this->onPages)

        {

            $this->pages = new CPagination();

            $this->pages->pageSize = self::PAGE_SIZE;

        }

....


        $this->criteria = new CDbCriteria();

        $this->criteria->condition = 'report_date="'. $this->view_params['date_report'] .'" AND vendor.project_id=' . Yii::app()->user->project_id;

        $this->criteria->with = array('account.vendor');

        if (isset($_GET['group']))

        {

            $this->criteria->group = 'vendor_name';

            $this->criteria->select = 'SUM(data_searches) .... MAX(update_date) as update_date' ;

            $this->view_params['vendor_group'] = true;

        }

        else

        {

            $this->criteria->order = 'vendor.vendor_name, account.account_name';

            $this->view_params['vendor_group'] = false;

        }

        

        $this->dataProvider=new CActiveDataProvider('AccountReport');

        $this->dataProvider->setCriteria($this->criteria);

        if ($this->onPages)

        {

            $this->dataProvider->setPagination($this->pages);

        }

        else

        {

            $this->dataProvider->setPagination(false);

        }

        $this->view_params['dataProvider'] = $this->dataProvider;

        $this->render('index',$this->view_params);




Спасибо что, так много народу откликнулось :lol: .

Попрактиковавшись немного MySQL Понял что это баг-проектирования т.к.

count(*) в запросах с группировками, возвращает количество обработанных записей,

а не количество получившихся в результате, так что господа разработчики, есть над чем подумать, или менять подход к получению количества записей в результирующем запросе, или сложить лапки и согласится с этим багом. Но тогда просьба большими буквами в доке прописать что это баг и он не лечится чтоб народ, потом зря время не терял.

Всем удачи.

В общем победил я этот баг но пришлось менять исходники

в CActiveDataProvaider меняем следуещее




    protected function calculateTotalItemCount()

        {

            return CActiveRecord::model($this->modelClass)->count($this->getCriteria());

        }



На




    protected function calculateTotalItemCount()

        {

            return count(CActiveRecord::model($this->modelClass)->findAll($this->getCriteria()));

        }



И все начинает работать правильно

не красиво менять исходники. может проще перегрузить как то?

Не красиво ляпы такие делать…

А это метод как быстро и на всегда убить проблему для себя…

Ну и это надо воспринимать как подсказку для создателей… :rolleyes:

Просто потом будет больше проблем при обновлении новой версии и тп. Каждый раз исходники менять

не совсем понял, у меня такая же проблема?

http://www.yiiframework.com/forum/index.php?/topic/6933-cpagination-models-count-limit-bug/page__hl__CPagination__fromsearch__1

Great

Уж тогда лучше добавить отдельную функцию типа findGroup, и в ней использовать PHP’шный count, для подсчета возвращаемых SQL данных. Вообще надо понимать, что это довольно дорогая операция в плане загрузки процессора и памяти.

Как минимум, при данном подходе, я бы оптимизировал, чтобы искало не все, а только id. Совсем незачем для банального подсчета количества строк запрашивать от SQL полную выборку - это транжирство ресурсов! При интенсивном использовании такого подхода можно начать получать предупреждения от хостеров.

Вижу по дате что топик был не вчера однако вопрос возник -

А почему бы просто не использовать для подсчета строк возможности mySQL

я имею ввиду - SQL_CALC_FOUND_ROWS

отчасти такой подход делает на один меньше запрос.

к примеру

SELCT SQL_CALC_FOUND_ROWS id, blablabla … limit 10

сразу после этого сделать

SELECT FOUND_ROWS()

и получить количество строк без учета лимит.

Что думаете ?

P.S. я в одном из проектов именно так и делал, правда использовал DAO для этих целей

для начала почитайте mysqlperformanceblog.com по этой теме (To SQL_CALC_FOUND_ROWS or not to SQL_CALC_FOUND_ROWS?) и поймите почему не рекомендуется использовать SQL_CALC_FOUND_ROWS :rolleyes: , ну а второе - а как же миграция между различными БД!?

За ссылку спасибо.

Но первый же комментарий к статье совсем не однозначный :)