From: thekid@thekid.de
Operating system: All
PHP version: 4.0CVS-2002-05-02
PHP Bug Type: Feature/Change Request
Bug description: [Sybase-CT] sybase_fetch_row() and types
First of all: I'm putting this in here since my mail to
php-dev@list.php.net was rejected thanks to an overefficient spam
protection filter (kundenserver.de).
Please see http://relaytest.kundenserver.de/ for
details.
Here's my mail:
--------------------------------------------------------
Hello,
as you might know, the sybase extension is very bad when it comes to
data types, since it returns almost everything as a string, except for
NULL values, which become FALSE.
Short example:
--- SQL -------------------------------
select
NULL as "null",
"string" as string,
6100 as integer,
6.1 as float,
getdate() as date
--- var_dump() of resultset -----------
array(10) {
[0]=>
string(0) ""
["null"]=>
string(0) ""
[1]=>
string(6) "string"
["string"]=>
string(6) "string"
[2]=>
string(4) "6100"
["integer"]=>
string(4) "6100"
[3]=>
string(3) "6.1"
["float"]=>
string(3) "6.1"
[4]=>
string(4) " :"
["date"]=>
string(4) " :"
}
Well, when writing applications communicating via SOAP with type-secure
languages - in my case PHP as server, Java as client - this comes quite
unhandy, since on ends up going through the resultset and changing types
for each entry, thus producing unnecessary overhead.
Something like this would be much nicer:
--- var_dump() of resultset -----------
array(10) {
[0]=>
NULL
["null"]=>
NULL
[1]=>
string(6) "string"
["string"]=>
string(6) "string"
[2]=>
int(6100)
["integer"]=>
int(6100)
[3]=>
float(6.1)
["float"]=>
float(6.1)
[4]=>
string(19) "May 02 2002 11:15AM"
["date"]=>
string(19) "May 02 2002 11:15AM"
}
OK, so I went ahead and patched ext/sybase_ct/php_sybase_ct.c to
accomplish my wishes. I must admit though I'm a total lamer when it goes
to writing C sourcecode and utilizing the Zend API, so - after studying
a couple of files, wrote a couple of lines, compiled, watched the thing
segfault once or twice, I finally managed to get a running PHP binary
and a sybase_ct.so compiled.
Attached is the patch, however ugly it may be, it compiles and produces
the resultset as intended - maybe you guys want to take a look at it
and correct it to be much nicer and much better:-)
--
Timm Friebe
Systems developer Schlund+Partner AG
Karlsruhe, Germany
[patch-ext_sybase_ct_php_sybase_ct.c]
--- php4-200205012100/ext/sybase_ct/php_sybase_ct.c Tue Mar 12 21:34:06
2002
+++ __build__/ext/sybase_ct/php_sybase_ct.c Thu May 2 10:47:53 2002
@@ -953,33 +953,33 @@
break;
case CS_SMALLINT_TYPE:
datafmt[i].maxlength = 7;
- numerics[i] = 1;
+ numerics[i] = 1;
break;
case CS_INT_TYPE:
datafmt[i].maxlength = 12;
- numerics[i] = 1;
+ numerics[i] = 1;
break;
case CS_REAL_TYPE:
case CS_FLOAT_TYPE:
datafmt[i].maxlength = 24;
- numerics[i] = 1;
- break;
+ numerics[i] = 2;
+ break;
case CS_MONEY_TYPE:
case CS_MONEY4_TYPE:
datafmt[i].maxlength = 24;
- numerics[i] = 0;
+ numerics[i] = 0;
break;
case CS_DATETIME_TYPE:
case CS_DATETIME4_TYPE:
datafmt[i].maxlength = 30;
numerics[i] = 0;
- break;
+ break;
case CS_NUMERIC_TYPE:
case CS_DECIMAL_TYPE:
datafmt[i].maxlength = datafmt[i].precision + 3;
- numerics[i] = 1;
+ numerics[i] = 2;
break;
- default:
+ default:
datafmt[i].maxlength++;
numerics[i] = 0;
break;
@@ -1004,11 +1004,19 @@
result->data[i] = (pval *) emalloc(sizeof(pval)*num_fields);
for (j=0; j<num_fields; j++) {
if (indicators[j] == -1) { /* null value */
- ZVAL_FALSE(&result->data[i][j]);
+ ZVAL_NULL(&result->data[i][j]);
} else {
Z_STRLEN(result->data[i][j]) = lengths[j]-1; /* we don't need the
NULL in the length */
Z_STRVAL(result->data[i][j]) = estrndup(tmp_buffer[j], lengths[j]);
Z_TYPE(result->data[i][j]) = IS_STRING;
+
+ // Here we go, i want those types!:-)
+ // Perhaps there is a nicer way of doing this, instead of making
strings first
+ // and then converting them back, but I'm a Zend-API-lamer.
+ switch (numerics[j]) {
+ case 1:
convert_to_long(&result->data[i][j]); break;
+ case 2:
convert_to_double(&result->data[i][j]); numerics[j]= 1; break;
+ }
}
}
}
--
Edit bug report at http://bugs.php.net/?id=16960&edit=1
--
Fixed in CVS: http://bugs.php.net/fix.php?id=16960&r=fixedcvs
Fixed in release: http://bugs.php.net/fix.php?id=16960&r=alreadyfixed
Need backtrace: http://bugs.php.net/fix.php?id=16960&r=needtrace
Try newer version: http://bugs.php.net/fix.php?id=16960&r=oldversion
Not developer issue: http://bugs.php.net/fix.php?id=16960&r=support
Expected behavior: http://bugs.php.net/fix.php?id=16960&r=notwrong
Not enough info: http://bugs.php.net/fix.php?id=16960&r=notenoughinfo
Submitted twice: http://bugs.php.net/fix.php?id=16960&r=submittedtwice