如何在 ZF2 zend-db 中缓冲未缓冲的结果集?
How can I buffer an unbuffered ResultSet in ZF2 zend-db?
My Atlas
class 执行递归数据探索给定一组不连续但顺序的 col1
值,从 MySQL table1
开始读取$startingVal
。限制 $totalVal
是任何给定会话期间工作单元的限制。在每次递归中,Atlas
将从不同的 table 中检索零到八 (0-8) 行。
Fatal error: Uncaught exception 'Zend\Db\Adapter\Exception\RuntimeException'
with message 'Row count is not available in unbuffered result sets.'
in /path/vendor/Zend/zend-db/src/Adapter/Driver/Mysqli/Result.php:316
Stack trace:
#0 /path/vendor/Zend/zend-db/src/ResultSet/AbstractResultSet.php(65):
Zend\Db\Adapter\Driver\Mysqli\Result->count()
#1 /path/vendor/Zend/zend-db/src/Adapter/Adapter.php(195):
Zend\Db\ResultSet\AbstractResultSet->
initialize(Object(Zend\Db\Adapter\Driver\Mysqli\Result))
#2 /path/modules/Flightplan/src/Flightplan/Atlas.php(110):
Zend\Db\Adapter\Adapter->query('SELECT col1...', Array)
#3 /path/utility.php(46):
Flightplan\Atlas->shoulder_routes('30000001', '1')
#4 {main} thrown in /path/vendor/Zend/zend-db/src/Adapter/Driver/Mysqli/Result.php
on line 316
如果我正确读取错误和 Zend 源,Adapter
正在使用 Mysqli\Result
资源(默认情况下非缓冲)初始化 AbstractResultSet
(默认情况下缓冲),并且紧接着,尝试对其进行计数,这会引发错误。这是在递归之前我第一次通过适配器查询时发生的。
AbstractResultSet.php
public function initialize($dataSource)
{
// reset buffering
if (is_array($this->buffer)) {
$this->buffer = array();
}
if ($dataSource instanceof ResultInterface) {
$this->count = $dataSource->count(); // line 65
Atlas.php:
use Zend\Db\Adapter\Adapter;
public function __construct( array $configArray = null ){
...
$this->configArray = $configArray;
$this->adapter = new Adapter( $this->configArray );
}
public function shoulder_routes( $startingVal, $totalVal ){
...
$result = $this->adapter->query( 'SELECT col1 FROM table1
WHERE col1 >= ? LIMIT ?', array( $startingVal, $totalVal )); // line 110
$result->buffer(); // ADDED AFTER 1st error occurrence
...
}
我添加了 $result->buffer();
,不幸的是,由于错误发生在 returns 到 Atlas
.
之前,所以没有用
我该如何纠正这个问题?
Mysqli\Result
可以在初始化时设置为缓冲。我是否在默认情况下使用缓冲来扩展 Result
,我是否会在 Atlas
中指定它,例如:
$this->adapter = new Adapter( $this->configArray,null,new MyMysqliResult() );
编辑:将 ResultInterface 作为参数提供给 Adapter 会引发错误,因为 Adapter 需要 ResultSet。但是,可以扩展 AbstractResultSet,以便 IT 在调用从 Adaper\Driver\Mysqli...[传递给它的 ResultSet 上的 $result->count() 之前调用 $result->buffer() =32=]
- (我认为)我读到 Zend\Adapter PDO_Mysql driver/platform/result 默认情况下会缓冲。有什么理由不切换到 PDO 吗?
编辑:切换到PDO_Mysql Adapter\Driver导致以下错误,我想如果我准备一个驱动程序提供的语句可能会解决
Uncaught exception 'PDOException' with message 'SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ''1'' at line 1' in /path/vendor/Zend/zend-db/src/Adapter/Driver/Pdo/Statement.php:239
- 我也在 this answer 中看到,其中
result->getResource()->fetchAll();
稍后可能会在 Atlas
中有所帮助,但在我有机会之前再次发生错误。
我错过了什么?谢谢-
在这个问题和项目中来来去去几个月后,我偶然发现了一个答案 here which lead me to the same answer here。
$config => array(
...
'options' => array(
'buffer_results' => true,
),
我一直在寻找这样的答案,显然是盯着太用力了。
My Atlas
class 执行递归数据探索给定一组不连续但顺序的 col1
值,从 MySQL table1
开始读取$startingVal
。限制 $totalVal
是任何给定会话期间工作单元的限制。在每次递归中,Atlas
将从不同的 table 中检索零到八 (0-8) 行。
Fatal error: Uncaught exception 'Zend\Db\Adapter\Exception\RuntimeException'
with message 'Row count is not available in unbuffered result sets.'
in /path/vendor/Zend/zend-db/src/Adapter/Driver/Mysqli/Result.php:316
Stack trace:
#0 /path/vendor/Zend/zend-db/src/ResultSet/AbstractResultSet.php(65):
Zend\Db\Adapter\Driver\Mysqli\Result->count()
#1 /path/vendor/Zend/zend-db/src/Adapter/Adapter.php(195):
Zend\Db\ResultSet\AbstractResultSet->
initialize(Object(Zend\Db\Adapter\Driver\Mysqli\Result))
#2 /path/modules/Flightplan/src/Flightplan/Atlas.php(110): Zend\Db\Adapter\Adapter->query('SELECT col1...', Array)
#3 /path/utility.php(46):
Flightplan\Atlas->shoulder_routes('30000001', '1')
#4 {main} thrown in /path/vendor/Zend/zend-db/src/Adapter/Driver/Mysqli/Result.php
on line 316
如果我正确读取错误和 Zend 源,Adapter
正在使用 Mysqli\Result
资源(默认情况下非缓冲)初始化 AbstractResultSet
(默认情况下缓冲),并且紧接着,尝试对其进行计数,这会引发错误。这是在递归之前我第一次通过适配器查询时发生的。
AbstractResultSet.php
public function initialize($dataSource)
{
// reset buffering
if (is_array($this->buffer)) {
$this->buffer = array();
}
if ($dataSource instanceof ResultInterface) {
$this->count = $dataSource->count(); // line 65
Atlas.php:
use Zend\Db\Adapter\Adapter;
public function __construct( array $configArray = null ){
...
$this->configArray = $configArray;
$this->adapter = new Adapter( $this->configArray );
}
public function shoulder_routes( $startingVal, $totalVal ){
...
$result = $this->adapter->query( 'SELECT col1 FROM table1
WHERE col1 >= ? LIMIT ?', array( $startingVal, $totalVal )); // line 110
$result->buffer(); // ADDED AFTER 1st error occurrence
...
}
我添加了 $result->buffer();
,不幸的是,由于错误发生在 returns 到 Atlas
.
我该如何纠正这个问题?
Mysqli\Result
可以在初始化时设置为缓冲。我是否在默认情况下使用缓冲来扩展Result
,我是否会在Atlas
中指定它,例如:
$this->adapter = new Adapter( $this->configArray,null,new MyMysqliResult() );
编辑:将 ResultInterface 作为参数提供给 Adapter 会引发错误,因为 Adapter 需要 ResultSet。但是,可以扩展 AbstractResultSet,以便 IT 在调用从 Adaper\Driver\Mysqli...[传递给它的 ResultSet 上的 $result->count() 之前调用 $result->buffer() =32=]
- (我认为)我读到 Zend\Adapter PDO_Mysql driver/platform/result 默认情况下会缓冲。有什么理由不切换到 PDO 吗?
编辑:切换到PDO_Mysql Adapter\Driver导致以下错误,我想如果我准备一个驱动程序提供的语句可能会解决
Uncaught exception 'PDOException' with message 'SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ''1'' at line 1' in /path/vendor/Zend/zend-db/src/Adapter/Driver/Pdo/Statement.php:239
- 我也在 this answer 中看到,其中
result->getResource()->fetchAll();
稍后可能会在Atlas
中有所帮助,但在我有机会之前再次发生错误。
我错过了什么?谢谢-
在这个问题和项目中来来去去几个月后,我偶然发现了一个答案 here which lead me to the same answer here。
$config => array(
...
'options' => array(
'buffer_results' => true,
),
我一直在寻找这样的答案,显然是盯着太用力了。