On Fri, 6 Sep 2002, Georg Richter wrote: [..]
GR>>> Cause the mysql-clientlib has no functionallity to determine the current GR>>> selected database ist not possible to set the previous selected(default) db GR>>> via mysql_select_db() back. The db field in the mysql structure only contains One can do it, with an extra query "SELECT DATABASE()". Using that I'd like to propose the attached patch. It's my first 'real' attempt at coding php extensions, so any pointers to make it better, are appreciated. It adds an extra optional argument 'restore_db' on to mysql_db_query, which resets, the database to the previously selected one, if > 0. I probably should use a boolean there, but chose a long, for more possibilities (i.e.: 2 = restore_to_5th_arg, 3 = restore_to_none). -- Melvyn.
Index: php_mysql.c =================================================================== RCS file: /repository/php4/ext/mysql/php_mysql.c,v retrieving revision 1.159 diff -u -r1.159 php_mysql.c --- php_mysql.c 6 Sep 2002 12:11:30 -0000 1.159 +++ php_mysql.c 6 Sep 2002 16:49:47 -0000 @@ -1168,13 +1168,46 @@ /* {{{ php_mysql_do_query_general */ -static void php_mysql_do_query_general(zval **query, zval **mysql_link, int link_id, zval **db, int use_store, zval *return_value TSRMLS_DC) +static void php_mysql_do_query_general(zval **query, zval **mysql_link, int link_id, +zval **db, int use_store, int restore_db, zval *return_value TSRMLS_DC) { php_mysql_conn *mysql; MYSQL_RES *mysql_result; + static const char *restore_query = "SELECT DATABASE()"; + char prev_db[1024]; ZEND_FETCH_RESOURCE2(mysql, php_mysql_conn *, mysql_link, link_id, "MySQL-Link", le_link, le_plink); + if(restore_db && db) do { + MYSQL_RES *restore_result; + MYSQL_ROW restore_row; + mysql_row_length_type *restore_row_lengths; + +#if MYSQL_VERSION_ID > 32199 + if(mysql_real_query(&mysql->conn, restore_query, +strlen(restore_query)) != 0) { + RETURN_FALSE; + } +#else + if(mysql_query(&mysql->conn, restore_query, strlen(restore_query)) != +0) { + RETURN_FALSE; + } +#endif + restore_result = mysql_use_result(&mysql->conn); + mysql_data_seek(restore_result, 0); + if((restore_row = mysql_fetch_row(restore_result)) == NULL + || (restore_row_lengths = mysql_fetch_lengths(restore_result)) +== NULL) { + RETURN_FALSE; + } + + if(restore_row[0]) { + if(strncpy(prev_db, restore_row[0], 1024) == NULL) { + RETURN_FALSE; + } + } + while((restore_row = (MYSQL_ROW) mysql_fetch_row(restore_result)) != +NULL) { + /* signal end of result set */ + } + } while(0); + if (db) { convert_to_string_ex(db); if (mysql_select_db(&mysql->conn, Z_STRVAL_PP(db))!=0) { @@ -1227,6 +1260,11 @@ if (use_store == MYSQL_USE_RESULT) { mysql->active_result_id = Z_LVAL_P(return_value); } + if(restore_db && prev_db) { + if(mysql_select_db(&mysql->conn, prev_db) != 0) { + php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unable to restore +db"); + } + } } /* }}} */ @@ -1255,7 +1293,7 @@ WRONG_PARAM_COUNT; break; } - php_mysql_do_query_general(query, mysql_link, id, NULL, use_store, return_value TSRMLS_CC); + php_mysql_do_query_general(query, mysql_link, id, NULL, use_store, 0, +return_value TSRMLS_CC); } /* }}} */ @@ -1277,12 +1315,13 @@ /* }}} */ -/* {{{ proto resource mysql_db_query(string database_name, string query [, int link_identifier]) +/* {{{ proto resource mysql_db_query(string database_name, string query [, int +link_identifier] [, int restore_db]) Sends an SQL query to MySQL */ PHP_FUNCTION(mysql_db_query) { - zval **db, **query, **mysql_link; + zval **db, **query, **mysql_link, **restore_db; int id; + short do_restore=0; switch(ZEND_NUM_ARGS()) { case 2: @@ -1298,6 +1337,16 @@ } id = -1; break; + case 4: + if (zend_get_parameters_ex(4, &db, &query, &mysql_link, +&restore_db)==FAILURE) { + RETURN_FALSE; + } + id = -1; + convert_to_long_ex(restore_db); + if(restore_db > 0) { + do_restore=1; + } + break; default: WRONG_PARAM_COUNT; break; @@ -1307,7 +1356,7 @@ php_error_docref(NULL TSRMLS_CC, E_NOTICE, "This function is deprecated; use mysql_query()"); } - php_mysql_do_query_general(query, mysql_link, id, db, MYSQL_STORE_RESULT, return_value TSRMLS_CC); + php_mysql_do_query_general(query, mysql_link, id, db, MYSQL_STORE_RESULT, +do_restore, return_value TSRMLS_CC); } /* }}} */
--TEST-- Restore database argument on mysql_db_query --SKIPIF-- <?php if (!extension_loaded("mysql")) die("skip\n"); ?> --POST-- --GET-- --FILE-- <?php $user=''; $password=''; $host = 'localhost'; $socket = ''; if (file_exists($_ENV['HOME'] . '/' . '.my.cnf')) { $options = file($_ENV['HOME'] . '/' . '.my.cnf'); foreach($options AS $pair) { if(!preg_match("/^[^=]+=.+$/", $pair)) continue; list($key, $value) = preg_split("/\s?=\s?/", $pair); $value = preg_replace("/(\r?\n|\r)$/", "", trim($value)); if(strcasecmp($key, 'user') == 0) { $user = $value; } else if( strcasecmp($key, 'password') == 0) { $password = $value; } else if( strcasecmp($key, 'host') == 0) { $host = $value; } else if( strcasecmp($key, 'socket') == 0) { $socket = ':'.$value; } else if( (strcasecmp($key, 'port') == 0) and ( $host != 'localhost' or empty($socket) ) ) { $socket = ':'.$value; } } } $conn = mysql_connect("$host$socket", $user, $password); if(!$conn) die("skip\n"); mysql_select_db("test", $conn); $t1=mysql_result(mysql_query("SHOW TABLES", $conn), 0, 0); $t2=mysql_result(mysql_db_query("mysql", "SHOW TABLES", $conn, 1), 0, 0); $t3=mysql_result(mysql_query("SHOW TABLES", $conn), 0, 0); if($t1 == $t3) { echo "OK "; } else { echo "$t1 $t2 $t3 "; } mysql_close($conn); /* * Crash test, restore a db, when none is set. * Silenced warning. */ $conn2 = mysql_connect("$host$socket", $user, $password); if(!$conn2) die("Could not make second connection"); $t4=mysql_result(@mysql_db_query("test", "SHOW TABLES", $conn2, 1), 0, 0); $currdb = mysql_result(mysql_query("SELECT DATABASE()", $conn2), 0, 0); echo $currdb; ?> --EXPECT-- OK test
-- PHP Development Mailing List <http://www.php.net/> To unsubscribe, visit: http://www.php.net/unsub.php