Pagination 分页不';在Zend框架2中不能使用HAVING子句
我实现了一个分页,类似于它的显示方式: 搜索\模型\课程表Pagination 分页不';在Zend框架2中不能使用HAVING子句,pagination,zend-framework2,zend-paginator,having-clause,Pagination,Zend Framework2,Zend Paginator,Having Clause,我实现了一个分页,类似于它的显示方式: 搜索\模型\课程表 class CourseTable { const RELEVANCE_TITLE = 5; const RELEVANCE_DESCRIPTION = 2; const RELEVANCE_MIN = 3; protected $tableGateway; public function __construct(TableGateway $tableGateway) { $
class CourseTable {
const RELEVANCE_TITLE = 5;
const RELEVANCE_DESCRIPTION = 2;
const RELEVANCE_MIN = 3;
protected $tableGateway;
public function __construct(TableGateway $tableGateway) {
$this->tableGateway = $tableGateway;
}
public function findAllByCriteria(CourseSearchInput $input) {
$concatDelimiter = self::CONCAT_DELIMITER;
$select = new Select();
$where = $this->buildWhereFromCriteria($input);
$having = new Having();
$select->columns(array(
...
));
$select->from($this->tableGateway->getTable());
$select
->join('...)) // and some more JOINs
;
$where
// condition
;
$having
->greaterThanOrEqualTo('relevance', self::RELEVANCE_MIN);
;
$select->where($where, Predicate::OP_AND);
$select->having($having);
$select->group(array('courses.id'));
$adapter = new \Zend\Paginator\Adapter\DbSelect($select, $this->tableGateway->getAdapter());
$paginator = new \Zend\Paginator\Paginator($adapter);
return $paginator;
// $resultSet = $this->tableGateway->selectWith($select);
// return $resultSet;
}
public function buildRelevanceExpressionFromCriteria(CourseSearchInput $input) {
$criteria = $input->getArrayCopy();
$relevanceTitle = self::RELEVANCE_TITLE;
$relevanceDescription = self::RELEVANCE_DESCRIPTION;
$expressionSQL = <<<SQL
MATCH (coursedata.title) AGAINST ('{$criteria['keyword']}') * $relevanceTitle +
MATCH (coursedata.description) AGAINST ('{$criteria['keyword']}') * $relevanceDescription
SQL;
return new Expression($expressionSQL);
}
function buildWhereFromCriteria(CourseSearchInput $input) {
...
}
}
现在抛出一个异常:
File:
/var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Db/Adapter/Driver/Pdo/Statement.php:245
Message:
Statement could not be executed
Stapelüberwachung:
#0 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Paginator/Adapter/DbSelect.php(122): Zend\Db\Adapter\Driver\Pdo\Statement->execute()
#1 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Paginator/Paginator.php(881): Zend\Paginator\Adapter\DbSelect->count()
#2 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Paginator/Paginator.php(343): Zend\Paginator\Paginator->_calculatePageCount()
#3 /var/www/path/to/project/module/Search/src/Search/Controller/SearchController.php(38): Zend\Paginator\Paginator->count()
#4 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/Controller/AbstractActionController.php(83): Search\Controller\SearchController->searchCoursesAction()
#5 [internal function]: Zend\Mvc\Controller\AbstractActionController->onDispatch(Object(Zend\Mvc\MvcEvent))
#6 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(460): call_user_func(Array, Object(Zend\Mvc\MvcEvent))
#7 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(204): Zend\EventManager\EventManager->triggerListeners('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#8 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/Controller/AbstractController.php(117): Zend\EventManager\EventManager->trigger('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#9 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/DispatchListener.php(114): Zend\Mvc\Controller\AbstractController->dispatch(Object(Zend\Http\PhpEnvironment\Request), Object(Zend\Http\PhpEnvironment\Response))
#10 [internal function]: Zend\Mvc\DispatchListener->onDispatch(Object(Zend\Mvc\MvcEvent))
#11 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(460): call_user_func(Array, Object(Zend\Mvc\MvcEvent))
#12 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(204): Zend\EventManager\EventManager->triggerListeners('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#13 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/Application.php(294): Zend\EventManager\EventManager->trigger('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#14 /var/www/path/to/project/public/index.php(12): Zend\Mvc\Application->run()
#15 {main}
前一个是:
Previous Exception:
PDOException
File:
/var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Db/Adapter/Driver/Pdo/Statement.php:240
Message:
SQLSTATE[42S22]: Column not found: 1054 Unknown column 'relevance' in 'having clause'
Stapelüberwachung:
#0 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Db/Adapter/Driver/Pdo/Statement.php(240): PDOStatement->execute()
#1 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Paginator/Adapter/DbSelect.php(122): Zend\Db\Adapter\Driver\Pdo\Statement->execute()
#2 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Paginator/Paginator.php(881): Zend\Paginator\Adapter\DbSelect->count()
#3 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Paginator/Paginator.php(343): Zend\Paginator\Paginator->_calculatePageCount()
#4 /var/www/path/to/project/module/Search/src/Search/Controller/SearchController.php(38): Zend\Paginator\Paginator->count()
#5 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/Controller/AbstractActionController.php(83): Search\Controller\SearchController->searchCoursesAction()
#6 [internal function]: Zend\Mvc\Controller\AbstractActionController->onDispatch(Object(Zend\Mvc\MvcEvent))
#7 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(460): call_user_func(Array, Object(Zend\Mvc\MvcEvent))
#8 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(204): Zend\EventManager\EventManager->triggerListeners('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#9 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/Controller/AbstractController.php(117): Zend\EventManager\EventManager->trigger('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#10 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/DispatchListener.php(114): Zend\Mvc\Controller\AbstractController->dispatch(Object(Zend\Http\PhpEnvironment\Request), Object(Zend\Http\PhpEnvironment\Response))
#11 [internal function]: Zend\Mvc\DispatchListener->onDispatch(Object(Zend\Mvc\MvcEvent))
#12 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(460): call_user_func(Array, Object(Zend\Mvc\MvcEvent))
#13 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(204): Zend\EventManager\EventManager->triggerListeners('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#14 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/Application.php(294): Zend\EventManager\EventManager->trigger('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#15 /var/www/path/to/project/public/index.php(12): Zend\Mvc\Application->run()
#16 {main}
这是一个框架错误吗
编辑 使用
$test=$select->getSqlString($this->tableGateway->getAdapter()->getPlatform())生成的查询代码>在$adapter=new\Zend\Paginator\adapter\DbSelect($select,$this->tableGateway->getAdapter()之前的行中代码>:
我删除了我的答案,因为我不确定你的问题到底是什么。我怀疑它与查询本身有关,它不是一个真正的bug。您能显示您正在选择的列吗(您没有选择)?另外,您尝试使用普通SQL编写的查询也会有所帮助。它不分页工作;2.当我提取查询并在MySQL客户机上执行它时,它也可以工作。该查询太长,无法发表评论,我更新了该问题。我仍然认为是这样,因为它看起来像是您按courses.id分组(对我来说已经很奇怪了,但还行),而在您的示例中,您使用的是“相关性”,它不是分组列。根据MySQL模式(即,如果仅未设置_FULL _GROUP _BY),MySQL可能会在您的会话中允许此操作,但这不会减少错误。当您设置ONLY_FULL_GROUP_BY mode时,您可以做的是测试查询是否仍然在您的客户机中工作:set sql_mode='ONLY_FULL_GROUP_BY';是的,我现在明白了。当我禁用时,查询实际上返回了一个错误(但不是异常中的错误):错误代码:1055'unisportr_zf.courses.title'不在groupby
中。我将尝试重写代码,以便将GROUP BY
using简化为标准SQL。是的,这非常简单:您只需确保HAVING子句中使用的所有列也在GROUP BY子句中列出。这非常有意义,因为您的have包含关于每个组的条件,而不是关于每一行的条件。
Previous Exception:
PDOException
File:
/var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Db/Adapter/Driver/Pdo/Statement.php:240
Message:
SQLSTATE[42S22]: Column not found: 1054 Unknown column 'relevance' in 'having clause'
Stapelüberwachung:
#0 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Db/Adapter/Driver/Pdo/Statement.php(240): PDOStatement->execute()
#1 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Paginator/Adapter/DbSelect.php(122): Zend\Db\Adapter\Driver\Pdo\Statement->execute()
#2 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Paginator/Paginator.php(881): Zend\Paginator\Adapter\DbSelect->count()
#3 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Paginator/Paginator.php(343): Zend\Paginator\Paginator->_calculatePageCount()
#4 /var/www/path/to/project/module/Search/src/Search/Controller/SearchController.php(38): Zend\Paginator\Paginator->count()
#5 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/Controller/AbstractActionController.php(83): Search\Controller\SearchController->searchCoursesAction()
#6 [internal function]: Zend\Mvc\Controller\AbstractActionController->onDispatch(Object(Zend\Mvc\MvcEvent))
#7 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(460): call_user_func(Array, Object(Zend\Mvc\MvcEvent))
#8 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(204): Zend\EventManager\EventManager->triggerListeners('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#9 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/Controller/AbstractController.php(117): Zend\EventManager\EventManager->trigger('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#10 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/DispatchListener.php(114): Zend\Mvc\Controller\AbstractController->dispatch(Object(Zend\Http\PhpEnvironment\Request), Object(Zend\Http\PhpEnvironment\Response))
#11 [internal function]: Zend\Mvc\DispatchListener->onDispatch(Object(Zend\Mvc\MvcEvent))
#12 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(460): call_user_func(Array, Object(Zend\Mvc\MvcEvent))
#13 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/EventManager/EventManager.php(204): Zend\EventManager\EventManager->triggerListeners('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#14 /var/www/path/to/project/vendor/zendframework/zendframework/library/Zend/Mvc/Application.php(294): Zend\EventManager\EventManager->trigger('dispatch', Object(Zend\Mvc\MvcEvent), Object(Closure))
#15 /var/www/path/to/project/public/index.php(12): Zend\Mvc\Application->run()
#16 {main}
SELECT `courses`.`id` AS `id`,
`courses`.`title` AS `title`,
`courses`.`description` AS `description`,
DATE_FORMAT(courses.startdate, "%e\.%m\.%Y") AS `startDate`,
DATE_FORMAT(courses.enddate, "%e\.%m\.%Y") AS `endDate`,
DATE_FORMAT(courses.starttime, "%H\:%i") AS `startTime`,
DATE_FORMAT(courses.endtime, "%H\:%i") AS `endTime`,
`allproviders`.`displayedname` AS `providerName`,
`allproviders`.`providertype` AS `providerType`,
`cities`.`name` AS `city`,
`weekdays`.`labelde` AS `weekday`,
`levelsmin`.`usrlevel` AS `usrLevelMin`,
`levelsmin`.`unilevel` AS `uniLevelMin`,
`levelsmax`.`usrlevel` AS `usrLevelMax`,
`levelsmax`.`unilevel` AS `uniLevelMax`,
MATCH (coursedata.title) AGAINST ('Salsa') * 5 + MATCH (coursedata.description) AGAINST ('Salsa') * 2 AS `relevance`,
GROUP_CONCAT(trainers.name SEPARATOR '|||') AS `trainers`
FROM `courses`
INNER JOIN `allproviders` ON `courses`.`provider_id` = `allproviders`.`providerid`
INNER JOIN `cities` ON `allproviders`.`city_id` = `cities`.`id`
INNER JOIN `weekdays` ON `courses`.`weekday_id` = `weekdays`.`id`
LEFT JOIN `levels` AS `levelsmin` ON `courses`.`levelmin_id` = `levelsmin`.`id`
LEFT JOIN `levels` AS `levelsmax` ON `courses`.`levelmax_id` = `levelsmax`.`id`
INNER JOIN `coursedata` ON `courses`.`id` = `coursedata`.`id`
INNER JOIN `courses_trainers` ON `courses`.`id` = `courses_trainers`.`course_id`
INNER JOIN `trainers` ON `trainer_id` = `trainers`.`id`
WHERE `cities`.`id` = '23'
AND `weekdays`.`id` IN ('1',
'2',
'3',
'4',
'5',
'6',
'7')
AND `courses`.`enddate` > NOW()
GROUP BY `courses`.`id` HAVING `relevance` >= '3'