bson 4.1.1-java → 4.2.0-java

Sign up to get free protection for your applications and to get access to all the features.
Files changed (82) hide show
  1. checksums.yaml +4 -4
  2. checksums.yaml.gz.sig +0 -0
  3. data.tar.gz.sig +0 -0
  4. data/Rakefile +18 -3
  5. data/lib/bson-ruby.jar +0 -0
  6. data/lib/bson.rb +6 -4
  7. data/lib/bson/array.rb +1 -1
  8. data/lib/bson/binary.rb +4 -2
  9. data/lib/bson/code.rb +1 -1
  10. data/lib/bson/code_with_scope.rb +1 -1
  11. data/lib/bson/config.rb +1 -1
  12. data/lib/bson/date.rb +1 -1
  13. data/lib/bson/date_time.rb +1 -1
  14. data/lib/bson/decimal128.rb +318 -0
  15. data/lib/bson/decimal128/builder.rb +448 -0
  16. data/lib/bson/document.rb +2 -2
  17. data/lib/bson/environment.rb +13 -1
  18. data/lib/bson/false_class.rb +1 -1
  19. data/lib/bson/float.rb +1 -1
  20. data/lib/bson/hash.rb +1 -1
  21. data/lib/bson/int32.rb +46 -0
  22. data/lib/bson/int64.rb +46 -0
  23. data/lib/bson/integer.rb +1 -1
  24. data/lib/bson/max_key.rb +1 -1
  25. data/lib/bson/min_key.rb +1 -1
  26. data/lib/bson/object_id.rb +3 -2
  27. data/lib/bson/open_struct.rb +57 -0
  28. data/lib/bson/regexp.rb +87 -19
  29. data/lib/bson/registry.rb +1 -1
  30. data/lib/bson/specialized.rb +1 -1
  31. data/lib/bson/string.rb +1 -1
  32. data/lib/bson/symbol.rb +1 -1
  33. data/lib/bson/time.rb +1 -1
  34. data/lib/bson/timestamp.rb +2 -2
  35. data/lib/bson/true_class.rb +1 -1
  36. data/lib/bson/version.rb +2 -2
  37. data/spec/bson/array_spec.rb +1 -1
  38. data/spec/bson/binary_spec.rb +2 -1
  39. data/spec/bson/corpus_spec.rb +68 -0
  40. data/spec/bson/decimal128_spec.rb +1583 -0
  41. data/spec/bson/document_spec.rb +1 -1
  42. data/spec/bson/driver_bson_spec.rb +77 -0
  43. data/spec/bson/int32_spec.rb +58 -0
  44. data/spec/bson/int64_spec.rb +58 -0
  45. data/spec/bson/open_struct_spec.rb +144 -0
  46. data/spec/bson/raw_spec.rb +540 -0
  47. data/spec/bson/regexp_spec.rb +7 -7
  48. data/spec/bson/timestamp_spec.rb +1 -1
  49. data/spec/spec_helper.rb +5 -0
  50. data/spec/support/common_driver.rb +347 -0
  51. data/spec/support/corpus-tests/array.json +43 -0
  52. data/spec/support/corpus-tests/boolean.json +27 -0
  53. data/spec/support/corpus-tests/code.json +67 -0
  54. data/spec/support/corpus-tests/code_w_scope.json +78 -0
  55. data/spec/support/corpus-tests/document.json +36 -0
  56. data/spec/support/corpus-tests/double.json +69 -0
  57. data/spec/support/corpus-tests/failures/binary.json +69 -0
  58. data/spec/support/corpus-tests/failures/datetime.json +31 -0
  59. data/spec/support/corpus-tests/failures/dbpointer.json +42 -0
  60. data/spec/support/corpus-tests/failures/int64.json +38 -0
  61. data/spec/support/corpus-tests/failures/symbol.json +62 -0
  62. data/spec/support/corpus-tests/failures/undefined.json +13 -0
  63. data/spec/support/corpus-tests/int32.json +38 -0
  64. data/spec/support/corpus-tests/maxkey.json +12 -0
  65. data/spec/support/corpus-tests/minkey.json +12 -0
  66. data/spec/support/corpus-tests/null.json +12 -0
  67. data/spec/support/corpus-tests/oid.json +28 -0
  68. data/spec/support/corpus-tests/regex.json +37 -0
  69. data/spec/support/corpus-tests/string.json +67 -0
  70. data/spec/support/corpus-tests/timestamp.json +18 -0
  71. data/spec/support/corpus-tests/top.json +62 -0
  72. data/spec/support/corpus.rb +265 -0
  73. data/spec/support/driver-spec-tests/decimal128/decimal128-1.json +363 -0
  74. data/spec/support/driver-spec-tests/decimal128/decimal128-2.json +793 -0
  75. data/spec/support/driver-spec-tests/decimal128/decimal128-3.json +1771 -0
  76. data/spec/support/driver-spec-tests/decimal128/decimal128-4.json +165 -0
  77. data/spec/support/driver-spec-tests/decimal128/decimal128-5.json +402 -0
  78. data/spec/support/driver-spec-tests/decimal128/decimal128-6.json +131 -0
  79. data/spec/support/driver-spec-tests/decimal128/decimal128-7.json +327 -0
  80. data/spec/support/shared_examples.rb +1 -1
  81. metadata +77 -4
  82. metadata.gz.sig +0 -0
