diff options
-rw-r--r-- | ext/oci8/oci8.c | 8 | ||||
-rw-r--r-- | ext/oci8/oci8_statement.c | 29 | ||||
-rw-r--r-- | ext/oci8/package.xml | 8 | ||||
-rw-r--r-- | ext/oci8/php_oci8.h | 2 | ||||
-rw-r--r-- | ext/oci8/tests/bind_boolean_1.phpt | 138 | ||||
-rw-r--r-- | ext/oci8/tests/error_bind_2.phpt | 63 | ||||
-rw-r--r-- | ext/oci8/tests/error_bind_3.phpt | 48 |
7 files changed, 282 insertions, 14 deletions
diff --git a/ext/oci8/oci8.c b/ext/oci8/oci8.c index c3ca7a8172..a890c94dab 100644 --- a/ext/oci8/oci8.c +++ b/ext/oci8/oci8.c @@ -26,8 +26,6 @@ +----------------------------------------------------------------------+ */ -/* $Id$ */ - #ifdef HAVE_CONFIG_H #include "config.h" #endif @@ -1251,6 +1249,9 @@ PHP_MINIT_FUNCTION(oci) REGISTER_LONG_CONSTANT("SQLT_BDOUBLE",SQLT_BDOUBLE, CONST_CS | CONST_PERSISTENT); REGISTER_LONG_CONSTANT("SQLT_BFLOAT",SQLT_BFLOAT, CONST_CS | CONST_PERSISTENT); #endif +#if defined(OCI_MAJOR_VERSION) && OCI_MAJOR_VERSION >= 12 + REGISTER_LONG_CONSTANT("SQLT_BOL",SQLT_BOL, CONST_CS | CONST_PERSISTENT); +#endif REGISTER_LONG_CONSTANT("OCI_B_NTY",SQLT_NTY, CONST_CS | CONST_PERSISTENT); REGISTER_LONG_CONSTANT("SQLT_NTY",SQLT_NTY, CONST_CS | CONST_PERSISTENT); @@ -1265,6 +1266,9 @@ PHP_MINIT_FUNCTION(oci) REGISTER_LONG_CONSTANT("OCI_B_BIN",SQLT_BIN, CONST_CS | CONST_PERSISTENT); REGISTER_LONG_CONSTANT("OCI_B_INT",SQLT_INT, CONST_CS | CONST_PERSISTENT); REGISTER_LONG_CONSTANT("OCI_B_NUM",SQLT_NUM, CONST_CS | CONST_PERSISTENT); +#if defined(OCI_MAJOR_VERSION) && OCI_MAJOR_VERSION >= 12 + REGISTER_LONG_CONSTANT("OCI_B_BOL",SQLT_BOL, CONST_CS | CONST_PERSISTENT); +#endif /* for OCIFetchStatement */ REGISTER_LONG_CONSTANT("OCI_FETCHSTATEMENT_BY_COLUMN", PHP_OCI_FETCHSTATEMENT_BY_COLUMN, CONST_CS | CONST_PERSISTENT); diff --git a/ext/oci8/oci8_statement.c b/ext/oci8/oci8_statement.c index 56882cf908..520809c81d 100644 --- a/ext/oci8/oci8_statement.c +++ b/ext/oci8/oci8_statement.c @@ -928,19 +928,16 @@ int php_oci_bind_pre_exec(void *data, void *result TSRMLS_DC) } break; + case SQLT_CHR: + case SQLT_AFC: case SQLT_INT: case SQLT_NUM: - if (Z_TYPE_P(bind->zval) == IS_RESOURCE || Z_TYPE_P(bind->zval) == IS_OBJECT) { - php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid variable used for bind"); - *(int *)result = 1; - } - break; - +#if defined(OCI_MAJOR_VERSION) && OCI_MAJOR_VERSION >= 12 + case SQLT_BOL: +#endif case SQLT_LBI: case SQLT_BIN: case SQLT_LNG: - case SQLT_AFC: - case SQLT_CHR: if (Z_TYPE_P(bind->zval) == IS_RESOURCE || Z_TYPE_P(bind->zval) == IS_OBJECT) { php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid variable used for bind"); *(int *)result = 1; @@ -955,7 +952,7 @@ int php_oci_bind_pre_exec(void *data, void *result TSRMLS_DC) break; } - /* reset all bind stuff to a normal state..-. */ + /* reset all bind stuff to a normal state... */ bind->indicator = 0; return 0; @@ -1185,6 +1182,20 @@ int php_oci_bind_by_name(php_oci_statement *statement, char *name, int name_len, } break; +#if defined(OCI_MAJOR_VERSION) && OCI_MAJOR_VERSION >= 12 + case SQLT_BOL: + if (Z_TYPE_P(var) == IS_RESOURCE || Z_TYPE_P(var) == IS_OBJECT) { + php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid variable used for bind"); + return 1; + } + convert_to_boolean(var); + bind_data = (int *)&Z_LVAL_P(var); + value_sz = sizeof(int); + + mode = OCI_DEFAULT; + break; +#endif + default: php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unknown or unsupported datatype given: %d", (int)type); return 1; diff --git a/ext/oci8/package.xml b/ext/oci8/package.xml index 8e55b9abd5..d81d896f13 100644 --- a/ext/oci8/package.xml +++ b/ext/oci8/package.xml @@ -45,7 +45,7 @@ libraries are available. <active>no</active> </lead> - <date>2013-10-22</date> + <date>2014-02-10</date> <time>12:00:00</time> <version> @@ -58,7 +58,8 @@ libraries are available. </stability> <license uri="http://www.php.net/license">PHP</license> <notes> - Build change: Fix source variable definition for C89 compatibility +Added oci_bind_by_name() support for PL/SQL BOOLEAN type +Build change: Fix source variable definition for C89 compatibility </notes> <contents> <dir name="/"> @@ -91,6 +92,7 @@ libraries are available. <file name="b47243_1.phpt" role="test" /> <file name="b47243_2.phpt" role="test" /> <file name="b47243_3.phpt" role="test" /> + <file name="bind_boolean_1.phpt" role="test" /> <file name="bind_char_1_11gR1.phpt" role="test" /> <file name="bind_char_1.phpt" role="test" /> <file name="bind_char_2_11gR1.phpt" role="test" /> @@ -268,6 +270,8 @@ libraries are available. <file name="error2.phpt" role="test" /> <file name="error3.phpt" role="test" /> <file name="error_bind.phpt" role="test" /> + <file name="error_bind_2.phpt" role="test" /> + <file name="error_bind_3.phpt" role="test" /> <file name="error_old.phpt" role="test" /> <file name="error_parse.phpt" role="test" /> <file name="error.phpt" role="test" /> diff --git a/ext/oci8/php_oci8.h b/ext/oci8/php_oci8.h index 63924eca01..17061066d2 100644 --- a/ext/oci8/php_oci8.h +++ b/ext/oci8/php_oci8.h @@ -45,7 +45,7 @@ */ #undef PHP_OCI8_VERSION #endif -#define PHP_OCI8_VERSION "2.0.7-dev" +#define PHP_OCI8_VERSION "2.0.7" extern zend_module_entry oci8_module_entry; #define phpext_oci8_ptr &oci8_module_entry diff --git a/ext/oci8/tests/bind_boolean_1.phpt b/ext/oci8/tests/bind_boolean_1.phpt new file mode 100644 index 0000000000..49ac03c882 --- /dev/null +++ b/ext/oci8/tests/bind_boolean_1.phpt @@ -0,0 +1,138 @@ +--TEST-- +Basic PL/SQL "BOOLEAN" (SQLT_BOL) bind test +--SKIPIF-- +<?php +if (!extension_loaded('oci8')) die ("skip no oci8 extension"); +require(dirname(__FILE__).'/connect.inc'); +preg_match('/.*Release ([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)*/', oci_server_version($c), $matches); +if (!(isset($matches[0]) && $matches[1] >= 12)) { + die("skip expected output only valid when using Oracle Database 12c or greater"); +} +preg_match('/^[[:digit:]]+/', oci_client_version(), $matches); +if (!(isset($matches[0]) && $matches[0] >= 12)) { + die("skip works only with Oracle 12c or greater version of Oracle client libraries"); +} +?> +--FILE-- +<?php + +require(dirname(__FILE__).'/connect.inc'); + +// Run Test + +echo "Test 1\n"; + +$sql = "begin + :output1 := true; + :output2 := false; + end;"; + +$s = oci_parse($c, $sql); +oci_bind_by_name($s, ':output1', $output1, -1, OCI_B_BOL); +oci_bind_by_name($s, ':output2', $output2, -1, OCI_B_BOL); +oci_execute($s); +var_dump($output1); +var_dump($output2); + +echo "Test 2\n"; + +$b = "abc"; // bind var type will change +$sql = "begin :b := true; end;"; +$s = oci_parse($c, $sql); +oci_bind_by_name($s, ':b', $b, -1, OCI_B_BOL); +oci_execute($s); +var_dump($b); + + +echo "Test 3\n"; + +$sql = + "begin + if (:input < 10) then + :output := true; + else + :output := false; + end if; +end;"; +$s = oci_parse($c, $sql); +oci_bind_by_name($s, ':output', $output, -1, OCI_B_BOL); +for ($input = 5; $input < 15; ++$input) { + oci_bind_by_name($s, ':input', $input); + oci_execute($s); + var_dump($output); +} + +echo "Test 4\n"; + +$sql = +"begin + if (mod(:userid,2) = 0) then + :b := true; + else + :b := false; + end if; +end;"; +$s = oci_parse($c, $sql); +oci_bind_by_name($s, ':b', $b, -1, OCI_B_BOL); +for ($userid = 1; $userid <= 10; ++$userid) { + oci_bind_by_name($s, ':userid', $userid, -1, SQLT_INT); + oci_execute($s); + var_dump($b); +} + +echo "Test 5\n"; + +$sql = +"declare + l boolean; +begin + l := :b1; + :b1 := :b2; + :b2 := l; +end;"; +$s = oci_parse($c, $sql); +$b1 = true; +$b2 = false; +var_dump($b1, $b2); +oci_bind_by_name($s, ':b1', $b1, -1, OCI_B_BOL); +oci_bind_by_name($s, ':b2', $b2, -1, OCI_B_BOL); +oci_execute($s); +var_dump($b1, $b2); + +?> +===DONE=== +<?php exit(0); ?> +--EXPECTF-- +Test 1 +bool(true) +bool(false) +Test 2 +bool(true) +Test 3 +bool(true) +bool(true) +bool(true) +bool(true) +bool(true) +bool(false) +bool(false) +bool(false) +bool(false) +bool(false) +Test 4 +bool(false) +bool(true) +bool(false) +bool(true) +bool(false) +bool(true) +bool(false) +bool(true) +bool(false) +bool(true) +Test 5 +bool(true) +bool(false) +bool(false) +bool(true) +===DONE=== diff --git a/ext/oci8/tests/error_bind_2.phpt b/ext/oci8/tests/error_bind_2.phpt new file mode 100644 index 0000000000..642716887e --- /dev/null +++ b/ext/oci8/tests/error_bind_2.phpt @@ -0,0 +1,63 @@ +--TEST-- +Test some more oci_bind_by_name error conditions +--SKIPIF-- +<?php +if (!extension_loaded('oci8')) die ("skip no oci8 extension"); +$target_dbs = array('oracledb' => true, 'timesten' => true); // test runs on these DBs +require(dirname(__FILE__).'/skipif.inc'); +preg_match('/.*Release ([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)*/', oci_server_version($c), $matches); +if (!(isset($matches[0]) && $matches[1] >= 12)) { + die("skip expected output only valid when using Oracle Database 12c or greater"); +} +preg_match('/^[[:digit:]]+/', oci_client_version(), $matches); +if (!(isset($matches[0]) && $matches[0] >= 12)) { + die("skip works only with Oracle 12c or greater version of Oracle client libraries"); +} +?> +--FILE-- +<?php + +require(dirname(__FILE__).'/connect.inc'); + +// Initialization + +$stmtarray = array( + "drop table error_bind_2_tab", + "create table error_bind_2_tab(name varchar(10))" +); +oci8_test_sql_execute($c, $stmtarray); + +echo "Test 1 - SQLT_BOL\n"; + +unset($name); +$stmt = oci_parse($c, "insert into error_bind_2_tab values (:name)"); +oci_bind_by_name($stmt, ":name", $name, -1, SQLT_BOL); +$name=$c; +var_dump(oci_execute($stmt)); + +echo "Test 2 - SQLT_BOL\n"; + +unset($name); +$stmt = oci_parse($c, "insert into error_bind_2_tab values (:name)"); +$name=$c; +oci_bind_by_name($stmt, ":name", $name, -1, SQLT_BOL); + +// Clean up + +$stmtarray = array( + "drop table error_bind_2_tab", +); +oci8_test_sql_execute($c, $stmtarray); + +echo "Done\n"; + +?> +--EXPECTF-- +Test 1 - SQLT_BOL + +Warning: oci_execute(): Invalid variable used for bind in %s on line %d +bool(false) +Test 2 - SQLT_BOL + +Warning: oci_bind_by_name(): Invalid variable used for bind in %s on line %d +Done diff --git a/ext/oci8/tests/error_bind_3.phpt b/ext/oci8/tests/error_bind_3.phpt new file mode 100644 index 0000000000..7522dfe60a --- /dev/null +++ b/ext/oci8/tests/error_bind_3.phpt @@ -0,0 +1,48 @@ +--TEST-- +Test some more oci_bind_by_name error conditions +--SKIPIF-- +<?php +if (!extension_loaded('oci8')) die ("skip no oci8 extension"); +$target_dbs = array('oracledb' => true, 'timesten' => true); // test runs on these DBs +require(dirname(__FILE__).'/skipif.inc'); +preg_match('/.*Release ([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)*/', oci_server_version($c), $matches); +if (!(isset($matches[0]) && $matches[1] >= 12)) { + die("skip expected output only valid when using Oracle Database 12c or greater"); +} +preg_match('/^[[:digit:]]+/', oci_client_version(), $matches); +if (!(isset($matches[0]) && $matches[0] >= 12)) { + die("skip works only with Oracle 12c or greater version of Oracle client libraries"); +} +?> +--FILE-- +<?php + +require(dirname(__FILE__).'/connect.inc'); + +$sql = "begin + :output1 := 99; + :output2 := 'abc'; + end;"; + +$s = oci_parse($c, $sql); +oci_bind_by_name($s, ':output1', $output1, -1, OCI_B_BOL); +oci_bind_by_name($s, ':output2', $output2, -1, OCI_B_BOL); +oci_execute($s); +var_dump($output1); +var_dump($output2); + +echo "Done\n"; + +?> +--EXPECTF-- +Warning: oci_execute(): ORA-06550: line %d, column %d: +PLS-00382: %s +ORA-06550: line %d, column %d: +PL/SQL: %s +ORA-06550: line %d, column %d: +PLS-00382: %s +ORA-06550: line %d, column %d: +PL/SQL: %s in %s on line %d +bool(false) +bool(false) +Done |