[
https://issues.apache.org/jira/browse/AVRO-2039?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=16692931#comment-16692931
]
ASF GitHub Bot commented on AVRO-2039:
--------------------------------------
Fokko closed pull request #230: AVRO-2039: Ruby encoding performance
improvements
URL: https://github.com/apache/avro/pull/230
This is a PR merged from a forked repository.
As GitHub hides the original diff on merge, it is displayed below for
the sake of provenance:
As this is a foreign pull request (from a fork), the diff is supplied
below (as it won't show otherwise due to GitHub magic):
diff --git a/lang/ruby/lib/avro/io.rb b/lang/ruby/lib/avro/io.rb
index 26bda973a..958159c79 100644
--- a/lang/ruby/lib/avro/io.rb
+++ b/lang/ruby/lib/avro/io.rb
@@ -5,9 +5,9 @@
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
-#
+#
# http://www.apache.org/licenses/LICENSE-2.0
-#
+#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@@ -45,7 +45,7 @@ def initialize(reader)
def byte!
@reader.read(1).unpack('C').first
end
-
+
def read_null
# null is written as zero byte's
nil
@@ -159,7 +159,7 @@ def write_null(datum)
nil
end
- # a boolean is written as a single byte
+ # a boolean is written as a single byte
# whose value is either 0 (false) or 1 (true).
def write_boolean(datum)
on_disk = datum ? 1.chr : 0.chr
@@ -504,7 +504,7 @@ def write(datum, encoder)
def write_data(writers_schema, logical_datum, encoder)
datum = writers_schema.type_adapter.encode(logical_datum)
- unless Schema.validate(writers_schema, datum, encoded = true)
+ unless Schema.validate(writers_schema, datum, { recursive: false,
encoded: true })
raise AvroTypeError.new(writers_schema, datum)
end
@@ -539,6 +539,7 @@ def write_enum(writers_schema, datum, encoder)
end
def write_array(writers_schema, datum, encoder)
+ raise AvroTypeError.new(writers_schema, datum) unless
datum.is_a?(Array)
if datum.size > 0
encoder.write_long(datum.size)
datum.each do |item|
@@ -549,6 +550,7 @@ def write_array(writers_schema, datum, encoder)
end
def write_map(writers_schema, datum, encoder)
+ raise AvroTypeError.new(writers_schema, datum) unless datum.is_a?(Hash)
if datum.size > 0
encoder.write_long(datum.size)
datum.each do |k,v|
@@ -571,6 +573,7 @@ def write_union(writers_schema, datum, encoder)
end
def write_record(writers_schema, datum, encoder)
+ raise AvroTypeError.new(writers_schema, datum) unless datum.is_a?(Hash)
writers_schema.fields.each do |field|
write_data(field.type, datum[field.name], encoder)
end
diff --git a/lang/ruby/lib/avro/schema.rb b/lang/ruby/lib/avro/schema.rb
index 3acd07b7f..c1b150ead 100644
--- a/lang/ruby/lib/avro/schema.rb
+++ b/lang/ruby/lib/avro/schema.rb
@@ -96,8 +96,8 @@ def self.real_parse(json_obj, names=nil,
default_namespace=nil)
end
# Determine if a ruby datum is an instance of a schema
- def self.validate(expected_schema, logical_datum, encoded = false)
- SchemaValidator.validate!(expected_schema, logical_datum, encoded)
+ def self.validate(expected_schema, logical_datum, options = { recursive:
true, encoded: false })
+ SchemaValidator.validate!(expected_schema, logical_datum, options)
true
rescue SchemaValidator::ValidationError
false
diff --git a/lang/ruby/lib/avro/schema_validator.rb
b/lang/ruby/lib/avro/schema_validator.rb
index 2117e92d4..28022a8c6 100644
--- a/lang/ruby/lib/avro/schema_validator.rb
+++ b/lang/ruby/lib/avro/schema_validator.rb
@@ -20,7 +20,8 @@ class SchemaValidator
PATH_SEPARATOR = '.'.freeze
INT_RANGE = Schema::INT_MIN_VALUE..Schema::INT_MAX_VALUE
LONG_RANGE = Schema::LONG_MIN_VALUE..Schema::LONG_MAX_VALUE
- COMPLEX_TYPES = [:array, :error, :map, :record, :request]
+ COMPLEX_TYPES = [:array, :error, :map, :record, :request].freeze
+ BOOLEAN_VALUES = [true, false].freeze
class Result
attr_reader :errors
@@ -62,27 +63,54 @@ def to_s
TypeMismatchError = Class.new(ValidationError)
class << self
- def validate!(expected_schema, logical_datum, encoded = false)
+ def validate!(expected_schema, logical_datum, options = { recursive:
true, encoded: false })
+ options ||= {}
+ options[:recursive] = true unless options.key?(:recursive)
+
result = Result.new
- validate_recursive(expected_schema, logical_datum, ROOT_IDENTIFIER,
result, encoded)
+ if options[:recursive]
+ validate_recursive(expected_schema, logical_datum, ROOT_IDENTIFIER,
result, options)
+ else
+ validate_simple(expected_schema, logical_datum, ROOT_IDENTIFIER,
result, options)
+ end
fail ValidationError, result if result.failure?
result
end
private
- def validate_recursive(expected_schema, logical_datum, path, result,
encoded = false)
- datum = if encoded
- logical_datum
- else
- expected_schema.type_adapter.encode(logical_datum) rescue nil
- end
+ def validate_recursive(expected_schema, logical_datum, path, result,
options = {})
+ datum = resolve_datum(expected_schema, logical_datum,
options[:encoded])
+
+ validate_simple(expected_schema, datum, path, result, encoded: true)
+
+ case expected_schema.type_sym
+ when :array
+ validate_array(expected_schema, datum, path, result)
+ when :map
+ validate_map(expected_schema, datum, path, result)
+ when :union
+ validate_union(expected_schema, datum, path, result)
+ when :record, :error, :request
+ fail TypeMismatchError unless datum.is_a?(Hash)
+ expected_schema.fields.each do |field|
+ deeper_path = deeper_path_for_hash(field.name, path)
+ validate_recursive(field.type, datum[field.name], deeper_path,
result)
+ end
+ end
+ rescue TypeMismatchError
+ result.add_error(path, "expected type #{expected_schema.type_sym}, got
#{actual_value_message(datum)}")
+ end
+
+ def validate_simple(expected_schema, logical_datum, path, result,
options = {})
+ datum = resolve_datum(expected_schema, logical_datum,
options[:encoded])
+ validate_type(expected_schema)
case expected_schema.type_sym
when :null
fail TypeMismatchError unless datum.nil?
when :boolean
- fail TypeMismatchError unless [true, false].include?(datum)
+ fail TypeMismatchError unless BOOLEAN_VALUES.include?(datum)
when :string, :bytes
fail TypeMismatchError unless datum.is_a?(String)
when :int
@@ -92,36 +120,42 @@ def validate_recursive(expected_schema, logical_datum,
path, result, encoded = f
fail TypeMismatchError unless datum.is_a?(Integer)
result.add_error(path, "out of bound value #{datum}") unless
LONG_RANGE.cover?(datum)
when :float, :double
- fail TypeMismatchError unless [Float,
Integer].any?(&datum.method(:is_a?))
+ fail TypeMismatchError unless datum.is_a?(Float) ||
datum.is_a?(Integer)
when :fixed
if datum.is_a? String
- message = "expected fixed with size #{expected_schema.size}, got
\"#{datum}\" with size #{datum.size}"
- result.add_error(path, message) unless datum.bytesize ==
expected_schema.size
+ result.add_error(path, fixed_string_message(expected_schema.size,
datum)) unless datum.bytesize == expected_schema.size
else
result.add_error(path, "expected fixed with size
#{expected_schema.size}, got #{actual_value_message(datum)}")
end
when :enum
- message = "expected enum with values #{expected_schema.symbols}, got
#{actual_value_message(datum)}"
- result.add_error(path, message) unless
expected_schema.symbols.include?(datum)
- when :array
- validate_array(expected_schema, datum, path, result)
- when :map
- validate_map(expected_schema, datum, path, result)
- when :union
- validate_union(expected_schema, datum, path, result)
- when :record, :error, :request
- fail TypeMismatchError unless datum.is_a?(Hash)
- expected_schema.fields.each do |field|
- deeper_path = deeper_path_for_hash(field.name, path)
- validate_recursive(field.type, datum[field.name], deeper_path,
result)
- end
- else
- fail "Unexpected schema type #{expected_schema.type_sym}
#{expected_schema.inspect}"
+ result.add_error(path, enum_message(expected_schema.symbols, datum))
unless expected_schema.symbols.include?(datum)
end
rescue TypeMismatchError
result.add_error(path, "expected type #{expected_schema.type_sym}, got
#{actual_value_message(datum)}")
end
+ def resolve_datum(expected_schema, logical_datum, encoded)
+ if encoded
+ logical_datum
+ else
+ expected_schema.type_adapter.encode(logical_datum) rescue nil
+ end
+ end
+
+ def validate_type(expected_schema)
+ unless Avro::Schema::VALID_TYPES_SYM.include?(expected_schema.type_sym)
+ fail "Unexpected schema type #{expected_schema.type_sym}
#{expected_schema.inspect}"
+ end
+ end
+
+ def fixed_string_message(size, datum)
+ "expected fixed with size #{size}, got \"#{datum}\" with size
#{datum.size}"
+ end
+
+ def enum_message(symbols, datum)
+ "expected enum with values #{symbols}, got
#{actual_value_message(datum)}"
+ end
+
def validate_array(expected_schema, datum, path, result)
fail TypeMismatchError unless datum.is_a?(Array)
datum.each_with_index do |d, i|
@@ -145,9 +179,10 @@ def validate_union(expected_schema, datum, path, result)
validate_recursive(expected_schema.schemas.first, datum, path,
result)
return
end
- types_and_results = validate_possible_types(datum, expected_schema,
path)
- failures, successes = types_and_results.partition { |r|
r[:result].failure? }
- return if successes.any?
+ failures = []
+ compatible_type = first_compatible_type(datum, expected_schema, path,
failures)
+ return unless compatible_type.nil?
+
complex_type_failed = failures.detect { |r|
COMPLEX_TYPES.include?(r[:type]) }
if complex_type_failed
complex_type_failed[:result].errors.each { |error| result << error }
@@ -157,11 +192,12 @@ def validate_union(expected_schema, datum, path, result)
end
end
- def validate_possible_types(datum, expected_schema, path)
- expected_schema.schemas.map do |schema|
+ def first_compatible_type(datum, expected_schema, path, failures)
+ expected_schema.schemas.find do |schema|
result = Result.new
validate_recursive(schema, datum, path, result)
- { type: schema.type_sym, result: result }
+ failures << { type: schema.type_sym, result: result } if
result.failure?
+ !result.failure?
end
end
@@ -169,8 +205,6 @@ def deeper_path_for_hash(sub_key, path)
"#{path}#{PATH_SEPARATOR}#{sub_key}".squeeze(PATH_SEPARATOR)
end
- private
-
def actual_value_message(value)
avro_type = if value.is_a?(Integer)
ruby_integer_to_avro_type(value)
diff --git a/lang/ruby/test/test_io.rb b/lang/ruby/test/test_io.rb
index 70bb4d60c..b518708b0 100644
--- a/lang/ruby/test/test_io.rb
+++ b/lang/ruby/test/test_io.rb
@@ -158,6 +158,27 @@ def test_fixed
check_default(fixed_schema, '"a"', "a")
end
+ def test_record_with_nil
+ schema = Avro::Schema.parse('{"type":"record", "name":"rec",
"fields":[{"type":"int", "name":"i"}]}')
+ assert_raise(Avro::IO::AvroTypeError) do
+ write_datum(nil, schema)
+ end
+ end
+
+ def test_array_with_nil
+ schema = Avro::Schema.parse('{"type":"array", "items":"int"}')
+ assert_raise(Avro::IO::AvroTypeError) do
+ write_datum(nil, schema)
+ end
+ end
+
+ def test_map_with_nil
+ schema = Avro::Schema.parse('{"type":"map", "values":"long"}')
+ assert_raise(Avro::IO::AvroTypeError) do
+ write_datum(nil, schema)
+ end
+ end
+
def test_enum_with_duplicate
str = '{"type": "enum", "name": "Test","symbols" : ["AA", "AA"]}'
assert_raises(Avro::SchemaParseError) do
diff --git a/lang/ruby/test/test_schema_validator.rb
b/lang/ruby/test/test_schema_validator.rb
index e77569a31..c4759da7b 100644
--- a/lang/ruby/test/test_schema_validator.rb
+++ b/lang/ruby/test/test_schema_validator.rb
@@ -21,6 +21,10 @@ def validate!(schema, value)
Avro::SchemaValidator.validate!(schema, value)
end
+ def validate_simple!(schema, value)
+ Avro::SchemaValidator.validate!(schema, value, recursive: false)
+ end
+
def hash_to_schema(hash)
Avro::Schema.parse(hash.to_json)
end
@@ -36,13 +40,16 @@ def assert_failed_validation(messages)
assert_equal(assert_messages.size, result_errors.size)
end
- def assert_valid_schema(schema, valid, invalid)
+ def assert_valid_schema(schema, valid, invalid, simple = false)
valid.each do |value|
assert_nothing_raised { Avro::SchemaValidator.validate!(schema, value) }
+ assert_nothing_raised { Avro::SchemaValidator.validate!(schema, value,
recursive: false) } if simple
end
invalid.each do |value|
assert_raise { Avro::SchemaValidator.validate!(schema, value) }
+ assert_raise { Avro::SchemaValidator.validate!(schema, value, recursive:
false) } if simple
+ assert_nothing_raised { Avro::SchemaValidator.validate!(schema, value,
recursive: false) } unless simple
end
end
@@ -50,10 +57,15 @@ def test_validate_nil
schema = hash_to_schema(type: 'null', name: 'name')
assert_nothing_raised { validate!(schema, nil) }
+ assert_nothing_raised { validate_simple!(schema, nil) }
assert_failed_validation('at . expected type null, got int with value 1')
do
validate!(schema, 1)
end
+
+ assert_failed_validation('at . expected type null, got int with value 1')
do
+ validate_simple!(schema, 1)
+ end
end
def test_validate_boolean
@@ -61,52 +73,67 @@ def test_validate_boolean
assert_nothing_raised { validate!(schema, true) }
assert_nothing_raised { validate!(schema, false) }
+ assert_nothing_raised { validate_simple!(schema, true) }
+ assert_nothing_raised { validate_simple!(schema, false) }
assert_failed_validation('at . expected type boolean, got int with value
1') do
validate!(schema, 1)
end
+ assert_failed_validation('at . expected type boolean, got int with value
1') do
+ validate_simple!(schema, 1)
+ end
assert_failed_validation('at . expected type boolean, got null') do
validate!(schema, nil)
end
+ assert_failed_validation('at . expected type boolean, got null') do
+ validate_simple!(schema, nil)
+ end
end
def test_fixed_size_string
schema = hash_to_schema(type: 'fixed', name: 'some', size: 3)
assert_nothing_raised { validate!(schema, 'baf') }
+ assert_nothing_raised { validate_simple!(schema, 'baf') }
assert_failed_validation('at . expected fixed with size 3, got "some" with
size 4') do
validate!(schema, 'some')
end
+ assert_failed_validation('at . expected fixed with size 3, got "some" with
size 4') do
+ validate_simple!(schema, 'some')
+ end
assert_failed_validation('at . expected fixed with size 3, got null') do
validate!(schema, nil)
end
+ assert_failed_validation('at . expected fixed with size 3, got null') do
+ validate_simple!(schema, nil)
+ end
end
def test_original_validate_nil
schema = hash_to_schema(type: 'null', name: 'name')
- assert_valid_schema(schema, [nil], ['something'])
+ assert_valid_schema(schema, [nil], ['something'], true)
end
def test_original_validate_boolean
schema = hash_to_schema(type: 'boolean', name: 'name')
- assert_valid_schema(schema, [true, false], [nil, 1])
+ assert_valid_schema(schema, [true, false], [nil, 1], true)
end
def test_validate_string
schema = hash_to_schema(type: 'string', name: 'name')
- assert_valid_schema(schema, ['string'], [nil, 1])
+ assert_valid_schema(schema, ['string'], [nil, 1], true)
end
def test_validate_bytes
schema = hash_to_schema(type: 'bytes', name: 'name')
- assert_valid_schema(schema, ['string'], [nil, 1])
+ assert_valid_schema(schema, ['string'], [nil, 1], true)
end
def test_validate_int
@@ -115,41 +142,45 @@ def test_validate_int
assert_valid_schema(
schema,
[Avro::Schema::INT_MIN_VALUE, Avro::Schema::INT_MAX_VALUE, 1],
- [Avro::Schema::LONG_MIN_VALUE, Avro::Schema::LONG_MAX_VALUE, 'string']
+ [Avro::Schema::LONG_MIN_VALUE, Avro::Schema::LONG_MAX_VALUE, 'string'],
+ true
)
assert_failed_validation('at . out of bound value 9223372036854775807') do
validate!(schema, Avro::Schema::LONG_MAX_VALUE)
end
+ assert_failed_validation('at . out of bound value 9223372036854775807') do
+ validate_simple!(schema, Avro::Schema::LONG_MAX_VALUE)
+ end
end
def test_validate_long
schema = hash_to_schema(type: 'long', name: 'name')
- assert_valid_schema(schema, [Avro::Schema::LONG_MIN_VALUE,
Avro::Schema::LONG_MAX_VALUE, 1], [1.1, 'string'])
+ assert_valid_schema(schema, [Avro::Schema::LONG_MIN_VALUE,
Avro::Schema::LONG_MAX_VALUE, 1], [1.1, 'string'], true)
end
def test_validate_float
schema = hash_to_schema(type: 'float', name: 'name')
- assert_valid_schema(schema, [1.1, 1, Avro::Schema::LONG_MAX_VALUE],
['string'])
+ assert_valid_schema(schema, [1.1, 1, Avro::Schema::LONG_MAX_VALUE],
['string'], true)
end
def test_validate_double
schema = hash_to_schema(type: 'double', name: 'name')
- assert_valid_schema(schema, [1.1, 1, Avro::Schema::LONG_MAX_VALUE],
['string'])
+ assert_valid_schema(schema, [1.1, 1, Avro::Schema::LONG_MAX_VALUE],
['string'], true)
end
def test_validate_fixed
schema = hash_to_schema(type: 'fixed', name: 'name', size: 3)
- assert_valid_schema(schema, ['abc'], ['ab', 1, 1.1, true])
+ assert_valid_schema(schema, ['abc'], ['ab', 1, 1.1, true], true)
end
def test_validate_original_num
schema = hash_to_schema(type: 'enum', name: 'name', symbols: %w(a b))
- assert_valid_schema(schema, ['a', 'b'], ['c'])
+ assert_valid_schema(schema, ['a', 'b'], ['c'], true)
end
def test_validate_record
@@ -164,22 +195,22 @@ def test_validate_shallow_record
)
assert_nothing_raised { validate!(schema, 'sub' => 1) }
+ assert_nothing_raised { validate_simple!(schema, 'sub' => 1) }
assert_failed_validation('at .sub expected type int, got null') do
validate!(schema, {})
end
+ assert_nothing_raised { validate_simple!(schema, {}) }
assert_failed_validation('at . expected type record, got float with value
1.2') do
validate!(schema, 1.2)
end
+ assert_nothing_raised { validate_simple!(schema, 1.2) }
assert_failed_validation('at .sub expected type int, got float with value
1.2') do
validate!(schema, 'sub' => 1.2)
end
-
- assert_failed_validation('at .sub expected type int, got null') do
- validate!(schema, {})
- end
+ assert_nothing_raised { validate_simple!(schema, 'sub' => 1.2) }
end
def test_validate_array
@@ -188,18 +219,22 @@ def test_validate_array
items: [{ type: 'int', name: 'height' }])
assert_nothing_raised { validate!(schema, []) }
+ assert_nothing_raised { validate_simple!(schema, []) }
assert_failed_validation 'at . expected type array, got null' do
validate!(schema, nil)
end
+ assert_nothing_raised { validate_simple!(schema, nil) }
assert_failed_validation('at .[0] expected type int, got null') do
validate!(schema, [nil])
end
+ assert_nothing_raised { validate_simple!(schema, [nil]) }
assert_failed_validation('at .[3] expected type int, got string with value
"so wrong"') do
validate!(schema, [1, 3, 9, 'so wrong'])
end
+ assert_nothing_raised { validate_simple!(schema, [1, 3, 9, 'so wrong']) }
end
def test_validate_enum
@@ -208,10 +243,14 @@ def test_validate_enum
symbols: %w(one two three))
assert_nothing_raised { validate!(schema, 'one') }
+ assert_nothing_raised { validate_simple!(schema, 'one') }
assert_failed_validation('at . expected enum with values ["one", "two",
"three"], got string with value "five"') do
validate!(schema, 'five')
end
+ assert_failed_validation('at . expected enum with values ["one", "two",
"three"], got string with value "five"') do
+ validate_simple!(schema, 'five')
+ end
end
def test_validate_union_on_primitive_types
@@ -226,6 +265,7 @@ def test_validate_union_on_primitive_types
assert_failed_validation('at .what_ever expected union of [\'long\',
\'string\'], got null') {
validate!(schema, 'what_ever' => nil)
}
+ assert_nothing_raised { validate_simple!(schema, 'what_ever' => nil) }
end
def test_validate_union_of_nil_and_record_inside_array
@@ -267,22 +307,27 @@ def test_validate_union_of_nil_and_record_inside_array
assert_failed_validation('at .person expected type record, got null') {
validate!(schema, 'not at all' => nil)
}
+ assert_nothing_raised { validate_simple!(schema, 'person' => {}) }
+
assert_nothing_raised { validate!(schema, 'person' => {}) }
assert_nothing_raised { validate!(schema, 'person' => { houses: [] }) }
assert_nothing_raised { validate!(schema, 'person' => { 'houses' => [{
'number_of_rooms' => 1 }] }) }
+ assert_nothing_raised { validate_simple!(schema, 'person' => {}) }
+ assert_nothing_raised { validate_simple!(schema, 'person' => { houses: []
}) }
+ assert_nothing_raised { validate_simple!(schema, 'person' => { 'houses' =>
[{ 'number_of_rooms' => 1 }] }) }
+
message = 'at .person.houses[1].number_of_rooms expected type long, got
string with value "not valid at all"'
- assert_failed_validation(message) do
- validate!(
- schema,
- 'person' => {
- 'houses' => [
- { 'number_of_rooms' => 2 },
- { 'number_of_rooms' => 'not valid at all' }
- ]
- }
- )
- end
+ datum = {
+ 'person' => {
+ 'houses' => [
+ { 'number_of_rooms' => 2 },
+ { 'number_of_rooms' => 'not valid at all' }
+ ]
+ }
+ }
+ assert_failed_validation(message) { validate!(schema, datum) }
+ assert_nothing_raised { validate_simple!(schema, datum) }
end
def test_validate_map
@@ -293,18 +338,22 @@ def test_validate_map
])
assert_nothing_raised { validate!(schema, 'some' => 1) }
+ assert_nothing_raised { validate_simple!(schema, 'some' => 1) }
assert_failed_validation('at .some expected type int, got string with
value "nope"') do
validate!(schema, 'some' => 'nope')
end
+ assert_nothing_raised { validate_simple!(schema, 'some' => 'nope')}
assert_failed_validation("at . unexpected key type 'Symbol' in map") do
validate!(schema, some: 1)
end
+ assert_nothing_raised { validate_simple!(schema, some: 1) }
assert_failed_validation('at . expected type map, got null') do
validate!(schema, nil)
end
+ assert_nothing_raised { validate_simple!(schema, nil) }
end
def test_validate_deep_record
@@ -336,22 +385,27 @@ def test_validate_deep_record
])
assert_nothing_raised { validate!(schema, 'head' => { 'hair' => { 'color'
=> 'black' } }) }
+ assert_nothing_raised { validate_simple!(schema, 'head' => { 'hair' => {
'color' => 'black' } }) }
assert_failed_validation('at .head.hair.color expected type string, got
null') do
validate!(schema, 'head' => { 'hair' => { 'color' => nil } })
end
+ assert_nothing_raised { validate_simple!(schema, 'head' => { 'hair' => {
'color' => nil } }) }
assert_failed_validation('at .head.hair.color expected type string, got
null') do
validate!(schema, 'head' => { 'hair' => {} })
end
+ assert_nothing_raised { validate_simple!(schema, 'head' => { 'hair' => {}
}) }
assert_failed_validation('at .head.hair expected type record, got null') do
validate!(schema, 'head' => {})
end
+ assert_nothing_raised { validate_simple!(schema, 'head' => {}) }
assert_failed_validation('at . expected type record, got null') do
validate!(schema, nil)
end
+ assert_nothing_raised { validate_simple!(schema, nil) }
end
def test_validate_deep_record_with_array
@@ -377,14 +431,17 @@ def test_validate_deep_record_with_array
}
])
assert_nothing_raised { validate!(schema, 'fruits' => [{ 'name' =>
'apple', 'weight' => 30.2 }]) }
+ assert_nothing_raised { validate_simple!(schema, 'fruits' => [{ 'name' =>
'apple', 'weight' => 30.2 }]) }
assert_failed_validation('at .fruits[0].name expected type string, got
null') do
validate!(schema, 'fruits' => [{ 'name' => nil, 'weight' => 30.2 }])
end
+ assert_nothing_raised { validate_simple!(schema, 'fruits' => [{ 'name' =>
nil, 'weight' => 30.2 }]) }
assert_failed_validation('at .fruits expected type array, got int with
value 1') do
validate!(schema, 'fruits' => 1)
end
+ assert_nothing_raised { validate_simple!(schema, 'fruits' => 1) }
end
def test_validate_multiple_errors
@@ -397,6 +454,7 @@ def test_validate_multiple_errors
exception = assert_raise(Avro::SchemaValidator::ValidationError) do
validate!(schema, [nil, 'e'])
end
+ assert_nothing_raised { validate_simple!(schema, [nil, 'e']) }
assert_equal 2, exception.result.errors.size
assert_equal(
"at .[0] expected type int, got null\nat .[1] expected type int, got
string with value \"e\"",
----------------------------------------------------------------
This is an automated message from the Apache Git Service.
To respond to the message, please log on GitHub and use the
URL above to go to the specific comment.
For queries about this service, please contact Infrastructure at:
[email protected]
> Ruby encoding performance improvement
> -------------------------------------
>
> Key: AVRO-2039
> URL: https://issues.apache.org/jira/browse/AVRO-2039
> Project: Apache Avro
> Issue Type: Improvement
> Components: ruby
> Reporter: Tim Perkins
> Assignee: Tim Perkins
> Priority: Critical
>
> For a use case with a few levels of nesting and unions in several places
> within the schema we saw a 5x improvement in encoding performance with these
> changes to encoding using Ruby.
> 1. Avoid the exhaustive validation of schemas in a union
> 2. Avoid the repeated validation of nested schemas
> https://github.com/apache/avro/pull/230
--
This message was sent by Atlassian JIRA
(v7.6.3#76005)