@@ -24,7 +24,7 @@ describe Regexp do
24
24
 
25
25
  it "returns the binary data plus type" do
26
26
  expect(object.as_json).to eq(
27
- { "$regex" => "\\W+", "$options" => "i" }
27
+ { "$regex" => "\\W+", "$options" => "im" }
28
28
  )
29
29
  end
30
30
 
@@ -55,9 +55,7 @@ describe Regexp do
55
55
  /\d+/
56
56
  end
57
57
 
58
- let :bson do
59
- [obj.source, BSON::NULL_BYTE, BSON::NULL_BYTE].join ''
60
- end
58
+ let(:bson) { "#{obj.source}#{BSON::NULL_BYTE}m#{BSON::NULL_BYTE}" }
61
59
 
62
60
  it_behaves_like "a serializable bson element"
63
61
 
@@ -69,7 +67,9 @@ describe Regexp do
69
67
  context "when the regexp has no options" do
70
68
 
71
69
  let(:obj) { /\d+/ }
72
- let(:bson) { "#{obj.source}#{BSON::NULL_BYTE}#{BSON::NULL_BYTE}" }
70
+ # Ruby always has a BSON regex's equivalent of multiline on
71
+ # http://www.regular-expressions.info/modifiers.html
72
+ let(:bson) { "#{obj.source}#{BSON::NULL_BYTE}m#{BSON::NULL_BYTE}" }
73
73
 
74
74
  it_behaves_like "a serializable bson element"
75
75
 
@@ -83,7 +83,7 @@ describe Regexp do
83
83
  context "when ignoring case" do
84
84
 
85
85
  let(:obj) { /\W+/i }
86
- let(:bson) { "#{obj.source}#{BSON::NULL_BYTE}i#{BSON::NULL_BYTE}" }
86
+ let(:bson) { "#{obj.source}#{BSON::NULL_BYTE}im#{BSON::NULL_BYTE}" }
87
87
 
88
88
  it_behaves_like "a serializable bson element"
89
89
 
@@ -107,7 +107,7 @@ describe Regexp do
107
107
  context "when matching extended" do
108
108
 
109
109
  let(:obj) { /\W+/x }
110
- let(:bson) { "#{obj.source}#{BSON::NULL_BYTE}x#{BSON::NULL_BYTE}" }
110
+ let(:bson) { "#{obj.source}#{BSON::NULL_BYTE}mx#{BSON::NULL_BYTE}" }
111
111
 
112
112
  it_behaves_like "a serializable bson element"
113
113
 
@@ -55,7 +55,7 @@ describe BSON::Timestamp do
55
55
  end
56
56
 
57
57
  it "returns the binary data plus type" do
58
- expect(object.as_json).to eq({ "t" => 10, "i" => 50 })
58
+ expect(object.as_json).to eq({"$timestamp" => { "t" => 10, "i" => 50 } })
59
59
  end
60
60
 
61
61
  it_behaves_like "a JSON serializable object"
@@ -12,9 +12,14 @@
12
12
  # See the License for the specific language governing permissions and
13
13
  # limitations under the License.
14
14
 
