Class: Avromatic::Model::Types::UnionType

Inherits:
AbstractType show all
Defined in:
lib/avromatic/model/types/union_type.rb

Constant Summary collapse

MEMBER_INDEX =
::Avromatic::IO::DatumReader::UNION_MEMBER_INDEX

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(member_types:) ⇒ UnionType

Returns a new instance of UnionType.



13
14
15
16
17
# File 'lib/avromatic/model/types/union_type.rb', line 13

def initialize(member_types:)
  @member_types = member_types
  @value_classes = member_types.flat_map(&:value_classes)
  @input_classes = member_types.flat_map(&:input_classes).uniq
end

Instance Attribute Details

#input_classesObject (readonly)

Returns the value of attribute input_classes.



11
12
13
# File 'lib/avromatic/model/types/union_type.rb', line 11

def input_classes
  @input_classes
end

#member_typesObject (readonly)

Returns the value of attribute member_types.



11
12
13
# File 'lib/avromatic/model/types/union_type.rb', line 11

def member_types
  @member_types
end

#value_classesObject (readonly)

Returns the value of attribute value_classes.



11
12
13
# File 'lib/avromatic/model/types/union_type.rb', line 11

def value_classes
  @value_classes
end

Instance Method Details

#coerce(input) ⇒ Object



23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
# File 'lib/avromatic/model/types/union_type.rb', line 23

def coerce(input)
  return input if coerced?(input)

  result = nil
  if input.is_a?(Hash) && input.key?(MEMBER_INDEX)
    result = member_types[input.delete(MEMBER_INDEX)].coerce(input)
  else
    member_types.find do |member_type|
      result = safe_coerce(member_type, input)
    end
  end

  unless result
    raise ArgumentError.new("Could not coerce '#{input.inspect}' to #{name}")
  end

  result
end

#coerced?(value) ⇒ Boolean

Returns:

  • (Boolean)


42
43
44
45
46
# File 'lib/avromatic/model/types/union_type.rb', line 42

def coerced?(value)
  value.nil? || member_types.any? do |member_type|
    member_type.coerced?(value)
  end
end

#coercible?(input) ⇒ Boolean

Returns:

  • (Boolean)


48
49
50
51
52
# File 'lib/avromatic/model/types/union_type.rb', line 48

def coercible?(input)
  coerced?(input) || member_types.any? do |member_type|
    member_type.coercible?(input)
  end
end

#nameObject



19
20
21
# File 'lib/avromatic/model/types/union_type.rb', line 19

def name
  "union[#{member_types.map(&:name).join(', ')}]"
end

#referenced_model_classesObject



70
71
72
# File 'lib/avromatic/model/types/union_type.rb', line 70

def referenced_model_classes
  member_types.flat_map(&:referenced_model_classes).tap(&:uniq!).freeze
end

#serialize(value, strict:) ⇒ Object



54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
# File 'lib/avromatic/model/types/union_type.rb', line 54

def serialize(value, strict:)
  # Avromatic does not treat the null of an optional field as part of the union
  return nil if value.nil?

  member_index = find_index(value)
  if member_index.nil?
    raise ArgumentError.new("Expected #{value.inspect} to be one of #{value_classes.map(&:name)}")
  end

  hash = member_types[member_index].serialize(value, strict: strict)
  if !strict && Avromatic.use_custom_datum_writer && value.is_a?(Avromatic::Model::Attributes)
    hash[Avromatic::IO::UNION_MEMBER_INDEX] = member_index
  end
  hash
end