oj 3.10.6 → 3.10.12
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/ext/oj/custom.c +1 -1
- data/ext/oj/mimic_json.c +4 -3
- data/ext/oj/object.c +1 -1
- data/ext/oj/oj.c +6 -1
- data/ext/oj/oj.h +3 -1
- data/ext/oj/parse.c +105 -37
- data/ext/oj/parse.h +2 -1
- data/ext/oj/sparse.c +22 -10
- data/lib/oj/version.rb +1 -1
- data/pages/Options.md +11 -11
- data/test/json_gem/json_common_interface_test.rb +6 -0
- data/test/prec.rb +23 -0
- data/test/sample_json.rb +1 -1
- data/test/test_custom.rb +11 -0
- data/test/test_various.rb +1 -2
- metadata +25 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 6fa2380f622d5ca9441eb9b2588179a077d851833c8c0985a99d5be562b033b3
|
4
|
+
data.tar.gz: 56f3d28b1a711efed58a4ef43a0518b44f127e1ad68a68fbe9afecbee9d6b395
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 1603e46da846347272f245183555480e944368eb1c0394bd8ab4e6cc0a916353e66ba94b14c6a45c687a80a033bf792161c64acb24a32d81f6d749f35dd1bf31
|
7
|
+
data.tar.gz: f2d40d5bb00fb5cfd0bbbc0eb55d15be1d90dd2da8657b07ce4156ab8fe3d91731bb536231be4d12d0f2f5e9979fd95dec77a800cfc8e11e96ce4856067d3788
|
data/ext/oj/custom.c
CHANGED
@@ -1089,7 +1089,7 @@ hash_set_num(struct _parseInfo *pi, Val kval, NumInfo ni) {
|
|
1089
1089
|
// offset and then a conversion to UTC keeps makes the time
|
1090
1090
|
// match the expected value.
|
1091
1091
|
parent->val = rb_funcall2(parent->val, oj_utc_id, 0, 0);
|
1092
|
-
} else if (ni->
|
1092
|
+
} else if (ni->has_exp) {
|
1093
1093
|
int64_t t = (int64_t)(ni->i + ni->exp);
|
1094
1094
|
struct _timeInfo ti;
|
1095
1095
|
VALUE args[8];
|
data/ext/oj/mimic_json.c
CHANGED
@@ -513,7 +513,8 @@ mimic_parse_core(int argc, VALUE *argv, VALUE self, bool bang) {
|
|
513
513
|
pi.options.create_ok = No;
|
514
514
|
pi.options.allow_nan = (bang ? Yes : No);
|
515
515
|
pi.options.nilnil = No;
|
516
|
-
pi.options.bigdec_load = FloatDec;
|
516
|
+
//pi.options.bigdec_load = FloatDec;
|
517
|
+
pi.options.bigdec_load = RubyDec;
|
517
518
|
pi.options.mode = CompatMode;
|
518
519
|
pi.max_depth = 100;
|
519
520
|
|
@@ -686,7 +687,7 @@ static struct _options mimic_object_to_json_options = {
|
|
686
687
|
No, // class_cache
|
687
688
|
RubyTime, // time_format
|
688
689
|
No, // bigdec_as_num
|
689
|
-
|
690
|
+
RubyDec, // bigdec_load
|
690
691
|
No, // to_hash
|
691
692
|
No, // to_json
|
692
693
|
No, // as_json
|
@@ -707,7 +708,7 @@ static struct _options mimic_object_to_json_options = {
|
|
707
708
|
oj_json_class,// create_id
|
708
709
|
10, // create_id_len
|
709
710
|
3, // sec_prec
|
710
|
-
|
711
|
+
0, // float_prec
|
711
712
|
"%0.16g", // float_fmt
|
712
713
|
Qnil, // hash_class
|
713
714
|
Qnil, // array_class
|
data/ext/oj/object.c
CHANGED
@@ -295,7 +295,7 @@ hat_num(ParseInfo pi, Val parent, Val kval, NumInfo ni) {
|
|
295
295
|
// offset and then a conversion to UTC keeps makes the time
|
296
296
|
// match the expected value.
|
297
297
|
parent->val = rb_funcall2(parent->val, oj_utc_id, 0, 0);
|
298
|
-
} else if (ni->
|
298
|
+
} else if (ni->has_exp) {
|
299
299
|
int64_t t = (int64_t)(ni->i + ni->exp);
|
300
300
|
struct _timeInfo ti;
|
301
301
|
VALUE args[8];
|
data/ext/oj/oj.c
CHANGED
@@ -115,6 +115,7 @@ static VALUE custom_sym;
|
|
115
115
|
static VALUE empty_string_sym;
|
116
116
|
static VALUE escape_mode_sym;
|
117
117
|
static VALUE integer_range_sym;
|
118
|
+
static VALUE fast_sym;
|
118
119
|
static VALUE float_prec_sym;
|
119
120
|
static VALUE float_sym;
|
120
121
|
static VALUE huge_sym;
|
@@ -230,7 +231,7 @@ struct _options oj_default_options = {
|
|
230
231
|
* - *:mode* [_:object_|_:strict_|_:compat_|_:null_|_:custom_|_:rails_|_:wab_] load and dump modes to use for JSON
|
231
232
|
* - *:time_format* [_:unix_|_:unix_zone_|_:xmlschema_|_:ruby_] time format when dumping
|
232
233
|
* - *:bigdecimal_as_decimal* [_Boolean_|_nil_] dump BigDecimal as a decimal number or as a String
|
233
|
-
* - *:bigdecimal_load* [_:bigdecimal_|_:float_|_:auto_] load decimals as BigDecimal instead of as a Float. :auto pick the most precise for the number of digits.
|
234
|
+
* - *:bigdecimal_load* [_:bigdecimal_|_:float_|_:auto_|_:fast_] load decimals as BigDecimal instead of as a Float. :auto pick the most precise for the number of digits. :float should be the same as ruby. :fast may require rounding but is must faster.
|
234
235
|
* - *:create_id* [_String_|_nil_] create id for json compatible object encoding, default is 'json_class'
|
235
236
|
* - *:create_additions* [_Boolean_|_nil_] if true allow creation of instances using create_id on load.
|
236
237
|
* - *:second_precision* [_Fixnum_|_nil_] number of digits after the decimal when dumping the seconds portion of time
|
@@ -331,6 +332,7 @@ get_def_opts(VALUE self) {
|
|
331
332
|
switch (oj_default_options.bigdec_load) {
|
332
333
|
case BigDec: rb_hash_aset(opts, bigdecimal_load_sym, bigdecimal_sym);break;
|
333
334
|
case FloatDec: rb_hash_aset(opts, bigdecimal_load_sym, float_sym); break;
|
335
|
+
case FastDec: rb_hash_aset(opts, bigdecimal_load_sym, fast_sym); break;
|
334
336
|
case AutoDec:
|
335
337
|
default: rb_hash_aset(opts, bigdecimal_load_sym, auto_sym); break;
|
336
338
|
}
|
@@ -574,6 +576,8 @@ oj_parse_options(VALUE ropts, Options copts) {
|
|
574
576
|
copts->bigdec_load = BigDec;
|
575
577
|
} else if (float_sym == v) {
|
576
578
|
copts->bigdec_load = FloatDec;
|
579
|
+
} else if (fast_sym == v) {
|
580
|
+
copts->bigdec_load = FastDec;
|
577
581
|
} else if (auto_sym == v || Qfalse == v) {
|
578
582
|
copts->bigdec_load = AutoDec;
|
579
583
|
} else {
|
@@ -1654,6 +1658,7 @@ Init_oj() {
|
|
1654
1658
|
empty_string_sym = ID2SYM(rb_intern("empty_string")); rb_gc_register_address(&empty_string_sym);
|
1655
1659
|
escape_mode_sym = ID2SYM(rb_intern("escape_mode")); rb_gc_register_address(&escape_mode_sym);
|
1656
1660
|
integer_range_sym = ID2SYM(rb_intern("integer_range")); rb_gc_register_address(&integer_range_sym);
|
1661
|
+
fast_sym = ID2SYM(rb_intern("fast")); rb_gc_register_address(&fast_sym);
|
1657
1662
|
float_prec_sym = ID2SYM(rb_intern("float_precision")); rb_gc_register_address(&float_prec_sym);
|
1658
1663
|
float_sym = ID2SYM(rb_intern("float")); rb_gc_register_address(&float_sym);
|
1659
1664
|
huge_sym = ID2SYM(rb_intern("huge")); rb_gc_register_address(&huge_sym);
|
data/ext/oj/oj.h
CHANGED
data/ext/oj/parse.c
CHANGED
@@ -393,8 +393,9 @@ read_num(ParseInfo pi) {
|
|
393
393
|
ni.infinity = 0;
|
394
394
|
ni.nan = 0;
|
395
395
|
ni.neg = 0;
|
396
|
-
ni.
|
397
|
-
ni.no_big = (FloatDec == pi->options.bigdec_load);
|
396
|
+
ni.has_exp = 0;
|
397
|
+
ni.no_big = (FloatDec == pi->options.bigdec_load || FastDec == pi->options.bigdec_load || RubyDec == pi->options.bigdec_load);
|
398
|
+
ni.bigdec_load = pi->options.bigdec_load;
|
398
399
|
|
399
400
|
if ('-' == *pi->cur) {
|
400
401
|
pi->cur++;
|
@@ -453,6 +454,7 @@ read_num(ParseInfo pi) {
|
|
453
454
|
// except when mimicing the JSON gem or in strict mode.
|
454
455
|
if (StrictMode == pi->options.mode || CompatMode == pi->options.mode) {
|
455
456
|
int pos = (int)(pi->cur - ni.str);
|
457
|
+
|
456
458
|
if (1 == pos || (2 == pos && ni.neg)) {
|
457
459
|
oj_set_error_at(pi, oj_parse_error_class, __FILE__, __LINE__, "not a number");
|
458
460
|
return;
|
@@ -468,18 +470,26 @@ read_num(ParseInfo pi) {
|
|
468
470
|
if (0 < ni.num || 0 < ni.i) {
|
469
471
|
dec_cnt++;
|
470
472
|
}
|
471
|
-
|
472
|
-
|
473
|
-
|
474
|
-
|
475
|
-
|
473
|
+
if (INT64_MAX <= ni.div) {
|
474
|
+
if (!ni.no_big) {
|
475
|
+
ni.big = true;
|
476
|
+
}
|
477
|
+
} else {
|
478
|
+
ni.num = ni.num * 10 + d;
|
479
|
+
ni.div *= 10;
|
480
|
+
ni.di++;
|
481
|
+
if (INT64_MAX <= ni.div || DEC_MAX < dec_cnt) {
|
482
|
+
if (!ni.no_big) {
|
483
|
+
ni.big = true;
|
484
|
+
}
|
485
|
+
}
|
476
486
|
}
|
477
487
|
}
|
478
488
|
}
|
479
489
|
if ('e' == *pi->cur || 'E' == *pi->cur) {
|
480
490
|
int eneg = 0;
|
481
491
|
|
482
|
-
ni.
|
492
|
+
ni.has_exp = 1;
|
483
493
|
pi->cur++;
|
484
494
|
if ('-' == *pi->cur) {
|
485
495
|
pi->cur++;
|
@@ -490,7 +500,7 @@ read_num(ParseInfo pi) {
|
|
490
500
|
for (; '0' <= *pi->cur && *pi->cur <= '9'; pi->cur++) {
|
491
501
|
ni.exp = ni.exp * 10 + (*pi->cur - '0');
|
492
502
|
if (EXP_MAX <= ni.exp) {
|
493
|
-
ni.big =
|
503
|
+
ni.big = true;
|
494
504
|
}
|
495
505
|
}
|
496
506
|
if (eneg) {
|
@@ -750,6 +760,59 @@ parse_big_decimal(VALUE str) {
|
|
750
760
|
return rb_funcall(rb_cObject, oj_bigdecimal_id, 1, str);
|
751
761
|
}
|
752
762
|
|
763
|
+
static long double exp_plus[] = {
|
764
|
+
1.0,
|
765
|
+
1.0e1,
|
766
|
+
1.0e2,
|
767
|
+
1.0e3,
|
768
|
+
1.0e4,
|
769
|
+
1.0e5,
|
770
|
+
1.0e6,
|
771
|
+
1.0e7,
|
772
|
+
1.0e8,
|
773
|
+
1.0e9,
|
774
|
+
1.0e10,
|
775
|
+
1.0e11,
|
776
|
+
1.0e12,
|
777
|
+
1.0e13,
|
778
|
+
1.0e14,
|
779
|
+
1.0e15,
|
780
|
+
1.0e16,
|
781
|
+
1.0e17,
|
782
|
+
1.0e18,
|
783
|
+
1.0e19,
|
784
|
+
1.0e20,
|
785
|
+
1.0e21,
|
786
|
+
1.0e22,
|
787
|
+
1.0e23,
|
788
|
+
1.0e24,
|
789
|
+
1.0e25,
|
790
|
+
1.0e26,
|
791
|
+
1.0e27,
|
792
|
+
1.0e28,
|
793
|
+
1.0e29,
|
794
|
+
1.0e30,
|
795
|
+
1.0e31,
|
796
|
+
1.0e32,
|
797
|
+
1.0e33,
|
798
|
+
1.0e34,
|
799
|
+
1.0e35,
|
800
|
+
1.0e36,
|
801
|
+
1.0e37,
|
802
|
+
1.0e38,
|
803
|
+
1.0e39,
|
804
|
+
1.0e40,
|
805
|
+
1.0e41,
|
806
|
+
1.0e42,
|
807
|
+
1.0e43,
|
808
|
+
1.0e44,
|
809
|
+
1.0e45,
|
810
|
+
1.0e46,
|
811
|
+
1.0e47,
|
812
|
+
1.0e48,
|
813
|
+
1.0e49,
|
814
|
+
};
|
815
|
+
|
753
816
|
VALUE
|
754
817
|
oj_num_as_value(NumInfo ni) {
|
755
818
|
volatile VALUE rnum = Qnil;
|
@@ -762,7 +825,7 @@ oj_num_as_value(NumInfo ni) {
|
|
762
825
|
}
|
763
826
|
} else if (ni->nan) {
|
764
827
|
rnum = rb_float_new(0.0/0.0);
|
765
|
-
} else if (1 == ni->div && 0 == ni->exp) { // fixnum
|
828
|
+
} else if (1 == ni->div && 0 == ni->exp && !ni->has_exp) { // fixnum
|
766
829
|
if (ni->big) {
|
767
830
|
if (256 > ni->len) {
|
768
831
|
char buf[256];
|
@@ -793,40 +856,39 @@ oj_num_as_value(NumInfo ni) {
|
|
793
856
|
if (ni->no_big) {
|
794
857
|
rnum = rb_funcall(rnum, rb_intern("to_f"), 0);
|
795
858
|
}
|
796
|
-
} else {
|
797
|
-
// All these machinations are to get rounding to work better.
|
859
|
+
} else if (FastDec == ni->bigdec_load) {
|
798
860
|
long double ld = (long double)ni->i * (long double)ni->div + (long double)ni->num;
|
799
861
|
int x = (int)((int64_t)ni->exp - ni->di);
|
800
862
|
|
801
|
-
|
802
|
-
|
803
|
-
|
804
|
-
if ((long double)INT64_MAX > ld && (int64_t)ld != (ni->i * ni->div + ni->num)) {
|
805
|
-
volatile VALUE bd = rb_str_new(ni->str, ni->len);
|
806
|
-
|
807
|
-
rnum = rb_rescue2(parse_big_decimal, bd, rescue_big_decimal, bd, rb_eException, 0);
|
808
|
-
if (ni->no_big) {
|
809
|
-
rnum = rb_funcall(rnum, rb_intern("to_f"), 0);
|
810
|
-
}
|
811
|
-
} else {
|
812
|
-
double d;
|
813
|
-
|
814
|
-
ld = roundl(ld);
|
815
|
-
// You would expect that staying with a long double would be
|
816
|
-
// more accurate but it fails to match what Ruby generates so
|
817
|
-
// drop down to a double.
|
818
|
-
if (0 < x) {
|
819
|
-
d = (double)ld * pow(10.0, x);
|
820
|
-
} else if (0 > x) {
|
821
|
-
d = (double)ld / pow(10.0, -x);
|
863
|
+
if (0 < x) {
|
864
|
+
if (x < (int)(sizeof(exp_plus) / sizeof(*exp_plus))) {
|
865
|
+
ld *= exp_plus[x];
|
822
866
|
} else {
|
823
|
-
|
867
|
+
ld *= powl(10.0, x);
|
824
868
|
}
|
825
|
-
|
826
|
-
|
869
|
+
} else if (x < 0) {
|
870
|
+
if (-x < (int)(sizeof(exp_plus) / sizeof(*exp_plus))) {
|
871
|
+
ld /= exp_plus[-x];
|
872
|
+
} else {
|
873
|
+
ld /= powl(10.0, -x);
|
827
874
|
}
|
828
|
-
rnum = rb_float_new(d);
|
829
875
|
}
|
876
|
+
if (ni->neg) {
|
877
|
+
ld = -ld;
|
878
|
+
}
|
879
|
+
rnum = rb_float_new((double)ld);
|
880
|
+
} else if (RubyDec == ni->bigdec_load) {
|
881
|
+
volatile VALUE sv = rb_str_new(ni->str, ni->len);
|
882
|
+
|
883
|
+
rnum = rb_funcall(sv, rb_intern("to_f"), 0);
|
884
|
+
} else {
|
885
|
+
char *end;
|
886
|
+
double d = strtod(ni->str, &end);
|
887
|
+
|
888
|
+
if ((long)ni->len != (long)(end - ni->str)) {
|
889
|
+
rb_raise(oj_parse_error_class, "Invalid float");
|
890
|
+
}
|
891
|
+
rnum = rb_float_new(d);
|
830
892
|
}
|
831
893
|
}
|
832
894
|
return rnum;
|
@@ -848,6 +910,12 @@ oj_set_error_at(ParseInfo pi, VALUE err_clas, const char* file, int line, const
|
|
848
910
|
if (p + 3 < end) {
|
849
911
|
*p++ = ' ';
|
850
912
|
*p++ = '(';
|
913
|
+
*p++ = 'a';
|
914
|
+
*p++ = 'f';
|
915
|
+
*p++ = 't';
|
916
|
+
*p++ = 'e';
|
917
|
+
*p++ = 'r';
|
918
|
+
*p++ = ' ';
|
851
919
|
start = p;
|
852
920
|
for (vp = pi->stack.head; vp < pi->stack.tail; vp++) {
|
853
921
|
if (end <= p + 1 + vp->klen) {
|
data/ext/oj/parse.h
CHANGED
data/ext/oj/sparse.c
CHANGED
@@ -407,8 +407,10 @@ read_num(ParseInfo pi) {
|
|
407
407
|
ni.infinity = 0;
|
408
408
|
ni.nan = 0;
|
409
409
|
ni.neg = 0;
|
410
|
-
ni.
|
411
|
-
ni.no_big = (FloatDec == pi->options.bigdec_load);
|
410
|
+
ni.has_exp = 0;
|
411
|
+
ni.no_big = (FloatDec == pi->options.bigdec_load || FastDec == pi->options.bigdec_load || RubyDec == pi->options.bigdec_load);
|
412
|
+
ni.bigdec_load = pi->options.bigdec_load;
|
413
|
+
|
412
414
|
c = reader_get(&pi->rd);
|
413
415
|
if ('-' == c) {
|
414
416
|
c = reader_get(&pi->rd);
|
@@ -469,18 +471,26 @@ read_num(ParseInfo pi) {
|
|
469
471
|
if (0 < ni.num || 0 < ni.i) {
|
470
472
|
dec_cnt++;
|
471
473
|
}
|
472
|
-
|
473
|
-
|
474
|
-
|
475
|
-
|
476
|
-
|
474
|
+
if (INT64_MAX <= ni.div) {
|
475
|
+
if (!ni.no_big) {
|
476
|
+
ni.big = true;
|
477
|
+
}
|
478
|
+
} else {
|
479
|
+
ni.num = ni.num * 10 + d;
|
480
|
+
ni.div *= 10;
|
481
|
+
ni.di++;
|
482
|
+
if (INT64_MAX <= ni.div || DEC_MAX < dec_cnt) {
|
483
|
+
if (!ni.no_big) {
|
484
|
+
ni.big = true;
|
485
|
+
}
|
486
|
+
}
|
477
487
|
}
|
478
488
|
}
|
479
489
|
}
|
480
490
|
if ('e' == c || 'E' == c) {
|
481
491
|
int eneg = 0;
|
482
492
|
|
483
|
-
ni.
|
493
|
+
ni.has_exp = 1;
|
484
494
|
c = reader_get(&pi->rd);
|
485
495
|
if ('-' == c) {
|
486
496
|
c = reader_get(&pi->rd);
|
@@ -539,7 +549,8 @@ read_nan(ParseInfo pi) {
|
|
539
549
|
ni.infinity = 0;
|
540
550
|
ni.nan = 1;
|
541
551
|
ni.neg = 0;
|
542
|
-
ni.no_big = (FloatDec == pi->options.bigdec_load);
|
552
|
+
ni.no_big = (FloatDec == pi->options.bigdec_load || FastDec == pi->options.bigdec_load || RubyDec == pi->options.bigdec_load);
|
553
|
+
ni.bigdec_load = pi->options.bigdec_load;
|
543
554
|
|
544
555
|
if ('a' != reader_get(&pi->rd) ||
|
545
556
|
('N' != (c = reader_get(&pi->rd)) && 'n' != c)) {
|
@@ -736,7 +747,8 @@ oj_sparse2(ParseInfo pi) {
|
|
736
747
|
ni.infinity = 0;
|
737
748
|
ni.nan = 1;
|
738
749
|
ni.neg = 0;
|
739
|
-
ni.no_big = (FloatDec == pi->options.bigdec_load);
|
750
|
+
ni.no_big = (FloatDec == pi->options.bigdec_load || RubyDec == pi->options.bigdec_load || FastDec == pi->options.bigdec_load);
|
751
|
+
ni.bigdec_load = pi->options.bigdec_load;
|
740
752
|
add_num_value(pi, &ni);
|
741
753
|
} else {
|
742
754
|
oj_set_error_at(pi, oj_parse_error_class, __FILE__, __LINE__, "invalid token");
|
data/lib/oj/version.rb
CHANGED
data/pages/Options.md
CHANGED
@@ -80,16 +80,16 @@ dynamically modifying classes or reloading classes then don't use this.
|
|
80
80
|
|
81
81
|
### :create_additions
|
82
82
|
|
83
|
-
A flag indicating the :create_id key when encountered during parsing
|
84
|
-
|
85
|
-
with the key.
|
83
|
+
A flag indicating that the :create_id key, when encountered during parsing,
|
84
|
+
should create an Object matching the class name specified in the value
|
85
|
+
associated with the key.
|
86
86
|
|
87
87
|
### :create_id [String]
|
88
88
|
|
89
89
|
The :create_id option specifies that key is used for dumping and loading when
|
90
90
|
specifying the class for an encoded object. The default is `json_create`.
|
91
91
|
|
92
|
-
In the `:custom` mode setting the `:create_id` to nil will cause Complex,
|
92
|
+
In the `:custom` mode, setting the `:create_id` to nil will cause Complex,
|
93
93
|
Rational, Range, and Regexp to be output as strings instead of as JSON
|
94
94
|
objects.
|
95
95
|
|
@@ -179,7 +179,7 @@ customization.
|
|
179
179
|
### :nan [Symbol]
|
180
180
|
|
181
181
|
How to dump Infinity, -Infinity, and NaN in :null, :strict, and :compat
|
182
|
-
mode. Default is :auto but is ignored in the :compat and :rails
|
182
|
+
mode. Default is :auto but is ignored in the :compat and :rails modes.
|
183
183
|
|
184
184
|
- `:null` places a null
|
185
185
|
|
@@ -252,7 +252,7 @@ The :time_format when dumping.
|
|
252
252
|
|
253
253
|
- `:unix` time is output as a decimal number in seconds since epoch including fractions of a second.
|
254
254
|
|
255
|
-
- `:unix_zone` similar to the `:unix` format but with the timezone encoded in
|
255
|
+
- `:unix_zone` is similar to the `:unix` format but with the timezone encoded in
|
256
256
|
the exponent of the decimal number of seconds since epoch.
|
257
257
|
|
258
258
|
- `:xmlschema` time is output as a string that follows the XML schema definition.
|
@@ -262,16 +262,16 @@ The :time_format when dumping.
|
|
262
262
|
### :use_as_json [Boolean]
|
263
263
|
|
264
264
|
Call `as_json()` methods on dump, default is false. The option is ignored in
|
265
|
-
the :compat and :rails
|
265
|
+
the :compat and :rails modes.
|
266
266
|
|
267
267
|
|
268
268
|
### :use_raw_json [Boolean]
|
269
269
|
|
270
270
|
Call `raw_json()` methods on dump, default is false. The option is
|
271
|
-
accepted in the :compat and :rails
|
271
|
+
accepted in the :compat and :rails modes even though it is not
|
272
272
|
supported by other JSON gems. It provides a means to optimize dump or
|
273
273
|
generate performance. The `raw_json(depth, indent)` method should be
|
274
|
-
called only by Oj. It is not intended for any other use. This is
|
274
|
+
called only by Oj. It is not intended for any other use. This is meant
|
275
275
|
to replace the abused `to_json` methods. Calling `Oj.dump` inside the
|
276
276
|
`raw_json` with the object itself when `:use_raw_json` is true will
|
277
277
|
result in an infinite loop.
|
@@ -279,9 +279,9 @@ result in an infinite loop.
|
|
279
279
|
### :use_to_hash [Boolean]
|
280
280
|
|
281
281
|
Call `to_hash()` methods on dump, default is false. The option is ignored in
|
282
|
-
the :compat and :rails
|
282
|
+
the :compat and :rails modes.
|
283
283
|
|
284
284
|
### :use_to_json [Boolean]
|
285
285
|
|
286
286
|
Call `to_json()` methods on dump, default is false. The option is ignored in
|
287
|
-
the :compat and :rails
|
287
|
+
the :compat and :rails modes.
|
@@ -23,8 +23,14 @@ class JSONCommonInterfaceTest < Test::Unit::TestCase
|
|
23
23
|
'h' => 1000.0,
|
24
24
|
'i' => 0.001
|
25
25
|
}
|
26
|
+
# Tired of chasing floating point rounding and precision. Oj not uses the
|
27
|
+
# Ruby float parser in compat mode yet on i386 machines there are issues
|
28
|
+
# with this test when the float is included.
|
29
|
+
|
26
30
|
@json = '{"a":2,"b":5.23683071,"c":"c","d":[1,"b",3.14],"e":{"foo":"bar"},'\
|
27
31
|
'"g":"\\"\\u0000\\u001f","h":1000.0,"i":0.001}'
|
32
|
+
#@json = '{"a":2,"c":"c","d":[1,"b",3.14],"e":{"foo":"bar"},'\
|
33
|
+
#p '"g":"\\"\\u0000\\u001f","h":1000.0,"i":0.001}'
|
28
34
|
end
|
29
35
|
|
30
36
|
def test_index
|
data/test/prec.rb
ADDED
@@ -0,0 +1,23 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'oj'
|
4
|
+
|
5
|
+
extras = {"locationLng" => -97.14690769100295}
|
6
|
+
|
7
|
+
Oj.default_options = {float_precision: 17}
|
8
|
+
|
9
|
+
encoded = Oj.dump(extras)
|
10
|
+
puts encoded
|
11
|
+
puts Oj.load(encoded)
|
12
|
+
|
13
|
+
require "active_record"
|
14
|
+
|
15
|
+
Oj::Rails.set_encoder()
|
16
|
+
Oj::Rails.set_decoder()
|
17
|
+
|
18
|
+
Oj.default_options = {float_precision: 17}
|
19
|
+
# Using Oj rails encoder, gets the correct value: {"locationLng":-97.14690769100295}
|
20
|
+
encoded = ActiveSupport::JSON.encode(extras)
|
21
|
+
puts encoded
|
22
|
+
puts ActiveSupport::JSON.decode(encoded)
|
23
|
+
puts Oj.load(encoded)
|
data/test/sample_json.rb
CHANGED
data/test/test_custom.rb
CHANGED
@@ -118,6 +118,17 @@ class CustomJuice < Minitest::Test
|
|
118
118
|
dump_and_load(-2.48e100 * 1.0e10, false)
|
119
119
|
end
|
120
120
|
|
121
|
+
def test_float_parse
|
122
|
+
f = Oj.load("12.123456789012345678", mode: :custom, bigdecimal_load: :float);
|
123
|
+
assert_equal(Float, f.class)
|
124
|
+
end
|
125
|
+
|
126
|
+
def test_float_parse_fast
|
127
|
+
f = Oj.load("12.123456789012345678", mode: :custom, bigdecimal_load: :fast);
|
128
|
+
assert_equal(Float, f.class)
|
129
|
+
assert_equal('12.12345678901235', "%0.14f" % [f]) # only care about 16 digits
|
130
|
+
end
|
131
|
+
|
121
132
|
def test_nan_dump
|
122
133
|
assert_equal('null', Oj.dump(0/0.0, :nan => :null))
|
123
134
|
assert_equal('3.3e14159265358979323846', Oj.dump(0/0.0, :nan => :huge))
|
data/test/test_various.rb
CHANGED
@@ -185,7 +185,6 @@ class Juice < Minitest::Test
|
|
185
185
|
n = Oj.load('-0.000012345678901234567')
|
186
186
|
assert_equal(BigDecimal, n.class)
|
187
187
|
assert_equal('-0.12345678901234567E-4', n.to_s.upcase)
|
188
|
-
|
189
188
|
end
|
190
189
|
|
191
190
|
=begin
|
@@ -671,7 +670,7 @@ class Juice < Minitest::Test
|
|
671
670
|
raise e
|
672
671
|
end
|
673
672
|
}
|
674
|
-
assert_equal('first[2].third', msg.split('(')[1].split(')')[0])
|
673
|
+
assert_equal('after first[2].third', msg.split('(')[1].split(')')[0])
|
675
674
|
end
|
676
675
|
|
677
676
|
def test_bad_bignum
|
metadata
CHANGED
@@ -1,15 +1,35 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: oj
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.10.
|
4
|
+
version: 3.10.12
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Peter Ohler
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2020-
|
11
|
+
date: 2020-08-20 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: bigdecimal
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - ">="
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '1.0'
|
20
|
+
- - "<"
|
21
|
+
- !ruby/object:Gem::Version
|
22
|
+
version: '3'
|
23
|
+
type: :runtime
|
24
|
+
prerelease: false
|
25
|
+
version_requirements: !ruby/object:Gem::Requirement
|
26
|
+
requirements:
|
27
|
+
- - ">="
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: '1.0'
|
30
|
+
- - "<"
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: '3'
|
13
33
|
- !ruby/object:Gem::Dependency
|
14
34
|
name: rake-compiler
|
15
35
|
requirement: !ruby/object:Gem::Requirement
|
@@ -219,6 +239,7 @@ files:
|
|
219
239
|
- test/perf_simple.rb
|
220
240
|
- test/perf_strict.rb
|
221
241
|
- test/perf_wab.rb
|
242
|
+
- test/prec.rb
|
222
243
|
- test/sample.rb
|
223
244
|
- test/sample/change.rb
|
224
245
|
- test/sample/dir.rb
|
@@ -276,7 +297,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
276
297
|
requirements:
|
277
298
|
- - ">="
|
278
299
|
- !ruby/object:Gem::Version
|
279
|
-
version: '2.
|
300
|
+
version: '2.4'
|
280
301
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
281
302
|
requirements:
|
282
303
|
- - ">="
|
@@ -289,6 +310,7 @@ specification_version: 4
|
|
289
310
|
summary: A fast JSON parser and serializer.
|
290
311
|
test_files:
|
291
312
|
- test/foo.rb
|
313
|
+
- test/prec.rb
|
292
314
|
- test/test_integer_range.rb
|
293
315
|
- test/test_strict.rb
|
294
316
|
- test/perf_strict.rb
|