RFC8259 8259
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +61 -0
- data/.rspec +4 -0
- data/.yardopts +2 -0
- data/Gemfile +58 -0
- data/LICENSE.txt +40 -0
- data/README.txt +1 -0
- data/RFC8259 +899 -0
- data/RFC8259.gemspec +89 -0
- data/Rakefile +86 -0
- data/lib/RFC8259.rb +94 -0
- data/lib/RFC8259/array.rb +136 -0
- data/lib/RFC8259/dumper.rb +255 -0
- data/lib/RFC8259/false.rb +79 -0
- data/lib/RFC8259/null.rb +79 -0
- data/lib/RFC8259/number.rb +149 -0
- data/lib/RFC8259/object.rb +137 -0
- data/lib/RFC8259/parser.ry +275 -0
- data/lib/RFC8259/string.rb +226 -0
- data/lib/RFC8259/true.rb +79 -0
- data/lib/RFC8259/value.rb +96 -0
- data/lib/RFC8259/version.rb +46 -0
- data/spec/RFC8259_spec.rb +305 -0
- data/spec/acceptance/README.txt +66 -0
- data/spec/acceptance/invalid/0001-ws/0001-verical-tab.txt +1 -0
- data/spec/acceptance/invalid/0001-ws/0002-null.txt +0 -0
- data/spec/acceptance/invalid/0001-ws/0003-space-in-number-1.txt +1 -0
- data/spec/acceptance/invalid/0001-ws/0004-space-in-number-2.txt +1 -0
- data/spec/acceptance/invalid/0001-ws/0005-space-in-number-3.txt +1 -0
- data/spec/acceptance/invalid/0001-ws/0006-space-in-number-4.txt +1 -0
- data/spec/acceptance/invalid/0001-ws/0007-space-in-number-5.txt +1 -0
- data/spec/acceptance/invalid/0001-ws/0008-space-in-number-6.txt +1 -0
- data/spec/acceptance/invalid/0001-ws/0009-space-in-literal.txt +1 -0
- data/spec/acceptance/invalid/0001-ws/0010-Unicode-LINE_SEPARATOR.txt +1 -0
- data/spec/acceptance/invalid/0002-comments/0001-C-style.txt +1 -0
- data/spec/acceptance/invalid/0002-comments/0002-C-plusplus-style.txt +2 -0
- data/spec/acceptance/invalid/0002-comments/0003-sh-style.txt +2 -0
- data/spec/acceptance/invalid/0002-comments/0004-python-docstring.txt +3 -0
- data/spec/acceptance/invalid/0002-comments/0005-SQL-style.txt +2 -0
- data/spec/acceptance/invalid/0002-comments/0006-BASIC-style.txt +2 -0
- data/spec/acceptance/invalid/0003-literals/0001-FALSE.txt +1 -0
- data/spec/acceptance/invalid/0003-literals/0002-NULL.txt +1 -0
- data/spec/acceptance/invalid/0003-literals/0003-TRUE.txt +1 -0
- data/spec/acceptance/invalid/0003-literals/0004-NUL.txt +1 -0
- data/spec/acceptance/invalid/0003-literals/0005-nil.txt +1 -0
- data/spec/acceptance/invalid/0003-literals/0006-undef.txt +1 -0
- data/spec/acceptance/invalid/0003-literals/0007-modifier.txt +1 -0
- data/spec/acceptance/invalid/0003-literals/0008-undefined.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0001-omit-zero.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0002-minus-dot.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0003-missing-frac.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0004-missing-exp.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0005-octal.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0006-hexadecimal.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0007-comma.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0008-perl-underscore.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0009-NaN.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0010-Inf.txt +1 -0
- data/spec/acceptance/invalid/0004-numbers/0011-Infinity.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0000-NUL.txt +0 -0
- data/spec/acceptance/invalid/0005-strings/0001-not-terminated.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0002-single-quote.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0003-back-quote.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0004-carriage-return.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0005-line-feed.txt +2 -0
- data/spec/acceptance/invalid/0005-strings/0006-unknown-escape-a.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0007-unknown-escape-perl-style.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0008-unknown-escape-C-style.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0009-unknown-escape-ruby-style.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0010-escape-too-short.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0011-C-string-concat.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0012-perl-string-concat.txt +1 -0
- data/spec/acceptance/invalid/0005-strings/0013-Java-string-concat.txt +1 -0
- data/spec/acceptance/invalid/0006-encodings/0001-CESU-8.txt +1 -0
- data/spec/acceptance/invalid/0006-encodings/0002-Windows-31J.txt +1 -0
- data/spec/acceptance/invalid/0006-encodings/0003-EBCDIC.txt +1 -0
- data/spec/acceptance/invalid/0006-encodings/0004-overlong-utf8.txt +1 -0
- data/spec/acceptance/invalid/0007-arrays/0001-lacks-open.txt +1 -0
- data/spec/acceptance/invalid/0007-arrays/0002-lacks-close.txt +1 -0
- data/spec/acceptance/invalid/0007-arrays/0003-interleaving-parens.txt +1 -0
- data/spec/acceptance/invalid/0007-arrays/0004-dangling-comma.txt +1 -0
- data/spec/acceptance/invalid/0007-arrays/0005-missing-comma.txt +1 -0
- data/spec/acceptance/invalid/0007-arrays/0006-colon-instead-of-comma.txt +1 -0
- data/spec/acceptance/invalid/0008-hashes/0001-key-missing.txt +1 -0
- data/spec/acceptance/invalid/0008-hashes/0002-value-missing.txt +1 -0
- data/spec/acceptance/invalid/0008-hashes/0003-true-key.txt +1 -0
- data/spec/acceptance/invalid/0008-hashes/0004-false-key.txt +1 -0
- data/spec/acceptance/invalid/0008-hashes/0005-null-key.txt +1 -0
- data/spec/acceptance/invalid/0008-hashes/0006-numeric-key.txt +1 -0
- data/spec/acceptance/invalid/0008-hashes/0007-array-key.txt +1 -0
- data/spec/acceptance/invalid/0008-hashes/0008-hash-key.txt +1 -0
- data/spec/acceptance/invalid/0008-hashes/0009-key-not-escaped.txt +4 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0001-JSONP.txt +1 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0002-new-Array.txt +3 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0003-new-Date.txt +1 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0004-new-Error.txt +1 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0005-Math.txt +1 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0006-regular-expression.txt +1 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0007-function.txt +7 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0008-this.txt +1 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0009-plusplus.txt +3 -0
- data/spec/acceptance/invalid/0009-javascriptisms/0010-ternary-operator.txt +1 -0
- data/spec/acceptance/valid/0001-ws/0001-space.json +1 -0
- data/spec/acceptance/valid/0001-ws/0002-tab.json +1 -0
- data/spec/acceptance/valid/0001-ws/0003-lf.json +1 -0
- data/spec/acceptance/valid/0001-ws/0004-cr.json +1 -0
- data/spec/acceptance/valid/0001-ws/0005-before.json +1 -0
- data/spec/acceptance/valid/0001-ws/0006-after.json +1 -0
- data/spec/acceptance/valid/0001-ws/0007-around-comma.json +3 -0
- data/spec/acceptance/valid/0001-ws/0008-around-colon.json +3 -0
- data/spec/acceptance/valid/0002-bare-values/0001-false.json +1 -0
- data/spec/acceptance/valid/0002-bare-values/0002-null.json +1 -0
- data/spec/acceptance/valid/0002-bare-values/0003-true.json +1 -0
- data/spec/acceptance/valid/0002-bare-values/0004-number.json +1 -0
- data/spec/acceptance/valid/0002-bare-values/0005-string.json +1 -0
- data/spec/acceptance/valid/0003-literals/0001-false.json +1 -0
- data/spec/acceptance/valid/0003-literals/0002-null.json +1 -0
- data/spec/acceptance/valid/0003-literals/0003-true.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0000-zero.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0001-one.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0002-two.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0003-three.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0004-four.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0005-five.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0006-six.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0007-seven.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0008-eight.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0009-nine.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0010-ten.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0011-minus.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0012-fraction.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0013-exponent.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0014-exponent-minus.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0015-exponent-plus.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0016-complex.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0017-DBL_MAX.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0018-DBL_MIN.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0019-subnormal-number.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0020-1E400.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0021-pi.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0022-UINT32_MAX.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0023-UINT64_MAX.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0024-INT64_MIN.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0025-high-resolution-zero.json +1 -0
- data/spec/acceptance/valid/0004-numbers/0026-high-resolution-100.json +1 -0
- data/spec/acceptance/valid/0005-strings/0001-empty.json +1 -0
- data/spec/acceptance/valid/0005-strings/0002-basic-latin.json +1 -0
- data/spec/acceptance/valid/0005-strings/0003-escapes.json +1 -0
- data/spec/acceptance/valid/0005-strings/0004-raw-unicode.json +1 -0
- data/spec/acceptance/valid/0005-strings/0005-escaped-unicode.json +1 -0
- data/spec/acceptance/valid/0005-strings/0006-escaped-NUL.json +1 -0
- data/spec/acceptance/valid/0005-strings/0007-escaped-invalid-unicode-still-valid-as-json.json +1 -0
- data/spec/acceptance/valid/0005-strings/0008-ruby-json-gem-cant-handle-this.json +1 -0
- data/spec/acceptance/valid/0005-strings/0009-unescaped-invalid-javascript-still-valid-as-json.json +1 -0
- data/spec/acceptance/valid/0005-strings/0010-escaped-separated-surrogate.json +1 -0
- data/spec/acceptance/valid/0005-strings/0011-escaped-surrogate-then-normal.json +1 -0
- data/spec/acceptance/valid/0006-m17n/0001-genesis.json +6 -0
- data/spec/acceptance/valid/0006-m17n/0002-heart-sutra.json +5 -0
- data/spec/acceptance/valid/0006-m17n/0003-escaped-valid-surrogate-pair.json +1 -0
- data/spec/acceptance/valid/0006-m17n/0004-unescaped-valid-supplementary-multilingual-plane.json +1 -0
- data/spec/acceptance/valid/0007-arrays/0000-empty.json +1 -0
- data/spec/acceptance/valid/0007-arrays/0001-one-element.json +1 -0
- data/spec/acceptance/valid/0007-arrays/0002-multiple-elements.json +33 -0
- data/spec/acceptance/valid/0007-arrays/0003-various-types.json +1 -0
- data/spec/acceptance/valid/0007-arrays/0004-nested.json +17 -0
- data/spec/acceptance/valid/0008-hashes/0000-empty.json +1 -0
- data/spec/acceptance/valid/0008-hashes/0001-onekey.json +1 -0
- data/spec/acceptance/valid/0008-hashes/0002-many-keys.json +5 -0
- data/spec/acceptance/valid/0008-hashes/0003-empty-key.json +3 -0
- data/spec/acceptance/valid/0008-hashes/0004-true-value.json +3 -0
- data/spec/acceptance/valid/0008-hashes/0005-false-value.json +3 -0
- data/spec/acceptance/valid/0008-hashes/0006-null-value.json +3 -0
- data/spec/acceptance/valid/0008-hashes/0007-string-value.json +3 -0
- data/spec/acceptance/valid/0008-hashes/0008-numeric-value.json +3 -0
- data/spec/acceptance/valid/0008-hashes/0009-array-value.json +8 -0
- data/spec/acceptance/valid/0008-hashes/0010-hash-value.json +20 -0
- data/spec/acceptance/valid/0008-hashes/0011-duplicate-key.json +4 -0
- data/spec/acceptance/valid/0008-hashes/0012-duplicate-key-in-different-representations.json +4 -0
- data/spec/acceptance/valid/0009-complicated/0001-jsonschema.json +46 -0
- data/spec/acceptance/valid/0009-complicated/0002-example-in-RFC7159-section-13.json +14 -0
- data/spec/acceptance/valid/0009-complicated/0003-example-in-RFC7159-section-13.json +22 -0
- data/spec/spec_helper.rb +60 -0
- metadata +530 -0
@@ -0,0 +1,305 @@
|
|
1
|
+
#! /your/favourite/path/to/rspec
|
2
|
+
# -*- coding: utf-8 -*-
|
3
|
+
|
4
|
+
# Copyright (c) 2014 Urabe, Shyouhei. All rights reserved.
|
5
|
+
#
|
6
|
+
# Redistribution and use in source and binary forms, with or without
|
7
|
+
# modification, are permitted provided that the following conditions are met:
|
8
|
+
#
|
9
|
+
# - Redistributions of source code must retain the above copyright
|
10
|
+
# notice, this list of conditions and the following disclaimer.
|
11
|
+
#
|
12
|
+
# - Redistributions in binary form must reproduce the above copyright
|
13
|
+
# notice, this list of conditions and the following disclaimer in
|
14
|
+
# the documentation and/or other materials provided with the
|
15
|
+
# distribution.
|
16
|
+
#
|
17
|
+
# - Neither the name of Internet Society, IETF or IETF Trust, nor the
|
18
|
+
# names of specific contributors, may be used to endorse or promote
|
19
|
+
# products derived from this software without specific prior written
|
20
|
+
# permission.
|
21
|
+
#
|
22
|
+
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS “AS IS”
|
23
|
+
# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
24
|
+
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
25
|
+
# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
26
|
+
# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
27
|
+
# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
28
|
+
# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
29
|
+
# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
30
|
+
# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
31
|
+
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
32
|
+
# POSSIBILITY OF SUCH DAMAGE.
|
33
|
+
|
34
|
+
require_relative 'spec_helper'
|
35
|
+
require 'pathname'
|
36
|
+
|
37
|
+
describe RFC8259 do
|
38
|
+
this_dir = Pathname.new __dir__
|
39
|
+
|
40
|
+
describe '.load' do
|
41
|
+
the_dir = this_dir + 'acceptance/valid'
|
42
|
+
the_dir.find do |f|
|
43
|
+
case f.extname when '.json'
|
44
|
+
it "should accept: #{f.basename}" do
|
45
|
+
expect do
|
46
|
+
f.open encoding: Encoding::UTF_8 do |fp|
|
47
|
+
RFC8259.load fp
|
48
|
+
end
|
49
|
+
end.to_not raise_exception
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
the_dir = this_dir + 'acceptance/invalid'
|
55
|
+
the_dir.find do |f|
|
56
|
+
case f.extname when '.txt'
|
57
|
+
it "should reject: #{f.basename}" do
|
58
|
+
expect do
|
59
|
+
f.open do |fp|
|
60
|
+
RFC8259.load fp
|
61
|
+
end
|
62
|
+
end.to raise_exception
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
[
|
68
|
+
Encoding::UTF_16BE,
|
69
|
+
Encoding::UTF_16LE,
|
70
|
+
Encoding::UTF_32BE,
|
71
|
+
Encoding::UTF_32LE,
|
72
|
+
].each do |enc|
|
73
|
+
the_dir = this_dir + 'acceptance'
|
74
|
+
the_dir.find do |f|
|
75
|
+
case f.extname when '.json', '.txt'
|
76
|
+
it "should reject: #{enc}-encoded #{f.basename}" do
|
77
|
+
expect do
|
78
|
+
f.open "rb", external_encoding: Encoding::UTF_8, internal_encoding: enc do |fp|
|
79
|
+
RFC8259.load fp
|
80
|
+
end
|
81
|
+
end.to raise_exception(Encoding::CompatibilityError)
|
82
|
+
end
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
87
|
+
|
88
|
+
describe '.dump' do
|
89
|
+
the_dir = this_dir + 'acceptance/valid'
|
90
|
+
the_dir.find do |f|
|
91
|
+
case f.extname when '.json'
|
92
|
+
it "should round-trip: #{f.basename}" do
|
93
|
+
str1 = f.read encoding: Encoding::UTF_8
|
94
|
+
obj = RFC8259.load str1
|
95
|
+
str2 = RFC8259.dump obj
|
96
|
+
# not interested in indents
|
97
|
+
expect(str2.gsub(/\s+/, '')).to eq(str1.gsub(/\s+/, ''))
|
98
|
+
end
|
99
|
+
end
|
100
|
+
end
|
101
|
+
|
102
|
+
context 'from something outside JSON world' do
|
103
|
+
{
|
104
|
+
false => 'false',
|
105
|
+
true => 'true',
|
106
|
+
nil => 'null',
|
107
|
+
0 => '0',
|
108
|
+
0.5 => '0.5', # 0.5 has no error
|
109
|
+
'foo' => '"foo"',
|
110
|
+
"\"\\\/\b\f\n\r\t"=> '"\"\\\/\b\f\n\r\t"',
|
111
|
+
"\xED\xBA\xAD".force_encoding('utf-8') => '"\\uDEAD"', # invalid UTF8 to be valid escaped UTF8
|
112
|
+
'foo'.encode('utf-32le') => '"foo"',
|
113
|
+
"\xDE\xAD".force_encoding('utf-16be') => '"\\uDEAD"',
|
114
|
+
[] => '[ ]',
|
115
|
+
[0] => '[ 0 ]',
|
116
|
+
[0,1] => '[ 0, 1 ]',
|
117
|
+
{} => '{ }',
|
118
|
+
{'1'=>1} => '{ "1": 1 }',
|
119
|
+
{''=>''} => '{ "": "" }',
|
120
|
+
(0.0/0.0) => false,
|
121
|
+
(1.0/0.0) => false,
|
122
|
+
BigDecimal("NaN") => false,
|
123
|
+
// => false,
|
124
|
+
0..1 => false,
|
125
|
+
{{}=>{}} => false,
|
126
|
+
{[]=>[]} => false,
|
127
|
+
{1=>1} => false,
|
128
|
+
{nil=>nil} => false,
|
129
|
+
Object.new => false,
|
130
|
+
Class.new => false,
|
131
|
+
Proc.new {} => false,
|
132
|
+
}.each_pair do |src, expected|
|
133
|
+
if expected
|
134
|
+
it { expect(RFC8259.dump src).to eq(expected) }
|
135
|
+
else
|
136
|
+
it { expect{RFC8259.dump src}.to raise_exception }
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
140
|
+
it 'raises for loops' do
|
141
|
+
expect do
|
142
|
+
RFC8259.dump [].tap {|i| i << i }
|
143
|
+
end.to raise_exception(Errno::ELOOP)
|
144
|
+
end
|
145
|
+
end
|
146
|
+
end
|
147
|
+
|
148
|
+
context 'versus', skip: true do
|
149
|
+
the_dir = this_dir + 'acceptance/valid'
|
150
|
+
the_targets = Array.new
|
151
|
+
the_dir.find do |f|
|
152
|
+
case f.extname when '.json'
|
153
|
+
begin
|
154
|
+
f.open 'r:utf-8' do |fp|
|
155
|
+
RFC8259.load fp, plain:true
|
156
|
+
end
|
157
|
+
rescue RuntimeError
|
158
|
+
# there are cases JSON can't be represented in PORO
|
159
|
+
# we ignore them here.
|
160
|
+
else
|
161
|
+
the_targets.push f
|
162
|
+
end
|
163
|
+
end
|
164
|
+
end
|
165
|
+
the_dir = this_dir + 'acceptance/invalid'
|
166
|
+
the_invalids = Array.new
|
167
|
+
the_dir.find do |f|
|
168
|
+
case f.extname when '.txt'
|
169
|
+
the_invalids.push f
|
170
|
+
end
|
171
|
+
end
|
172
|
+
|
173
|
+
require 'json'
|
174
|
+
require 'oj'
|
175
|
+
require 'yajl'
|
176
|
+
targets = {
|
177
|
+
JSON => {
|
178
|
+
load: -> str {
|
179
|
+
JSON.parse str
|
180
|
+
},
|
181
|
+
dump: -> obj {
|
182
|
+
begin
|
183
|
+
ret = JSON.generate obj
|
184
|
+
rescue
|
185
|
+
raise "JSON (not us) failed: #{$!.inspect}"
|
186
|
+
else
|
187
|
+
unless ret.valid_encoding?
|
188
|
+
raise "JSON (not us) is broken: generated #{ret.dump}"
|
189
|
+
end
|
190
|
+
return ret
|
191
|
+
end
|
192
|
+
},
|
193
|
+
},
|
194
|
+
|
195
|
+
Oj => {
|
196
|
+
load: -> str {
|
197
|
+
Oj.load str
|
198
|
+
},
|
199
|
+
dump: -> obj {
|
200
|
+
begin
|
201
|
+
ret = Oj.dump obj
|
202
|
+
rescue
|
203
|
+
raise "Oj (not us) failed: #{$!.inspect}"
|
204
|
+
else
|
205
|
+
unless ret.valid_encoding?
|
206
|
+
raise "Oj (not us) is broken: generated #{ret.dump}"
|
207
|
+
end
|
208
|
+
return ret
|
209
|
+
end
|
210
|
+
},
|
211
|
+
},
|
212
|
+
|
213
|
+
Yajl => {
|
214
|
+
load: -> str {
|
215
|
+
Yajl::Parser.parse str, allow_comments: false, symbolize_keys: false
|
216
|
+
},
|
217
|
+
dump: -> obj {
|
218
|
+
begin
|
219
|
+
ret = Yajl::Encoder.encode obj
|
220
|
+
rescue
|
221
|
+
raise "Yajl (not us) failed: #{$!.inspect}"
|
222
|
+
else
|
223
|
+
unless ret.valid_encoding?
|
224
|
+
raise "Yajl (not us) is broken: generated #{ret.dump}"
|
225
|
+
end
|
226
|
+
return ret
|
227
|
+
end
|
228
|
+
},
|
229
|
+
},
|
230
|
+
}
|
231
|
+
|
232
|
+
targets.each_pair do |klass, howto|
|
233
|
+
describe klass do
|
234
|
+
the_invalids.each do |f|
|
235
|
+
it "should reject: #{f.basename}" do
|
236
|
+
begin
|
237
|
+
theirs = f.open 'r:utf-8' do |fp|
|
238
|
+
howto[:load].(fp.read)
|
239
|
+
end
|
240
|
+
rescue
|
241
|
+
# ok
|
242
|
+
else
|
243
|
+
pending "#{klass} (not us) failed to reject: #{theirs.inspect}"
|
244
|
+
end
|
245
|
+
end
|
246
|
+
end
|
247
|
+
|
248
|
+
the_targets.each do |f|
|
249
|
+
context f.basename do
|
250
|
+
before :all do
|
251
|
+
str = f.open 'r:utf-8' do |fp| fp.read end
|
252
|
+
@ours = RFC8259.load str, plain: true
|
253
|
+
begin
|
254
|
+
@theirs = howto[:load].(str)
|
255
|
+
rescue
|
256
|
+
pending "#{klass} (not us) failed to accept: #{$!.inspect}"
|
257
|
+
end
|
258
|
+
# JSON.load sometimes generates Infinity and that's not JSONable
|
259
|
+
case @theirs when Array
|
260
|
+
case @theirs[0] when Float
|
261
|
+
if @theirs[0].infinite?
|
262
|
+
pending "#{klass} (not us) generates non-JSONables: #{@theirs.inspect}"
|
263
|
+
end
|
264
|
+
end
|
265
|
+
end
|
266
|
+
end
|
267
|
+
|
268
|
+
it "compare load" do
|
269
|
+
if @ours != @theirs
|
270
|
+
pending "They load differently: \n#{@ours.inspect} versus \n#{@theirs.inspect}"
|
271
|
+
end
|
272
|
+
end
|
273
|
+
|
274
|
+
it "compare dump ours" do
|
275
|
+
ours = RFC8259.dump @ours
|
276
|
+
theirs = howto[:dump].(@ours) rescue pending($!.message)
|
277
|
+
if ours.gsub(/\s+/, '') != theirs.gsub(/\s+/, '')
|
278
|
+
pending "They dump differently: \n#{ours.dump} versus \n#{theirs.dump}"
|
279
|
+
end
|
280
|
+
end
|
281
|
+
|
282
|
+
it "compare dump theirs" do
|
283
|
+
ours = RFC8259.dump @theirs
|
284
|
+
theirs = (howto[:dump].(@theirs) rescue pending($!.message))
|
285
|
+
if ours.gsub(/\s+/, '') != theirs.gsub(/\s+/, '')
|
286
|
+
pending "They dump differently: \n#{ours.dump} versus \n#{theirs.dump}"
|
287
|
+
end
|
288
|
+
end
|
289
|
+
end
|
290
|
+
end
|
291
|
+
end
|
292
|
+
end
|
293
|
+
end
|
294
|
+
end
|
295
|
+
|
296
|
+
#
|
297
|
+
# Local Variables:
|
298
|
+
# mode: ruby
|
299
|
+
# coding: utf-8-unix
|
300
|
+
# indent-tabs-mode: t
|
301
|
+
# tab-width: 3
|
302
|
+
# ruby-indent-level: 3
|
303
|
+
# fill-column: 79
|
304
|
+
# default-justification: full
|
305
|
+
# End:
|
@@ -0,0 +1,66 @@
|
|
1
|
+
This directory contains various JSON and quasi-JSON texts. The files
|
2
|
+
under "valid" directory are believed to be valid JSON texts, while
|
3
|
+
those under "invalid" are believed to be invalid. And the author of
|
4
|
+
this library believe that there is no instance of text that exhibits
|
5
|
+
Russell's paradox -like behaviour, where one cannot say if that text
|
6
|
+
(if any) is valid or invalid.
|
7
|
+
|
8
|
+
All files under this directory, including this file itself, are
|
9
|
+
written by me, Urabe Shyouhei <shyouhei@ruby-lang.org>. You can
|
10
|
+
safely copy & paste them to your project to test your own JSON parser.
|
11
|
+
|
12
|
+
I repeat the license of this project below, just in case you separate
|
13
|
+
this test suite form the library.
|
14
|
+
|
15
|
+
----------------------------------------------------------------------
|
16
|
+
|
17
|
+
Copyright (c) 2014 Urabe, Shyouhei. All rights reserved.
|
18
|
+
|
19
|
+
Redistribution and use in source and binary forms, with or without
|
20
|
+
modification, are permitted provided that the following conditions are
|
21
|
+
met:
|
22
|
+
|
23
|
+
- Redistributions of source code must retain the above copyright
|
24
|
+
notice, this list of conditions and the following disclaimer.
|
25
|
+
|
26
|
+
- Redistributions in binary form must reproduce the above copyright
|
27
|
+
notice, this list of conditions and the following disclaimer in
|
28
|
+
the documentation and/or other materials provided with the
|
29
|
+
distribution.
|
30
|
+
|
31
|
+
- Neither the name of Internet Society, IETF or IETF Trust, nor the
|
32
|
+
names of specific contributors, may be used to endorse or promote
|
33
|
+
products derived from this software without specific prior written
|
34
|
+
permission.
|
35
|
+
|
36
|
+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
37
|
+
“AS IS” AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
38
|
+
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
39
|
+
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
40
|
+
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
41
|
+
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
42
|
+
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
43
|
+
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
44
|
+
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
45
|
+
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
46
|
+
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
47
|
+
|
48
|
+
----------------------------------------------------------------------
|
49
|
+
|
50
|
+
P.S. For those who copy & paste the test cases to your own parser:
|
51
|
+
|
52
|
+
- In convenience for your own parser, most (not all) files starts
|
53
|
+
with '[' and ends with ']'. This is because that should also pass
|
54
|
+
older JSON spec (RFC4627).
|
55
|
+
|
56
|
+
- RFC7159 requests us, with using the strongest word (“MUST”) that
|
57
|
+
all the valid examples are to be accepted. On the other hand the
|
58
|
+
RFC _allows_ you to extend the grammar to, say, accept JavaScript
|
59
|
+
comments and so on. So failure in parsing valid examples are
|
60
|
+
fatal, but accepting invalid examples might not.
|
61
|
+
|
62
|
+
- RFC7159 tells no so much about semantics. For instance it does
|
63
|
+
not define object equality. It does not even define the character
|
64
|
+
set of parsed JSON strings (it DOES define the encoding of
|
65
|
+
generated JSON text themselves though).
|
66
|
+
|
@@ -0,0 +1 @@
|
|
1
|
+
[]
|
Binary file
|
@@ -0,0 +1 @@
|
|
1
|
+
[- 1]
|
@@ -0,0 +1 @@
|
|
1
|
+
[-0 .1]
|
@@ -0,0 +1 @@
|
|
1
|
+
[-0. 1]
|
@@ -0,0 +1 @@
|
|
1
|
+
[-0.1 e1]
|
@@ -0,0 +1 @@
|
|
1
|
+
[-0.1e -1]
|
@@ -0,0 +1 @@
|
|
1
|
+
[-0.1e- 1]
|
@@ -0,0 +1 @@
|
|
1
|
+
[ f a l s e ]
|
@@ -0,0 +1 @@
|
|
1
|
+
["Here you are U+0208 ->",
"<- (might be invisible in github) and is invalid"]
|
@@ -0,0 +1 @@
|
|
1
|
+
[/* comments are invalid in JSON */]
|
@@ -0,0 +1 @@
|
|
1
|
+
[FALSE]
|
@@ -0,0 +1 @@
|
|
1
|
+
[NULL]
|
@@ -0,0 +1 @@
|
|
1
|
+
[TRUE]
|
@@ -0,0 +1 @@
|
|
1
|
+
[NUL]
|
@@ -0,0 +1 @@
|
|
1
|
+
[nil]
|
@@ -0,0 +1 @@
|
|
1
|
+
[undef]
|
@@ -0,0 +1 @@
|
|
1
|
+
[JSON::false]
|
@@ -0,0 +1 @@
|
|
1
|
+
[undefined]
|
@@ -0,0 +1 @@
|
|
1
|
+
[.1]
|