helly Sat Sep 6 15:34:49 2003 EDT
Modified files:
/php-src/ext/mysqli mysqli.c mysqli_api.c mysqli_nonapi.c
php_mysqli.h
Log:
Modify mysqli_fetch_object() to be able to instantiate a selected class and
pass parameters to the constructor.
Index: php-src/ext/mysqli/mysqli.c
diff -u php-src/ext/mysqli/mysqli.c:1.15 php-src/ext/mysqli/mysqli.c:1.16
--- php-src/ext/mysqli/mysqli.c:1.15 Tue Jul 15 06:37:19 2003
+++ php-src/ext/mysqli/mysqli.c Sat Sep 6 15:34:48 2003
@@ -15,7 +15,7 @@
| Author: Georg Richter <[EMAIL PROTECTED]> |
+----------------------------------------------------------------------+
- $Id: mysqli.c,v 1.15 2003/07/15 10:37:19 georg Exp $
+ $Id: mysqli.c,v 1.16 2003/09/06 19:34:48 helly Exp $
*/
#ifdef HAVE_CONFIG_H
@@ -29,6 +29,7 @@
#include "ext/standard/info.h"
#include "ext/standard/php_string.h"
#include "php_mysqli.h"
+#include "zend_default_classes.h"
#define MYSQLI_STORE_RESULT 0
#define MYSQLI_USE_RESULT 1
@@ -371,7 +372,7 @@
/* {{{ php_mysqli_fetch_into_hash
*/
-void php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAMETERS, int override_flags)
+void php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAMETERS, int override_flags, int
into_object)
{
MYSQL_RES *result;
zval *mysql_result;
@@ -383,17 +384,38 @@
unsigned long *field_len;
PR_RESULT *prresult;
PR_COMMAND *prcommand;
+ zval *ctor_params = NULL;
+ zend_class_entry *ce = NULL;
- if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O|l",
&mysql_result, mysqli_result_class_entry, &fetchtype) == FAILURE) {
- return;
- }
-
- if (ZEND_NUM_ARGS() < 2 && !override_flags) {
- fetchtype = MYSQLI_BOTH;
- }
+ if (into_object) {
+ char *class_name;
+ int class_name_len;
- if (override_flags) {
- fetchtype = override_flags;
+ if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(),
"O|sz", &mysql_result, mysqli_result_class_entry, &class_name, &class_name_len,
&ctor_params) == FAILURE) {
+ return;
+ }
+ if (ZEND_NUM_ARGS() < (getThis() ? 1 : 2)) {
+ ce = zend_standard_class_def;
+ } else {
+ ce = zend_fetch_class(class_name, class_name_len,
ZEND_FETCH_CLASS_AUTO TSRMLS_CC);
+ }
+ if (!ce) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Could not find
class '%s'", class_name);
+ return;
+ }
+ fetchtype = MYSQLI_ASSOC;
+ } else {
+ if (override_flags) {
+ if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC,
getThis(), "O", &mysql_result, mysqli_result_class_entry) == FAILURE) {
+ return;
+ }
+ fetchtype = override_flags;
+ } else {
+ fetchtype = MYSQLI_NUM;
+ if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC,
getThis(), "O|l", &mysql_result, mysqli_result_class_entry, &fetchtype) == FAILURE) {
+ return;
+ }
+ }
}
MYSQLI_FETCH_RESOURCE(result, MYSQL_RES *, prresult, PR_RESULT *,
&mysql_result, "mysqli_result");
@@ -436,6 +458,70 @@
if (fetchtype & MYSQLI_ASSOC) {
add_assoc_null(return_value, fields[i].name);
}
+ }
+ }
+
+ if (into_object) {
+ zval dataset = *return_value;
+ zend_fcall_info fci;
+ zend_fcall_info_cache fcc;
+ zval *retval_ptr;
+
+ object_and_properties_init(return_value, ce, NULL);
+ zend_merge_properties(return_value, Z_ARRVAL(dataset), 1 TSRMLS_CC);
+
+ if (ce->constructor) {
+ fci.size = sizeof(fci);
+ fci.function_table = &ce->function_table;
+ fci.function_name = NULL;
+ fci.symbol_table = NULL;
+ fci.object_pp = &return_value;
+ fci.retval_ptr_ptr = &retval_ptr;
+ if (ctor_params && Z_TYPE_P(ctor_params) != IS_NULL) {
+ if (Z_TYPE_P(ctor_params) == IS_ARRAY) {
+ HashTable *ht = Z_ARRVAL_P(ctor_params);
+ Bucket *p;
+
+ fci.param_count = 0;
+ fci.params = emalloc(sizeof(zval*) *
ht->nNumOfElements);
+ p = ht->pListHead;
+ while (p != NULL) {
+ fci.params[fci.param_count++] =
(zval**)p->pData;
+ p = p->pListNext;
+ }
+ } else {
+ /* Two problems why we throw exceptions here:
PHP is typeless
+ * and hence passing one argument that's not
an array could be
+ * by mistake and the other way round is
possible, too. The
+ * single value is an array. Also we'd have to
make that one
+ * argument passed by reference.
+ */
+
zend_throw_exception(zend_exception_get_default(), "Parameter ctor_params must be an
array", 0 TSRMLS_CC);
+ return;
+ }
+ } else {
+ fci.param_count = 0;
+ fci.params = NULL;
+ }
+ fci.no_separation = 1;
+
+ fcc.initialized = 1;
+ fcc.function_handler = ce->constructor;
+ fcc.calling_scope = EG(scope);
+ fcc.object_pp = &return_value;
+
+ if (zend_call_function(&fci, &fcc TSRMLS_CC) == FAILURE) {
+ zend_throw_exception_ex(zend_exception_get_default(),
0 TSRMLS_CC, "Could not execute %s::%s()", ce->name,
ce->constructor->common.function_name);
+ } else {
+ if (retval_ptr) {
+ zval_ptr_dtor(&retval_ptr);
+ }
+ }
+ if (fci.params) {
+ efree(fci.params);
+ }
+ } else if (ctor_params) {
+ zend_throw_exception_ex(zend_exception_get_default(), 0
TSRMLS_CC, "Class %s does not have a constructor hence you cannot use ctor_params",
ce->name);
}
}
Index: php-src/ext/mysqli/mysqli_api.c
diff -u php-src/ext/mysqli/mysqli_api.c:1.43 php-src/ext/mysqli/mysqli_api.c:1.44
--- php-src/ext/mysqli/mysqli_api.c:1.43 Sun Aug 31 07:03:05 2003
+++ php-src/ext/mysqli/mysqli_api.c Sat Sep 6 15:34:48 2003
@@ -15,7 +15,7 @@
| Author: Georg Richter <[EMAIL PROTECTED]> |
+----------------------------------------------------------------------+
- $Id: mysqli_api.c,v 1.43 2003/08/31 11:03:05 helly Exp $
+ $Id: mysqli_api.c,v 1.44 2003/09/06 19:34:48 helly Exp $
*/
#ifdef HAVE_CONFIG_H
@@ -899,7 +899,7 @@
Get a result row as an enumerated array */
PHP_FUNCTION(mysqli_fetch_row)
{
- php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAM_PASSTHRU, MYSQLI_NUM);
+ php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAM_PASSTHRU, MYSQLI_NUM, 0);
}
/* }}} */
Index: php-src/ext/mysqli/mysqli_nonapi.c
diff -u php-src/ext/mysqli/mysqli_nonapi.c:1.15 php-src/ext/mysqli/mysqli_nonapi.c:1.16
--- php-src/ext/mysqli/mysqli_nonapi.c:1.15 Fri Sep 5 15:27:26 2003
+++ php-src/ext/mysqli/mysqli_nonapi.c Sat Sep 6 15:34:48 2003
@@ -15,7 +15,7 @@
| Author: Georg Richter <[EMAIL PROTECTED]> |
+----------------------------------------------------------------------+
- $Id: mysqli_nonapi.c,v 1.15 2003/09/05 19:27:26 helly Exp $
+ $Id: mysqli_nonapi.c,v 1.16 2003/09/06 19:34:48 helly Exp $
*/
#ifdef HAVE_CONFIG_H
@@ -120,7 +120,7 @@
Fetch a result row as an associative array, a numeric array, or both */
PHP_FUNCTION(mysqli_fetch_array)
{
- php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAM_PASSTHRU, 0);
+ php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAM_PASSTHRU, 0, 0);
}
/* }}} */
@@ -128,19 +128,15 @@
Fetch a result row as an associative array */
PHP_FUNCTION(mysqli_fetch_assoc)
{
- php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAM_PASSTHRU, MYSQLI_ASSOC);
+ php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAM_PASSTHRU, MYSQLI_ASSOC, 0);
}
/* }}} */
-/* {{{ proto array mysqli_fetch_object (object result)
+/* {{{ proto array mysqli_fetch_object (object result [, string class_name [,
NULL|array ctor_params]])
Fetch a result row as an object */
PHP_FUNCTION(mysqli_fetch_object)
{
- php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAM_PASSTHRU, MYSQLI_ASSOC);
-
- if (Z_TYPE_P(return_value) == IS_ARRAY) {
- object_and_properties_init(return_value, ZEND_STANDARD_CLASS_DEF_PTR,
Z_ARRVAL_P(return_value));
- }
+ php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAM_PASSTHRU, MYSQLI_ASSOC, 1);
}
/* }}} */
Index: php-src/ext/mysqli/php_mysqli.h
diff -u php-src/ext/mysqli/php_mysqli.h:1.20 php-src/ext/mysqli/php_mysqli.h:1.21
--- php-src/ext/mysqli/php_mysqli.h:1.20 Fri Jul 18 02:17:39 2003
+++ php-src/ext/mysqli/php_mysqli.h Sat Sep 6 15:34:48 2003
@@ -15,7 +15,7 @@
| Author: Georg Richter <[EMAIL PROTECTED]> |
+----------------------------------------------------------------------+
- $Id: php_mysqli.h,v 1.20 2003/07/18 06:17:39 georg Exp $
+ $Id: php_mysqli.h,v 1.21 2003/09/06 19:34:48 helly Exp $
*/
/* A little hack to prevent build break, when mysql is used together with
@@ -90,7 +90,7 @@
extern function_entry mysqli_link_methods[];
extern function_entry mysqli_stmt_methods[];
extern function_entry mysqli_result_methods[];
-extern void php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAMETERS, int flag);
+extern void php_mysqli_fetch_into_hash(INTERNAL_FUNCTION_PARAMETERS, int
override_flag, int into_object);
extern void php_clear_stmt_bind(STMT *stmt);
extern void php_free_stmt_bind_buffer(BIND_BUFFER bbuf, int type);
--
PHP CVS Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php