summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ext/sqlite/php_sqlite.h1
-rw-r--r--ext/sqlite/sqlite.c150
-rwxr-xr-xext/sqlite/tests/sqlite_019.phpt46
-rwxr-xr-xext/sqlite/tests/sqlite_oo_021.phpt48
4 files changed, 211 insertions, 34 deletions
diff --git a/ext/sqlite/php_sqlite.h b/ext/sqlite/php_sqlite.h
index ea1aa45389..80336dded2 100644
--- a/ext/sqlite/php_sqlite.h
+++ b/ext/sqlite/php_sqlite.h
@@ -48,6 +48,7 @@ PHP_FUNCTION(sqlite_close);
PHP_FUNCTION(sqlite_query);
PHP_FUNCTION(sqlite_unbuffered_query);
PHP_FUNCTION(sqlite_array_query);
+PHP_FUNCTION(sqlite_single_query);
PHP_FUNCTION(sqlite_fetch_array);
PHP_FUNCTION(sqlite_fetch_string);
diff --git a/ext/sqlite/sqlite.c b/ext/sqlite/sqlite.c
index 6d403393ac..d97715dbd8 100644
--- a/ext/sqlite/sqlite.c
+++ b/ext/sqlite/sqlite.c
@@ -162,6 +162,7 @@ function_entry sqlite_functions[] = {
PHP_FE(sqlite_close, NULL)
PHP_FE(sqlite_query, NULL)
PHP_FE(sqlite_array_query, NULL)
+ PHP_FE(sqlite_single_query, NULL)
PHP_FE(sqlite_fetch_array, NULL)
PHP_FE(sqlite_fetch_string, NULL)
PHP_FE(sqlite_fetch_all, NULL)
@@ -199,6 +200,7 @@ function_entry sqlite_funcs_db[] = {
/* PHP_ME_MAPPING(close, sqlite_close, NULL)*/
PHP_ME_MAPPING(query, sqlite_query, NULL)
PHP_ME_MAPPING(array_query, sqlite_array_query, NULL)
+ PHP_ME_MAPPING(single_query, sqlite_single_query, NULL)
PHP_ME_MAPPING(unbuffered_query, sqlite_unbuffered_query, NULL)
PHP_ME_MAPPING(last_insert_rowid, sqlite_last_insert_rowid, NULL)
PHP_ME_MAPPING(create_aggregate, sqlite_create_aggregate, NULL)
@@ -1687,35 +1689,19 @@ PHP_FUNCTION(sqlite_array_query)
}
/* }}} */
-/* {{{ proto string sqlite_fetch_array(resource result [, bool decode_binary])
- Fetches first column of a result set as a string */
-PHP_FUNCTION(sqlite_fetch_string)
+/* {{{ php_sqlite_fetch_string */
+static void php_sqlite_fetch_string(struct php_sqlite_result *res, zend_bool decode_binary, zval *return_value TSRMLS_DC)
{
- zval *zres;
- zend_bool decode_binary = 1;
- struct php_sqlite_result *res;
+ const char **rowdata;
char *decoded = NULL;
int decoded_len;
- const char **rowdata;
- zval *object = getThis();
-
- if (object) {
- if (FAILURE == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "|b", &decode_binary)) {
- return;
- }
- RES_FROM_OBJECT(res, object);
- } else {
- if (FAILURE == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r|b", &zres, &decode_binary)) {
- return;
- }
- ZEND_FETCH_RESOURCE(res, struct php_sqlite_result *, &zres, -1, "sqlite result", le_sqlite_result);
- }
-
- /* check if there are any more rows on the cursor */
+
+ /* check range of the row */
if (res->curr_row >= res->nrows) {
+ /* no more */
RETURN_FALSE;
}
-
+
if (res->buffered) {
rowdata = (const char**)&res->table[res->curr_row * res->ncolumns];
} else {
@@ -1729,18 +1715,13 @@ PHP_FUNCTION(sqlite_fetch_string)
efree((char*)rowdata[0]);
rowdata[0] = NULL;
}
- } else {
- if (rowdata[0]) {
- decoded_len = strlen((char*)rowdata[0]);
- if (res->buffered) {
- decoded = estrndup((char*)rowdata[0], decoded_len);
- } else {
- decoded = (char*)rowdata[0];
- rowdata[0] = NULL;
- }
+ } else if (rowdata[0]) {
+ decoded_len = strlen((char*)rowdata[0]);
+ if (res->buffered) {
+ decoded = estrndup((char*)rowdata[0], decoded_len);
} else {
- decoded_len = 0;
- decoded = NULL;
+ decoded = (char*)rowdata[0];
+ rowdata[0] = NULL;
}
}
@@ -1759,6 +1740,107 @@ PHP_FUNCTION(sqlite_fetch_string)
}
/* }}} */
+
+/* {{{ proto array sqlite_single_query(resource db, string query [ , bool single_row, bool decode_binary ])
+ Executes a query against a given database and returns an array */
+PHP_FUNCTION(sqlite_single_query)
+{
+ zval *zdb, *ent;
+ struct php_sqlite_db *db;
+ struct php_sqlite_result *rres;
+ char *sql;
+ long sql_len;
+ char *errtext = NULL;
+ zend_bool decode_binary = 1;
+ zend_bool srow = 1;
+ zval *object = getThis();
+
+ if (object) {
+ if (FAILURE == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|bb", &sql, &sql_len, &srow, &decode_binary)) {
+ return;
+ }
+ RES_FROM_OBJECT(db, object);
+ } else {
+ if (FAILURE == zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET,
+ ZEND_NUM_ARGS() TSRMLS_CC, "sr|bb", &sql, &sql_len, &zdb, &srow, &decode_binary) &&
+ FAILURE == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs|bb", &zdb, &sql, &sql_len, &srow, &decode_binary)) {
+ return;
+ }
+ DB_FROM_ZVAL(db, &zdb);
+ }
+
+ /* avoid doing work if we can */
+ if (!return_value_used) {
+ db->last_err_code = sqlite_exec(db->db, sql, NULL, NULL, &errtext);
+
+ if (db->last_err_code != SQLITE_OK) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "%s", errtext);
+ sqlite_freemem(errtext);
+ }
+ return;
+ }
+
+ rres = (struct php_sqlite_result *)emalloc(sizeof(*rres));
+ sqlite_query(NULL, db, sql, sql_len, PHPSQLITE_NUM, 0, NULL, rres TSRMLS_CC);
+ if (db->last_err_code != SQLITE_OK) {
+ efree(rres);
+ RETURN_FALSE;
+ }
+
+ if (!srow) {
+ array_init(return_value);
+ }
+
+ while (rres->curr_row < rres->nrows) {
+ MAKE_STD_ZVAL(ent);
+ php_sqlite_fetch_string(rres, decode_binary, ent TSRMLS_DC);
+
+ /* if set and we only have 1 row in the result set, return the result as a string. */
+ if (srow) {
+ if (rres->curr_row == 1 && rres->curr_row >= rres->nrows) {
+ *return_value = *ent;
+ zval_copy_ctor(return_value);
+ zval_dtor(ent);
+ FREE_ZVAL(ent);
+ break;
+ } else {
+ srow = 0;
+ array_init(return_value);
+ }
+ }
+ add_next_index_zval(return_value, ent);
+ }
+
+ real_result_dtor(rres TSRMLS_CC);
+}
+/* }}} */
+
+
+/* {{{ proto string sqlite_fetch_array(resource result [, bool decode_binary])
+ Fetches first column of a result set as a string */
+PHP_FUNCTION(sqlite_fetch_string)
+{
+ zval *zres;
+ zend_bool decode_binary = 1;
+ struct php_sqlite_result *res;
+ zval *object = getThis();
+
+ if (object) {
+ if (FAILURE == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "|b", &decode_binary)) {
+ return;
+ }
+ RES_FROM_OBJECT(res, object);
+ } else {
+ if (FAILURE == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r|b", &zres, &decode_binary)) {
+ return;
+ }
+ ZEND_FETCH_RESOURCE(res, struct php_sqlite_result *, &zres, -1, "sqlite result", le_sqlite_result);
+ }
+
+ php_sqlite_fetch_string(res, decode_binary, return_value TSRMLS_DC);
+}
+/* }}} */
+
/* {{{ proto array sqlite_fetch_array(resource result [, int result_type, bool decode_binary])
Fetches the current row from a result set as an array */
PHP_FUNCTION(sqlite_current)
diff --git a/ext/sqlite/tests/sqlite_019.phpt b/ext/sqlite/tests/sqlite_019.phpt
new file mode 100755
index 0000000000..b67d5d2899
--- /dev/null
+++ b/ext/sqlite/tests/sqlite_019.phpt
@@ -0,0 +1,46 @@
+--TEST--
+sqlite: single query
+--SKIPIF--
+<?php # vim:ft=php
+if (!extension_loaded("sqlite")) print "skip"; ?>
+--FILE--
+<?php
+include "blankdb.inc";
+
+sqlite_query($db, "CREATE TABLE test_db ( id INTEGER PRIMARY KEY, data VARCHAR(100) )");
+for ($i = 0; $i < 10; $i++) {
+ sqlite_query($db, "INSERT INTO test_db (data) VALUES('{$i}data')");
+}
+sqlite_query($db, "INSERT INTO test_db (data) VALUES(NULL)");
+
+var_dump(sqlite_single_query($db, "SELECT id FROM test_db WHERE id=5"));
+var_dump(sqlite_single_query($db, "SELECT * FROM test_db WHERE id=4"));
+var_dump(sqlite_single_query($db, "SELECT data FROM test_db WHERE id=6"));
+var_dump(sqlite_single_query($db, "SELECT * FROM test_db WHERE id < 5"));
+var_dump(sqlite_single_query($db, "SELECT * FROM test db WHERE id < 4"));
+var_dump(sqlite_single_query($db, "SELECT * FROM test_db WHERE id=999999"));
+var_dump(sqlite_single_query($db, "SELECT id FROM test_db WHERE id=5", FALSE));
+
+?>
+--EXPECTF--
+string(1) "5"
+string(1) "4"
+string(5) "5data"
+array(4) {
+ [0]=>
+ string(1) "1"
+ [1]=>
+ string(1) "2"
+ [2]=>
+ string(1) "3"
+ [3]=>
+ string(1) "4"
+}
+
+Warning: sqlite_single_query(): no such table: test in %s on line %d
+bool(false)
+NULL
+array(1) {
+ [0]=>
+ string(1) "5"
+}
diff --git a/ext/sqlite/tests/sqlite_oo_021.phpt b/ext/sqlite/tests/sqlite_oo_021.phpt
new file mode 100755
index 0000000000..496514b622
--- /dev/null
+++ b/ext/sqlite/tests/sqlite_oo_021.phpt
@@ -0,0 +1,48 @@
+--TEST--
+sqlite-oo: single query
+--SKIPIF--
+<?php # vim:ft=php
+if (!extension_loaded("sqlite")) print "skip"; ?>
+--FILE--
+<?php
+include "blankdb_oo.inc";
+
+$db->query("CREATE TABLE test_db ( id INTEGER PRIMARY KEY, data VARCHAR(100) )");
+for ($i = 0; $i < 10; $i++) {
+ $db->query("INSERT INTO test_db (data) VALUES('{$i}data')");
+}
+$db->query("INSERT INTO test_db (data) VALUES(NULL)");
+
+var_dump($db->single_query("SELECT id FROM test_db WHERE id=5"));
+var_dump($db->single_query("SELECT * FROM test_db WHERE id=4"));
+var_dump($db->single_query("SELECT data FROM test_db WHERE id=6"));
+var_dump($db->single_query("SELECT * FROM test_db WHERE id < 5"));
+var_dump($db->single_query("SELECT * FROM test db WHERE id < 4"));
+var_dump($db->single_query("SELECT * FROM test_db WHERE id=999999"));
+var_dump($db->single_query("SELECT id FROM test_db WHERE id=5", FALSE));
+
+echo "DONE!\n";
+?>
+--EXPECTF--
+string(1) "5"
+string(1) "4"
+string(5) "5data"
+array(4) {
+ [0]=>
+ string(1) "1"
+ [1]=>
+ string(1) "2"
+ [2]=>
+ string(1) "3"
+ [3]=>
+ string(1) "4"
+}
+
+Warning: single_query(): no such table: test in %s on line %d
+bool(false)
+NULL
+array(1) {
+ [0]=>
+ string(1) "5"
+}
+DONE!