Skip to content

Commit 6d42e9f

Browse files
PDO: add mysql-specific warning count function
MySQL supplies the count of warnings along with the result set and provides a handy function to retrieve it. Without this, the only way to discover if there has been warnings in the last query is to run *another* query: "SHOW WARNINGS" OR "SELECT @@warning_count". This requires another round-trip across the network which makes warning discovery or reporting a drag on performance. Instead, we use the existing get_driver_methods function that others (postgres, sqlite) use to provide custom functionality outside the standard PDO interface. Thinking about the PDO interface, I looked into several other PDO drivers but couldn't find an analog for mysql_warning_count(). Thus I determined that this may well stay mysql-specific. Fixes php bug: #51499 (https://bugs.php.net/bug.php?id=51499)
1 parent 57a635c commit 6d42e9f

File tree

2 files changed

+53
-1
lines changed

2 files changed

+53
-1
lines changed

ext/pdo_mysql/mysql_driver.c

Lines changed: 31 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -581,6 +581,36 @@ static zend_result pdo_mysql_check_liveness(pdo_dbh_t *dbh)
581581
}
582582
/* }}} */
583583

584+
/* {{{ proto string PDO::mysqlGetWarningCount()
585+
Returns the number of SQL warnings during the execution of the last statement */
586+
static PHP_METHOD(PDO, mysqlGetWarningCount)
587+
{
588+
pdo_dbh_t *dbh;
589+
pdo_mysql_db_handle *H;
590+
591+
dbh = Z_PDO_DBH_P(ZEND_THIS);
592+
PDO_CONSTRUCT_CHECK;
593+
594+
H = (pdo_mysql_db_handle *)dbh->driver_data;
595+
RETURN_LONG(mysql_warning_count(H->server));
596+
}
597+
/* }}} */
598+
599+
static const zend_function_entry dbh_methods[] = {
600+
PHP_ME(PDO, mysqlGetWarningCount, NULL, ZEND_ACC_PUBLIC)
601+
PHP_FE_END
602+
};
603+
604+
static const zend_function_entry *pdo_mysql_get_driver_methods(pdo_dbh_t *dbh, int kind)
605+
{
606+
switch (kind) {
607+
case PDO_DBH_DRIVER_METHOD_KIND_DBH:
608+
return dbh_methods;
609+
default:
610+
return NULL;
611+
}
612+
}
613+
584614
/* {{{ pdo_mysql_request_shutdown */
585615
static void pdo_mysql_request_shutdown(pdo_dbh_t *dbh)
586616
{
@@ -625,7 +655,7 @@ static const struct pdo_dbh_methods mysql_methods = {
625655
pdo_mysql_fetch_error_func,
626656
pdo_mysql_get_attribute,
627657
pdo_mysql_check_liveness,
628-
NULL,
658+
pdo_mysql_get_driver_methods,
629659
pdo_mysql_request_shutdown,
630660
pdo_mysql_in_transaction,
631661
NULL /* get_gc */
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
--TEST--
2+
MySQL PDO->mysqlGetWarningCount()
3+
--SKIPIF--
4+
<?php
5+
require_once(__DIR__ . DIRECTORY_SEPARATOR . 'skipif.inc');
6+
require_once(__DIR__ . DIRECTORY_SEPARATOR . 'mysql_pdo_test.inc');
7+
MySQLPDOTest::skip();
8+
?>
9+
--FILE--
10+
<?php
11+
require_once(__DIR__ . DIRECTORY_SEPARATOR . 'mysql_pdo_test.inc');
12+
$db = MySQLPDOTest::factory();
13+
$assertWarnings = function ($db, $q, $count) {
14+
$db->query($q);
15+
printf("Query %s produced %d warnings\n", $q, $db->mysqlGetWarningCount());
16+
};
17+
$assertWarnings($db, 'SELECT 1 = 1', 0);
18+
$assertWarnings($db, 'SELECT 1 = "A"', 1);
19+
?>
20+
--EXPECT--
21+
Query SELECT 1 = 1 produced 0 warnings
22+
Query SELECT 1 = "A" produced 1 warnings

0 commit comments

Comments
 (0)