mbeccati Sat Mar 28 03:01:38 2009 UTC Modified files: /php-src/ext/pdo_pgsql pgsql_driver.c pgsql_statement.c /php-src/ext/pdo_pgsql/tests bug44861.phpt Log: MFB: - Fixed bug #44861 (scrollable cursor don't work with pgsql) http://cvs.php.net/viewvc.cgi/php-src/ext/pdo_pgsql/pgsql_driver.c?r1=1.71&r2=1.72&diff_format=u Index: php-src/ext/pdo_pgsql/pgsql_driver.c diff -u php-src/ext/pdo_pgsql/pgsql_driver.c:1.71 php-src/ext/pdo_pgsql/pgsql_driver.c:1.72 --- php-src/ext/pdo_pgsql/pgsql_driver.c:1.71 Sat Mar 28 02:34:02 2009 +++ php-src/ext/pdo_pgsql/pgsql_driver.c Sat Mar 28 03:01:38 2009 @@ -18,7 +18,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: pgsql_driver.c,v 1.71 2009/03/28 02:34:02 mbeccati Exp $ */ +/* $Id: pgsql_driver.c,v 1.72 2009/03/28 03:01:38 mbeccati Exp $ */ #ifdef HAVE_CONFIG_H #include "config.h" @@ -232,13 +232,13 @@ if (S->cursor_name) { efree(S->cursor_name); } - /* TODO: check how scrollable cursors related to prepared statements */ spprintf(&S->cursor_name, 0, "pdo_pgsql_cursor_%08x", (unsigned int) stmt); + emulate = 1; } #if HAVE_PQPREPARE - if (driver_options) { + else if (driver_options) { if (pdo_attr_lval(driver_options, PDO_PGSQL_ATTR_DISABLE_NATIVE_PREPARED_STATEMENT, 0 TSRMLS_CC) == 1) { emulate = 1; http://cvs.php.net/viewvc.cgi/php-src/ext/pdo_pgsql/pgsql_statement.c?r1=1.51&r2=1.52&diff_format=u Index: php-src/ext/pdo_pgsql/pgsql_statement.c diff -u php-src/ext/pdo_pgsql/pgsql_statement.c:1.51 php-src/ext/pdo_pgsql/pgsql_statement.c:1.52 --- php-src/ext/pdo_pgsql/pgsql_statement.c:1.51 Sat Mar 28 02:34:02 2009 +++ php-src/ext/pdo_pgsql/pgsql_statement.c Sat Mar 28 03:01:38 2009 @@ -18,7 +18,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: pgsql_statement.c,v 1.51 2009/03/28 02:34:02 mbeccati Exp $ */ +/* $Id: pgsql_statement.c,v 1.52 2009/03/28 03:01:38 mbeccati Exp $ */ #ifdef HAVE_CONFIG_H #include "config.h" @@ -129,6 +129,24 @@ S->current_row = 0; + if (S->cursor_name) { + char *q = NULL; + spprintf(&q, 0, "DECLARE %s SCROLL CURSOR WITH HOLD FOR %s", S->cursor_name, stmt->active_query_string); + S->result = PQexec(H->server, q); + efree(q); + + /* check if declare failed */ + status = PQresultStatus(S->result); + if (status != PGRES_COMMAND_OK && status != PGRES_TUPLES_OK) { + pdo_pgsql_error_stmt(stmt, status, pdo_pgsql_sqlstate(S->result)); + return 0; + } + + /* fetch to be able to get the number of tuples later, but don't advance the cursor pointer */ + spprintf(&q, 0, "FETCH FORWARD 0 FROM %s", S->cursor_name); + S->result = PQexec(H->server, q); + efree(q); + } else #if HAVE_PQPREPARE if (S->stmt_name) { /* using a prepared statement */ @@ -182,12 +200,7 @@ 0); } else #endif - if (S->cursor_name) { - char *q = NULL; - spprintf(&q, 0, "DECLARE %s CURSOR FOR %s", S->cursor_name, stmt->active_query_string); - S->result = PQexec(H->server, q); - efree(q); - } else { + { S->result = PQexec(H->server, stmt->active_query_string); } status = PQresultStatus(S->result); @@ -350,19 +363,23 @@ pdo_pgsql_stmt *S = (pdo_pgsql_stmt*)stmt->driver_data; if (S->cursor_name) { - char *ori_str; + char *ori_str = NULL; char *q = NULL; ExecStatusType status; switch (ori) { - case PDO_FETCH_ORI_NEXT: ori_str = "FORWARD"; break; - case PDO_FETCH_ORI_PRIOR: ori_str = "BACKWARD"; break; - case PDO_FETCH_ORI_REL: ori_str = "RELATIVE"; break; + case PDO_FETCH_ORI_NEXT: spprintf(&ori_str, 0, "NEXT"); break; + case PDO_FETCH_ORI_PRIOR: spprintf(&ori_str, 0, "BACKWARD"); break; + case PDO_FETCH_ORI_FIRST: spprintf(&ori_str, 0, "FIRST"); break; + case PDO_FETCH_ORI_LAST: spprintf(&ori_str, 0, "LAST"); break; + case PDO_FETCH_ORI_ABS: spprintf(&ori_str, 0, "ABSOLUTE %ld", offset); break; + case PDO_FETCH_ORI_REL: spprintf(&ori_str, 0, "RELATIVE %ld", offset); break; default: return 0; } - spprintf(&q, 0, "FETCH %s %ld FROM %s", ori_str, offset, S->cursor_name); + spprintf(&q, 0, "FETCH %s FROM %s", ori_str, S->cursor_name); + efree(ori_str); S->result = PQexec(S->H->server, q); efree(q); status = PQresultStatus(S->result); @@ -372,9 +389,12 @@ return 0; } - S->current_row = 1; - return 1; - + if (PQntuples(S->result)) { + S->current_row = 1; + return 1; + } else { + return 0; + } } else { if (S->current_row < stmt->row_count) { S->current_row++; http://cvs.php.net/viewvc.cgi/php-src/ext/pdo_pgsql/tests/bug44861.phpt?r1=1.1&r2=1.2&diff_format=u Index: php-src/ext/pdo_pgsql/tests/bug44861.phpt diff -u /dev/null php-src/ext/pdo_pgsql/tests/bug44861.phpt:1.2 --- /dev/null Sat Mar 28 03:01:38 2009 +++ php-src/ext/pdo_pgsql/tests/bug44861.phpt Sat Mar 28 03:01:38 2009 @@ -0,0 +1,78 @@ +--TEST-- +Bug #44861 (scrollable cursor don't work with pgsql) +--SKIPIF-- +<?php +if (!extension_loaded('pdo') || !extension_loaded('pdo_pgsql')) die('skip not loaded'); +require dirname(__FILE__) . '/config.inc'; +require dirname(__FILE__) . '/../../../ext/pdo/tests/pdo_test.inc'; +PDOTest::skip(); +?> +--FILE-- +<?php +require dirname(__FILE__) . '/../../../ext/pdo/tests/pdo_test.inc'; +$dbh = PDOTest::test_factory(dirname(__FILE__) . '/common.phpt'); + +$dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); + +$query = "SELECT 'row1' AS r UNION SELECT 'row2' UNION SELECT 'row3' UNION SELECT 'row4'"; +$aParams = array(PDO::ATTR_CURSOR => PDO::CURSOR_SCROLL); + +$res = $dbh->prepare($query, $aParams); +$res->execute(); +var_dump($res->fetchColumn()); +var_dump($res->fetchColumn()); +var_dump($res->fetchColumn()); +var_dump($res->fetchColumn()); +var_dump($res->fetchColumn()); + +var_dump($res->fetch(PDO::FETCH_NUM, PDO::FETCH_ORI_ABS, 3)); +var_dump($res->fetch(PDO::FETCH_NUM, PDO::FETCH_ORI_PRIOR)); +var_dump($res->fetch(PDO::FETCH_NUM, PDO::FETCH_ORI_FIRST)); +var_dump($res->fetch(PDO::FETCH_NUM, PDO::FETCH_ORI_LAST)); +var_dump($res->fetch(PDO::FETCH_NUM, PDO::FETCH_ORI_REL, -1)); + +var_dump($res->fetchAll(PDO::FETCH_ASSOC)); + +// Test binding params via emulated prepared query +$res = $dbh->prepare("SELECT ?", $aParams); +$res->execute(array("it's working")); +var_dump($res->fetch(PDO::FETCH_NUM)); + +?> +--EXPECT-- +string(4) "row1" +string(4) "row2" +string(4) "row3" +string(4) "row4" +bool(false) +array(1) { + [0]=> + string(4) "row3" +} +array(1) { + [0]=> + string(4) "row2" +} +array(1) { + [0]=> + string(4) "row1" +} +array(1) { + [0]=> + string(4) "row4" +} +array(1) { + [0]=> + string(4) "row3" +} +array(1) { + [0]=> + array(1) { + ["r"]=> + string(4) "row4" + } +} +array(1) { + [0]=> + string(12) "it's working" +}
-- PHP CVS Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php