@@ -477,9 +477,9 @@ Handle<Value> MysqlStatement::FetchAllSync(const Arguments& args) {
477
477
478
478
MYSQLSTMT_MUSTBE_INITIALIZED;
479
479
MYSQLSTMT_MUSTBE_PREPARED;
480
+ MYSQLSTMT_MUSTBE_STORED;
480
481
481
- /* Get meta data for binding buffers */
482
-
482
+ // Get fields count for binding buffers
483
483
unsigned int field_count = mysql_stmt_field_count (stmt->_stmt );
484
484
485
485
uint32_t i = 0 , j = 0 ;
@@ -490,52 +490,84 @@ Handle<Value> MysqlStatement::FetchAllSync(const Arguments& args) {
490
490
MYSQL_RES *meta;
491
491
MYSQL_FIELD *fields;
492
492
493
- /* Buffers */
493
+ // Buffers
494
494
int int_data[field_count];
495
- signed char tiny_data [field_count];
495
+ my_ulonglong my_ulonglong_data [field_count];
496
496
double double_data[field_count];
497
497
char str_data[field_count][64 ];
498
498
MYSQL_TIME date_data[field_count];
499
499
memset (date_data, 0 , sizeof (date_data));
500
500
501
501
memset (bind, 0 , sizeof (bind));
502
502
503
+ // Get meta data for binding buffers
503
504
meta = mysql_stmt_result_metadata (stmt->_stmt );
504
505
505
506
fields = meta->fields ;
506
507
while (i < field_count) {
507
508
bind[i].buffer_type = fields[i].type ;
508
509
509
510
switch (fields[i].type ) {
510
- case MYSQL_TYPE_NULL:
511
- case MYSQL_TYPE_SHORT:
512
- case MYSQL_TYPE_LONG:
513
- case MYSQL_TYPE_LONGLONG:
514
- case MYSQL_TYPE_INT24:
511
+ case MYSQL_TYPE_NULL: // NULL-type field
512
+ // TODO: Implement this
513
+ bind[i].buffer = &int_data[i];
514
+ break ;
515
+ case MYSQL_TYPE_TINY: // TINYINT field
516
+ case MYSQL_TYPE_SHORT: // SMALLINT field
517
+ case MYSQL_TYPE_LONG: // INTEGER field
518
+ case MYSQL_TYPE_INT24: // MEDIUMINT field
519
+ case MYSQL_TYPE_YEAR: // YEAR field
515
520
bind[i].buffer = &int_data[i];
516
521
break ;
517
- case MYSQL_TYPE_TINY:
518
- bind[i].buffer = &tiny_data[i];
522
+ case MYSQL_TYPE_BIT: // BIT field (MySQL 5.0.3 and up)
523
+ case MYSQL_TYPE_LONGLONG: // BIGINT field
524
+ // Return BIGINT as string, see #110
525
+ bind[i].buffer = &my_ulonglong_data[i];
519
526
break ;
520
- case MYSQL_TYPE_FLOAT:
521
- case MYSQL_TYPE_DOUBLE:
522
- case MYSQL_TYPE_DECIMAL:
523
- case MYSQL_TYPE_NEWDECIMAL:
527
+ case MYSQL_TYPE_FLOAT: // FLOAT field
528
+ case MYSQL_TYPE_DOUBLE: // DOUBLE or REAL field
524
529
bind[i].buffer = &double_data[i];
525
530
break ;
531
+ case MYSQL_TYPE_DECIMAL: // DECIMAL or NUMERIC field
532
+ case MYSQL_TYPE_NEWDECIMAL: // Precision math DECIMAL or NUMERIC field
533
+ // Return DECIMAL/NUMERIC as string, see #110
534
+ bind[i].buffer = (char *) str_data[i];
535
+ bind[i].buffer_length = fields[i].length ;
536
+ break ;
537
+ case MYSQL_TYPE_TIME: // TIME field
538
+ case MYSQL_TYPE_TIMESTAMP: // TIMESTAMP field
539
+ case MYSQL_TYPE_DATETIME: // DATETIME field
540
+ case MYSQL_TYPE_DATE: // DATE field
541
+ case MYSQL_TYPE_NEWDATE: // Newer const used in MySQL > 5.0
542
+ bind[i].buffer = (char *) &date_data[i];
543
+ break ;
544
+ case MYSQL_TYPE_TINY_BLOB:
545
+ case MYSQL_TYPE_MEDIUM_BLOB:
546
+ case MYSQL_TYPE_LONG_BLOB:
547
+ case MYSQL_TYPE_BLOB:
526
548
case MYSQL_TYPE_STRING:
527
549
case MYSQL_TYPE_VAR_STRING:
528
- case MYSQL_TYPE_VARCHAR:
529
550
bind[i].buffer = (char *) str_data[i];
530
551
bind[i].buffer_length = fields[i].length ;
531
552
break ;
532
- case MYSQL_TYPE_YEAR:
533
- case MYSQL_TYPE_DATE:
534
- case MYSQL_TYPE_NEWDATE:
535
- case MYSQL_TYPE_TIME:
536
- case MYSQL_TYPE_DATETIME:
537
- case MYSQL_TYPE_TIMESTAMP:
538
- bind[i].buffer = (char *) &date_data[i];
553
+ case MYSQL_TYPE_SET: // SET field
554
+ // TODO: Implement this
555
+ bind[i].buffer = (char *) str_data[i];
556
+ bind[i].buffer_length = fields[i].length ;
557
+ break ;
558
+ case MYSQL_TYPE_ENUM: // ENUM field
559
+ bind[i].buffer = (char *) str_data[i];
560
+ bind[i].buffer_length = fields[i].length ;
561
+ break ;
562
+ case MYSQL_TYPE_GEOMETRY: // Spatial fields
563
+ // See for information:
564
+ // http://dev.mysql.com/doc/refman/5.1/en/spatial-extensions.html
565
+ bind[i].buffer = (char *) str_data[i];
566
+ bind[i].buffer_length = fields[i].length ;
567
+ break ;
568
+ default :
569
+ bind[i].buffer = (char *) str_data[i];
570
+ bind[i].buffer_length = fields[i].length ;
539
571
break ;
540
572
}
541
573
@@ -554,15 +586,14 @@ Handle<Value> MysqlStatement::FetchAllSync(const Arguments& args) {
554
586
return scope.Close (Null ());
555
587
}
556
588
557
- Local<Array> js_result_rows = Array::New ();
589
+ Local<Array> js_result = Array::New ();
558
590
Local<Object> js_result_row;
559
- Handle<Value> js_result;
560
591
561
592
row_count = mysql_stmt_num_rows (stmt->_stmt );
562
593
563
594
/* If no rows, return empty array */
564
- if (! row_count) {
565
- return scope.Close (js_result_rows );
595
+ if (row_count == 0 ) {
596
+ return scope.Close (js_result );
566
597
}
567
598
568
599
i = 0 ;
@@ -571,66 +602,89 @@ Handle<Value> MysqlStatement::FetchAllSync(const Arguments& args) {
571
602
572
603
j = 0 ;
573
604
while (j < field_count) {
605
+ Local<Value> js_field = Local<Value>::New (Null ());
606
+
574
607
switch (fields[j].type ) {
575
- case MYSQL_TYPE_NULL:
576
- case MYSQL_TYPE_SHORT:
577
- case MYSQL_TYPE_LONG:
578
- case MYSQL_TYPE_LONGLONG:
579
- case MYSQL_TYPE_INT24:
580
- js_result = Integer::New (int_data[j]);
608
+ case MYSQL_TYPE_NULL: // NULL-type field
609
+ // Already null
581
610
break ;
582
- case MYSQL_TYPE_TINY:
583
- if (length[j] == 1 ) {
584
- js_result = Boolean::New (tiny_data[j] != 0 );
585
- } else {
586
- js_result = Integer::NewFromUnsigned (tiny_data[j]);
611
+ case MYSQL_TYPE_TINY: // TINYINT field
612
+ case MYSQL_TYPE_SHORT: // SMALLINT field
613
+ case MYSQL_TYPE_LONG: // INTEGER field
614
+ case MYSQL_TYPE_INT24: // MEDIUMINT field
615
+ case MYSQL_TYPE_YEAR: // YEAR field
616
+ if (!is_null[j]) {
617
+ js_field = Integer::New (int_data[j]);
618
+ }
619
+ break ;
620
+ case MYSQL_TYPE_BIT: // BIT field (MySQL 5.0.3 and up)
621
+ case MYSQL_TYPE_LONGLONG: // BIGINT field
622
+ // Return BIGINT as string, see #110
623
+ if (!is_null[j]) {
624
+ js_field = V8STR2 (str_data[j], length[j]);
625
+ }
626
+ break ;
627
+ case MYSQL_TYPE_FLOAT: // FLOAT field
628
+ case MYSQL_TYPE_DOUBLE: // DOUBLE or REAL field
629
+ if (!is_null[j]) {
630
+ js_field = Number::New (double_data[j]);
587
631
}
588
632
break ;
589
- case MYSQL_TYPE_FLOAT:
590
- case MYSQL_TYPE_DOUBLE:
591
- js_result = Number::New (double_data[j]);
633
+ case MYSQL_TYPE_DECIMAL: // DECIMAL or NUMERIC field
634
+ case MYSQL_TYPE_NEWDECIMAL: // Precision math DECIMAL or NUMERIC field
635
+ // Return DECIMAL/NUMERIC as string, see #110
636
+ if (!is_null[j]) {
637
+ js_field = V8STR2 (str_data[j], length[j]);
638
+ }
592
639
break ;
593
- case MYSQL_TYPE_DECIMAL:
594
- case MYSQL_TYPE_NEWDECIMAL:
595
- js_result = Number::New (double_data[j])->ToString ();
640
+ case MYSQL_TYPE_TIME: // TIME field
641
+ case MYSQL_TYPE_TIMESTAMP: // TIMESTAMP field
642
+ case MYSQL_TYPE_DATETIME: // DATETIME field
643
+ case MYSQL_TYPE_DATE: // DATE field
644
+ case MYSQL_TYPE_NEWDATE: // Newer const used in MySQL > 5.0
645
+ if (!is_null[j]) {
646
+ MYSQL_TIME ts = date_data[j];
647
+ time_t rawtime;
648
+ struct tm * datetime;
649
+ time (&rawtime);
650
+ datetime = localtime (&rawtime);
651
+ datetime->tm_year = ts.year - 1900 ;
652
+ datetime->tm_mon = ts.month - 1 ;
653
+ datetime->tm_mday = ts.day ;
654
+ datetime->tm_hour = ts.hour ;
655
+ datetime->tm_min = ts.minute ;
656
+ datetime->tm_sec = ts.second ;
657
+ time_t timestamp = mktime (datetime);
658
+
659
+ js_field = Date::New (1000 * (double ) timestamp);
660
+ }
596
661
break ;
662
+ case MYSQL_TYPE_TINY_BLOB:
663
+ case MYSQL_TYPE_MEDIUM_BLOB:
664
+ case MYSQL_TYPE_LONG_BLOB:
665
+ case MYSQL_TYPE_BLOB:
597
666
case MYSQL_TYPE_STRING:
598
667
case MYSQL_TYPE_VAR_STRING:
599
- case MYSQL_TYPE_VARCHAR:
600
- js_result = V8STR2 (str_data[j], length[j]);
668
+ if (!is_null[j]) {
669
+ js_field = V8STR2 (str_data[j], length[j]);
670
+ }
601
671
break ;
602
- case MYSQL_TYPE_YEAR:
603
- case MYSQL_TYPE_DATE:
604
- case MYSQL_TYPE_NEWDATE:
605
- case MYSQL_TYPE_TIME:
606
- case MYSQL_TYPE_DATETIME:
607
- case MYSQL_TYPE_TIMESTAMP:
608
- MYSQL_TIME ts = date_data[j];
609
- time_t rawtime;
610
- struct tm * datetime;
611
- time (&rawtime);
612
- datetime = localtime (&rawtime);
613
- datetime->tm_year = ts.year - 1900 ;
614
- datetime->tm_mon = ts.month - 1 ;
615
- datetime->tm_mday = ts.day ;
616
- datetime->tm_hour = ts.hour ;
617
- datetime->tm_min = ts.minute ;
618
- datetime->tm_sec = ts.second ;
619
- time_t timestamp = mktime (datetime);
620
-
621
- js_result = Date::New (1000 * (double ) timestamp);
672
+ default :
673
+ if (!is_null[j]) {
674
+ js_field = V8STR2 (str_data[j], length[j]);
675
+ }
622
676
break ;
623
677
}
624
678
625
- js_result_row->Set (V8STR (fields[j].name ), js_result );
679
+ js_result_row->Set (V8STR (fields[j].name ), js_field );
626
680
j++;
627
681
}
628
682
629
- js_result_rows ->Set (Integer::NewFromUnsigned (i), js_result_row);
683
+ js_result ->Set (Integer::NewFromUnsigned (i), js_result_row);
630
684
i++;
631
685
}
632
686
633
- return scope.Close (js_result_rows );
687
+ return scope.Close (js_result );
634
688
}
635
689
636
690
/* *
0 commit comments