15
+ CURRENT_PATH = File.expand_path(File.dirname(__FILE__))
16
+ DRIVER_COMMON_BSON_TESTS = Dir.glob("#{CURRENT_PATH}/support/driver-spec-tests/**/*.json")
17
+ BSON_CORPUS_TESTS = Dir.glob("#{CURRENT_PATH}/support/corpus-tests/*.json")
18
+
15
19
  $LOAD_PATH.unshift(File.dirname(__FILE__))
16
20
  $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), "..", "lib"))
17
21
 
22
+ require "ostruct"
18
23
  require "bson"
19
24
  require "json"
20
25
  require "rspec"
@@ -0,0 +1,347 @@
1
+ # Copyright (C) 2016 MongoDB, Inc.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require 'json'
16
+ require 'bigdecimal'
17
+
18
+ module BSON
19
+ module CommonDriver
20
+
21
+ # Represents a Common Driver specification test.
22
+ #
23
+ # @since 4.2.0
24
+ class Spec
25
+
26
+ # The spec description.
27
+ #
28
+ # @return [ String ] The spec description.
29
+ #
30
+ # @since 4.2.0
31
+ attr_reader :description
32
+
33
+ # The document key of the object to test.
34
+ #
35
+ # @return [ String ] The document key.
36
+ #
37
+ # @since 4.2.0
38
+ attr_reader :test_key
39
+
40
+ # Instantiate the new spec.
41
+ #
42
+ # @example Create the spec.
43
+ # Spec.new(file)
44
+ #
45
+ # @param [ String ] file The name of the yaml file.
46
+ #
47
+ # @since 4.2.0
48
+ def initialize(file)
49
+ @spec = ::JSON.parse(File.read(file))
50
+ @valid = @spec['valid'] || []
51
+ @invalid = @spec['parseErrors'] || []
52
+ @description = @spec['description']
53
+ @test_key = @spec['test_key']
54
+ end
55
+
56
+ # Get a list of tests that don't raise exceptions.
57
+ #
58
+ # @example Get the list of valid tests.
59
+ # spec.valid_tests
60
+ #
61
+ # @return [ Array<BSON::CommonDriver::Test> ] The list of valid Tests.
62
+ #
63
+ # @since 4.2.0
64
+ def valid_tests
65
+ @valid_tests ||=
66
+ @valid.collect do |test|
67
+ BSON::CommonDriver::Test.new(self, test)
68
+ end
69
+ end
70
+
71
+ # Get a list of tests that raise exceptions.
72
+ #
73
+ # @example Get the list of invalid tests.
74
+ # spec.invalid_tests
75
+ #
76
+ # @return [ Array<BSON::CommonDriver::Test> ] The list of invalid Tests.
77
+ #
78
+ # @since 4.2.0
79
+ def invalid_tests
80
+ @invalid_tests ||=
81
+ @invalid.collect do |test|
82
+ BSON::CommonDriver::Test.new(self, test)
83
+ end
84
+ end
85
+
86
+ # The class of the bson object to test.
87
+ #
88
+ # @example Get the class of the object to test.
89
+ # spec.klass
90
+ #
91
+ # @return [ Class ] The object class.
92
+ #
93
+ # @since 4.2.0
94
+ def klass
95
+ @klass ||= BSON.const_get(description)
96
+ end
97
+ end
98
+
99
+ # Represents a single CommonDriver test.
100
+ #
101
+ # @since 4.2.0
102
+ class Test
103
+
104
+ # The test description.
105
+ #
106
+ # @return [ String ] The test description.
107
+ #
108
+ # @since 4.2.0
109
+ attr_reader :description
110
+
111
+ # The test subject.
112
+ #
113
+ # @return [ String ] The test subject.
114
+ #
115
+ # @since 4.2.0
116
+ attr_reader :subject
117
+
118
+ # The string to use to create a Decimal128.
119
+ #
120
+ # @return [ String ] The string to use in creating a Decimal128 object.
121
+ #
122
+ # @since 4.2.0
123
+ attr_reader :string
124
+
125
+ # The expected string representation of the Decimal128 object.
126
+ #
127
+ # @return [ String ] The object as a string.
128
+ #
129
+ # @since 4.2.0
130
+ attr_reader :match_string
131
+
132
+ # The json representation of the object.
133
+ #
134
+ # @return [ Hash ] The json representation of the object.
135
+ #
136
+ # @since 4.2.0
137
+ attr_reader :ext_json
138
+
139
+ # Instantiate the new Test.
140
+ #
141
+ # @example Create the test.
142
+ # Test.new(test)
143
+ #
144
+ # @param [ CommonDriver::Spec ] spec The test specification.
145
+ # @param [ Hash ] test The test specification.
146
+ #
147
+ # @since 4.2.0
148
+ def initialize(spec, test)
149
+ @spec = spec
150
+ @description = test['description']
151
+ @string = test['string']
152
+ @match_string = test['match_string']
153
+ @ext_json = ::JSON.parse(test['extjson']) if test['extjson']
154
+ @from_ext_json = test['from_extjson'].nil? ? true : test['from_extjson']
155
+ @to_ext_json = test['to_extjson'].nil? ? true : test['to_extjson']
156
+ @subject = test['subject']
157
+ @test_key = spec.test_key
158
+ end
159
+
160
+ # Get the reencoded document in hex format.
161
+ #
162
+ # @example Get the reencoded document as hex.
163
+ # test.reencoded_hex
164
+ #
165
+ # @return [ String ] The reencoded document in hex format.
166
+ #
167
+ # @since 4.2.0
168
+ def reencoded_hex
169
+ decoded_document.to_bson.to_s.unpack("H*").first.upcase
170
+ end
171
+
172
+ # The object tested.
173
+ #
174
+ # @example Get the object for this test.
175
+ # test.object
176
+ #
177
+ # @return [ BSON::Object ] The object.
178
+ #
179
+ # @since 4.2.0
180
+ def object
181
+ @object ||= decoded_document[@test_key]
182
+ end
183
+
184
+ # The object as json, in a document with the test key.
185
+ #
186
+ # @example Get a document with the object at the test key.
187
+ # test.document_as_json
188
+ #
189
+ # @return [ BSON::Document ] The json document.
190
+ #
191
+ # @since 4.2.0
192
+ def document_as_json
193
+ { @test_key => object.as_json }
194
+ end
195
+
196
+ # Use the string in the extended json to instantiate the bson object.
197
+ #
198
+ # @example Get a bson object from the string in the extended json.
199
+ # test.from_json
200
+ #
201
+ # @return [ BSON::Object ] The BSON object.
202
+ #
203
+ # @since 4.2.0
204
+ def from_json_string
205
+ klass.from_string(@ext_json[@test_key][klass::EXTENDED_JSON_KEY])
206
+ end
207
+
208
+ # Create an object from the given test string.
209
+ #
210
+ # @example
211
+ # test.parse_string
212
+ #
213
+ # @return [ BSON::Object ] The object.
214
+ #
215
+ # @since 4.2.0
216
+ def parse_string
217
+ klass.from_string(string)
218
+ end
219
+
220
+ # Attempt to create an object from an invalid string.
221
+ #
222
+ # @example
223
+ # test.parse_invalid_string
224
+ #
225
+ # @raise [ Error ] Parsing an invalid string will raise an error.
226
+ #
227
+ # @since 4.2.0
228
+ def parse_invalid_string
229
+ klass.from_string(subject)
230
+ end
231
+
232
+ # The class of the object being tested.
233
+ #
234
+ # @example
235
+ # test.klass
236
+ #
237
+ # @return [ Class ] The object class.
238
+ #
239
+ # @since 4.2.0
240
+ def klass
241
+ @spec.klass
242
+ end
243
+
244
+ # The error class of a parse error.
245
+ #
246
+ # @example
247
+ # test.parse_error
248
+ #
249
+ # @return [ Class ] The parse error class.
250
+ #
251
+ # @since 4.2.0
252
+ def parse_error
253
+ klass::InvalidRange
254
+ end
255
+
256
+ # Whether the object can be instantiated from extended json.
257
+ #
258
+ # @example Check if an object can be instantiated from the extended json.
259
+ # test.from_ex_json?
260
+ #
261
+ # @return [ true, false ] If the object can be instantiated from
262
+ # the provided extended json.
263
+ #
264
+ # @since 4.2.0
265
+ def from_ext_json?
266
+ @ext_json && @from_ext_json
267
+ end
268
+
269
+ # Whether the object can be represented as extended json.
270
+ #
271
+ # @example Check if an object can be represented as extended json.
272
+ # test.to_ext_json?
273
+ #
274
+ # @return [ true, false ] If the object can be represented as
275
+ # extended json.
276
+ #
277
+ # @since 4.2.0
278
+ def to_ext_json?
279
+ @ext_json && @to_ext_json
280
+ end
281
+
282
+ # Whether the object can be instantiated from a string.
283
+ #
284
+ # @example Check if an object can be instantiated from a string.
285
+ # test.from_string?
286
+ #
287
+ # @return [ true, false ] If the object can be instantiated from a string.
288
+ #
289
+ # @since 4.2.0
290
+ def from_string?
291
+ @string && @from_ext_json
292
+ end
293
+
294
+ # The expected string representation of the test object.
295
+ #
296
+ # @example Get the expected String representation of the test object.
297
+ # test.expected_to_string
298
+ #
299
+ # @return [ String ] The expected string representation.
300
+ #
301
+ # @since 4.2.0
302
+ def expected_to_string
303
+ match_string || string
304
+ end
305
+
306
+ # The Ruby class to which this bson object can be converted via a helper.
307
+ #
308
+ # @example Get the native type to which this object can be converted.
309
+ # test.native_type
310
+ #
311
+ # @return [ Class ] The Ruby native type.
312
+ #
313
+ # @since 4.2.0
314
+ def native_type
315
+ klass::NATIVE_TYPE
316
+ end
317
+
318
+ # Get the object converted to an instance of the native Ruby type.
319
+ #
320
+ # @example Get a native Ruby instance.
321
+ # test.native_type_conversion
322
+ #
323
+ # @return [ Object ] An instance of the Ruby native type.
324
+ #
325
+ # @since 4.2.0
326
+ def native_type_conversion
327
+ object.send("to_#{to_snake_case(native_type)}")
328
+ end
329
+
330
+ private
331
+
332
+ def to_snake_case(string)
333
+ string.to_s.gsub(/::/, '/').
334
+ gsub(/([A-Z]+)([A-Z][a-z])/,'\1_\2').
335
+ gsub(/([a-z\d])([A-Z])/,'\1_\2').
336
+ tr("-", "_").
337
+ downcase
338
+ end
339
+
340
+ def decoded_document
341
+ @document ||= (data = [ @subject ].pack('H*')
342
+ buffer = BSON::ByteBuffer.new(data)
343
+ BSON::Document.from_bson(buffer))
344
+ end
345
+ end
346
+ end
347
+ end
@@ -0,0 +1,43 @@
1
+ {
2
+ "description": "Array",
3
+ "bson_type": "0x04",
4
+ "test_key": "a",
5
+ "valid": [
6
+ {
7
+ "description": "Empty",
8
+ "bson": "0D000000046100050000000000",
9
+ "extjson": "{\"a\" : []}"
10
+ },
11
+ {
12
+ "description": "Single Element Array",
13
+ "bson": "140000000461000C0000001030000A0000000000",
14
+ "extjson": "{\"a\" : [10]}"
15
+ },
16
+ {
17
+ "description": "Single Element Array with index set incorrectly",
18
+ "bson": "130000000461000B00000010000A0000000000",
19
+ "canonical_bson": "140000000461000C0000001030000A0000000000",
20
+ "extjson": "{\"a\" : [10]}"
21
+ },
22
+ {
23
+ "description": "Single Element Array with index set incorrectly",
24
+ "bson": "150000000461000D000000106162000A0000000000",
25
+ "canonical_bson": "140000000461000C0000001030000A0000000000",
26
+ "extjson": "{\"a\" : [10]}"
27
+ }
28
+ ],
29
+ "decodeErrors": [
30
+ {
31
+ "description": "Array length too long: eats outer terminator",
32
+ "bson": "140000000461000D0000001030000A0000000000"
33
+ },
34
+ {
35
+ "description": "Array length too short: leaks terminator",
36
+ "bson": "140000000461000B0000001030000A0000000000"
37
+ },
38
+ {
39
+ "description": "Invalid Array: bad string length in field",
40
+ "bson": "1A00000004666F6F00100000000230000500000062617A000000"
41
+ }
42
+ ]
43
+ }