ruby-changes:23517
From: naruse <ko1@a...>
Date: Tue, 8 May 2012 01:01:02 +0900 (JST)
Subject: [ruby-changes:23517] naruse:r35568 (trunk): * ext/json: Merge JSON 1.7.1.
naruse 2012-05-08 01:00:49 +0900 (Tue, 08 May 2012) New Revision: 35568 http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=rev&revision=35568 Log: * ext/json: Merge JSON 1.7.1. https://github.com/flori/json/commit/e5b9a9465c1159fae533bca320d950b772bcb4ac Modified files: trunk/ChangeLog trunk/ext/json/fbuffer/fbuffer.h trunk/ext/json/generator/depend trunk/ext/json/generator/extconf.rb trunk/ext/json/generator/generator.c trunk/ext/json/generator/generator.h trunk/ext/json/lib/json/common.rb trunk/ext/json/lib/json/version.rb trunk/ext/json/parser/depend trunk/ext/json/parser/parser.c trunk/ext/json/parser/parser.rl trunk/test/json/test_json.rb trunk/test/json/test_json_addition.rb trunk/test/json/test_json_encoding.rb trunk/test/json/test_json_fixtures.rb trunk/test/json/test_json_generate.rb trunk/test/json/test_json_string_matching.rb trunk/test/json/test_json_unicode.rb Index: ChangeLog =================================================================== --- ChangeLog (revision 35567) +++ ChangeLog (revision 35568) @@ -1,3 +1,8 @@ +Mon May 7 21:19:17 2012 NARUSE, Yui <naruse@r...> + + * ext/json: Merge JSON 1.7.1. + https://github.com/flori/json/commit/e5b9a9465c1159fae533bca320d950b772bcb4ac + Mon May 07 22:54:22 2012 Martin Bosslet <Martin.Bosslet@g...> * ext/openssl/ossl_ssl.c: add support for option flags Index: ext/json/fbuffer/fbuffer.h =================================================================== --- ext/json/fbuffer/fbuffer.h (revision 35567) +++ ext/json/fbuffer/fbuffer.h (revision 35568) @@ -35,10 +35,14 @@ static void fbuffer_free(FBuffer *fb); static void fbuffer_clear(FBuffer *fb); static void fbuffer_append(FBuffer *fb, const char *newstr, unsigned long len); +#ifdef JSON_GENERATOR static void fbuffer_append_long(FBuffer *fb, long number); +#endif static void fbuffer_append_char(FBuffer *fb, char newchr); +#ifdef JSON_GENERATOR static FBuffer *fbuffer_dup(FBuffer *fb); static VALUE fbuffer_to_s(FBuffer *fb); +#endif static FBuffer *fbuffer_alloc(unsigned long initial_length) { @@ -68,7 +72,6 @@ if (!fb->ptr) { fb->ptr = ALLOC_N(char, fb->initial_length); fb->capa = fb->initial_length; - fb->len = 0; } for (required = fb->capa; requested > required - fb->len; required <<= 1); @@ -88,15 +91,17 @@ } } +#ifdef JSON_GENERATOR static void fbuffer_append_str(FBuffer *fb, VALUE str) { const char *newstr = StringValuePtr(str); unsigned long len = RSTRING_LEN(str); + RB_GC_GUARD(str); + fbuffer_append(fb, newstr, len); - - RB_GC_GUARD(str); } +#endif static void fbuffer_append_char(FBuffer *fb, char newchr) { @@ -105,6 +110,7 @@ fb->len++; } +#ifdef JSON_GENERATOR static void freverse(char *start, char *end) { char c; @@ -155,3 +161,4 @@ return result; } #endif +#endif Index: ext/json/generator/depend =================================================================== --- ext/json/generator/depend (revision 35567) +++ ext/json/generator/depend (revision 35568) @@ -1 +1 @@ -generator.o: generator.c generator.h +generator.o: generator.c generator.h $(srcdir)/../fbuffer/fbuffer.h Index: ext/json/generator/generator.c =================================================================== --- ext/json/generator/generator.c (revision 35567) +++ ext/json/generator/generator.c (revision 35568) @@ -762,7 +762,6 @@ { VALUE tmp = rb_funcall(obj, i_to_s, 0); fbuffer_append_str(buffer, tmp); - RB_GC_GUARD(tmp); } static void generate_json_float(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj) @@ -854,6 +853,21 @@ } /* + * This function returns true if string is either a JSON array or JSON object. + * It might suffer from false positives, e. g. syntactically incorrect JSON in + * the string or certain UTF-8 characters on the right hand side. + */ +static int isArrayOrObject(VALUE string) +{ + long string_len = RSTRING_LEN(string); + char *p = RSTRING_PTR(string), *q = p + string_len - 1; + if (string_len < 2) return 0; + for (; p < q && isspace(*p); p++); + for (; q > p && isspace(*q); q--); + return *p == '[' && *q == ']' || *p == '{' && *q == '}'; +} + +/* * call-seq: generate(obj) * * Generates a valid JSON document from object +obj+ and returns the @@ -863,15 +877,9 @@ static VALUE cState_generate(VALUE self, VALUE obj) { VALUE result = cState_partial_generate(self, obj); - VALUE re, args[2]; GET_STATE(self); - if (!state->quirks_mode) { - args[0] = rb_str_new2("\\A\\s*(?:\\[.*\\]|\\{.*\\})\\s*\\Z"); - args[1] = CRegexp_MULTILINE; - re = rb_class_new_instance(2, args, rb_cRegexp); - if (NIL_P(rb_funcall(re, i_match, 1, result))) { - rb_raise(eGeneratorError, "only generation of JSON objects or arrays allowed"); - } + if (!state->quirks_mode && !isArrayOrObject(result)) { + rb_raise(eGeneratorError, "only generation of JSON objects or arrays allowed"); } return result; } Index: ext/json/generator/extconf.rb =================================================================== --- ext/json/generator/extconf.rb (revision 35567) +++ ext/json/generator/extconf.rb (revision 35568) @@ -1,3 +1,4 @@ require 'mkmf' +$defs << "-DJSON_GENERATOR" create_makefile 'json/ext/generator' Index: ext/json/generator/generator.h =================================================================== --- ext/json/generator/generator.h (revision 35567) +++ ext/json/generator/generator.h (revision 35568) @@ -4,6 +4,7 @@ #include <string.h> #include <assert.h> #include <math.h> +#include <ctype.h> #include "ruby.h" @@ -105,7 +106,6 @@ Data_Get_Struct(Vstate, JSON_Generator_State, state); \ buffer = cState_prepare_buffer(Vstate); \ generate_json_##type(buffer, Vstate, state, self); \ - RB_GC_GUARD(Vstate); \ return fbuffer_to_s(buffer) static VALUE mHash_to_json(int argc, VALUE *argv, VALUE self); Index: ext/json/lib/json/version.rb =================================================================== --- ext/json/lib/json/version.rb (revision 35567) +++ ext/json/lib/json/version.rb (revision 35568) @@ -1,6 +1,6 @@ module JSON # JSON version - VERSION = '1.6.6' + VERSION = '1.7.1' VERSION_ARRAY = VERSION.split(/\./).map { |x| x.to_i } # :nodoc: VERSION_MAJOR = VERSION_ARRAY[0] # :nodoc: VERSION_MINOR = VERSION_ARRAY[1] # :nodoc: Index: ext/json/lib/json/common.rb =================================================================== --- ext/json/lib/json/common.rb (revision 35567) +++ ext/json/lib/json/common.rb (revision 35568) @@ -1,4 +1,5 @@ require 'json/version' +require 'json/generic_object' module JSON class << self Index: ext/json/parser/depend =================================================================== --- ext/json/parser/depend (revision 35567) +++ ext/json/parser/depend (revision 35568) @@ -1 +1 @@ -parser.o: parser.c parser.h +parser.o: parser.c parser.h $(srcdir)/../fbuffer/fbuffer.h Index: ext/json/parser/parser.rl =================================================================== --- ext/json/parser/parser.rl (revision 35567) +++ ext/json/parser/parser.rl (revision 35568) @@ -705,6 +705,7 @@ source = convert_encoding(StringValue(source)); } json->current_nesting = 0; + StringValue(source); json->len = RSTRING_LEN(source); json->source = RSTRING_PTR(source);; json->Vsource = source; Index: ext/json/parser/parser.c =================================================================== --- ext/json/parser/parser.c (revision 35567) +++ ext/json/parser/parser.c (revision 35568) @@ -1721,6 +1721,7 @@ source = convert_encoding(StringValue(source)); } json->current_nesting = 0; + StringValue(source); json->len = RSTRING_LEN(source); json->source = RSTRING_PTR(source);; json->Vsource = source; @@ -1728,7 +1729,7 @@ } -#line 1732 "parser.c" +#line 1733 "parser.c" static const int JSON_start = 1; static const int JSON_first_final = 10; static const int JSON_error = 0; @@ -1736,7 +1737,7 @@ static const int JSON_en_main = 1; -#line 739 "parser.rl" +#line 740 "parser.rl" static VALUE cParser_parse_strict(VALUE self) @@ -1747,16 +1748,16 @@ GET_PARSER; -#line 1751 "parser.c" +#line 1752 "parser.c" { cs = JSON_start; } -#line 749 "parser.rl" +#line 750 "parser.rl" p = json->source; pe = p + json->len; -#line 1760 "parser.c" +#line 1761 "parser.c" { if ( p == pe ) goto _test_eof; @@ -1812,7 +1813,7 @@ goto st1; goto st5; tr3: -#line 728 "parser.rl" +#line 729 "parser.rl" { char *np; json->current_nesting = 1; @@ -1821,7 +1822,7 @@ } goto st10; tr4: -#line 721 "parser.rl" +#line 722 "parser.rl" { char *np; json->current_nesting = 1; @@ -1833,7 +1834,7 @@ if ( ++p == pe ) goto _test_eof10; case 10: -#line 1837 "parser.c" +#line 1838 "parser.c" switch( (*p) ) { case 13: goto st10; case 32: goto st10; @@ -1890,7 +1891,7 @@ _out: {} } -#line 752 "parser.rl" +#line 753 "parser.rl" if (cs >= JSON_first_final && p == pe) { return result; @@ -1902,7 +1903,7 @@ -#line 1906 "parser.c" +#line 1907 "parser.c" static const int JSON_quirks_mode_start = 1; static const int JSON_quirks_mode_first_final = 10; static const int JSON_quirks_mode_error = 0; @@ -1910,7 +1911,7 @@ static const int JSON_quirks_mode_en_main = 1; -#line 777 "parser.rl" +#line 778 "parser.rl" static VALUE cParser_parse_quirks_mode(VALUE self) @@ -1921,16 +1922,16 @@ GET_PARSER; -#line 1925 "parser.c" +#line 1926 "parser.c" { cs = JSON_quirks_mode_start; } -#line 787 "parser.rl" +#line 788 "parser.rl" p = json->source; pe = p + json->len; -#line 1934 "parser.c" +#line 1935 "parser.c" { if ( p == pe ) goto _test_eof; @@ -1964,7 +1965,7 @@ cs = 0; goto _out; tr2: -#line 769 "parser.rl" +#line 770 "parser.rl" { char *np = JSON_parse_value(json, p, pe, &result); if (np == NULL) { p--; {p++; cs = 10; goto _out;} } else {p = (( np))-1;} @@ -1974,7 +1975,7 @@ if ( ++p == pe ) goto _test_eof10; case 10: -#line 1978 "parser.c" +#line 1979 "parser.c" switch( (*p) ) { case 13: goto st10; case 32: goto st10; @@ -2063,7 +2064,7 @@ _out: {} } -#line 790 "parser.rl" +#line 791 "parser.rl" if (cs >= JSON_quirks_mode_first_final && p == pe) { return result; Index: test/json/test_json_encoding.rb =================================================================== --- test/json/test_json_encoding.rb (revision 35567) +++ test/json/test_json_encoding.rb (revision 35568) @@ -4,7 +4,7 @@ require 'test/unit' require File.join(File.dirname(__FILE__), 'setup_variant') -class TC_JSONEncoding < Test::Unit::TestCase +class TestJSONEncoding < Test::Unit::TestCase include JSON def setup Index: test/json/test_json_unicode.rb =================================================================== --- test/json/test_json_unicode.rb (revision 35567) +++ test/json/test_json_unicode.rb (revision 35568) @@ -4,7 +4,7 @@ require 'test/unit' require File.join(File.dirname(__FILE__), 'setup_variant') -class TC_JSONUnicode < Test::Unit::TestCase +class TestJSONUnicode < Test::Unit::TestCase include JSON def test_unicode Index: test/json/test_json_fixtures.rb =================================================================== --- test/json/test_json_fixtures.rb (revision 35567) +++ test/json/test_json_fixtures.rb (revision 35568) @@ -4,7 +4,7 @@ require 'test/unit' require File.join(File.dirname(__FILE__), 'setup_variant') -class TC_JSONFixtures < Test::Unit::TestCase +class TestJSONFixtures < Test::Unit::TestCase def setup fixtures = File.join(File.dirname(__FILE__), 'fixtures/*.json') passed, failed = Dir[fixtures].partition { |f| f['pass'] } Index: test/json/test_json_generate.rb =================================================================== --- test/json/test_json_generate.rb (revision 35567) +++ test/json/test_json_generate.rb (revision 35568) @@ -4,7 +4,7 @@ require 'test/unit' require File.join(File.dirname(__FILE__), 'setup_variant') -class TC_JSONGenerate < Test::Unit::TestCase +class TestJSONGenerate < Test::Unit::TestCase include JSON def setup Index: test/json/test_json_addition.rb =================================================================== --- test/json/test_json_addition.rb (revision 35567) +++ test/json/test_json_addition.rb (revision 35568) @@ -10,7 +10,7 @@ require 'json/add/ostruct' require 'date' -class TC_JSONAddition < Test::Unit::TestCase +class TestJSONAddition < Test::Unit::TestCase include JSON class A @@ -64,7 +64,7 @@ def to_json(*args) { - 'json_class' => 'TC_JSONAddition::Nix', + 'json_class' => 'TestJSONAddition::Nix', }.to_json(*args) end end @@ -88,7 +88,7 @@ a_hash = JSON.parse(json, :create_additions => false) assert_kind_of Hash, a_hash assert_equal( - {"args"=>[666], "json_class"=>"TC_JSONAddition::A"}.sort_by { |k,| k }, + {"args"=>[666], "json_class"=>"TestJSONAddition::A"}.sort_by { |k,| k }, a_hash.sort_by { |k,| k } ) end @@ -97,7 +97,7 @@ b = B.new assert !B.json_creatable? json = generate(b) - assert_equal({ "json_class"=>"TC_JSONAddition::B" }, JSON.parse(json)) + assert_equal({ "json_class"=>"TestJSONAddition::B" }, JSON.parse(json)) end def test_extended_json_fail2 Index: test/json/test_json.rb =================================================================== --- test/json/test_json.rb (revision 35567) +++ test/json/test_json.rb (revision 35568) @@ -21,7 +21,7 @@ end end -class TC_JSON < Test::Unit::TestCase +class TestJSON < Test::Unit::TestCase include JSON def setup @@ -109,6 +109,8 @@ def test_parse_json_primitive_values assert_raise(JSON::ParserError) { JSON.parse('') } assert_raise(JSON::ParserError) { JSON.parse('', :quirks_mode => true) } + assert_raise(TypeError) { JSON::Parser.new(nil).parse } + assert_raise(TypeError) { JSON::Parser.new(nil, :quirks_mode => true).parse } assert_raise(TypeError) { JSON.parse(nil) } assert_raise(TypeError) { JSON.parse(nil, :quirks_mode => true) } assert_raise(JSON::ParserError) { JSON.parse(' /* foo */ ') } @@ -314,6 +316,16 @@ assert res.item_set? end + def test_parse_generic_object + res = parse('{"foo":"bar", "baz":{}}', :object_class => JSON::GenericObject) + assert_equal(JSON::GenericObject, res.class) + assert_equal "bar", res.foo + assert_equal "bar", res["foo"] + assert_equal "bar", res[:foo] + assert_equal "bar", res.to_hash[:foo] + assert_equal(JSON::GenericObject, res.baz.class) + end + def test_generate_core_subclasses_with_new_to_json obj = SubHash2["foo" => SubHash2["bar" => true]] obj_json = JSON(obj) Index: test/json/test_json_string_matching.rb =================================================================== --- test/json/test_json_string_matching.rb (revision 35567) +++ test/json/test_json_string_matching.rb (revision 35568) @@ -6,7 +6,7 @@ require 'stringio' require 'time' -class TestJsonStringMatching < Test::Unit::TestCase +class TestJSONStringMatching < Test::Unit::TestCase include JSON class TestTime < ::Time -- ML: ruby-changes@q... Info: http://www.atdot.net/~ko1/quickml/