lutaml-model 0.8.17 → 0.8.18
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/downstream-performance.yml +27 -1
- data/.github/workflows/js-pr-check.yml +102 -0
- data/.github/workflows/js-sync.yml +51 -0
- data/.github/workflows/opal.yml +26 -6
- data/.github/workflows/performance.yml +32 -7
- data/.github/workflows/rake.yml +78 -32
- data/.gitmodules +6 -0
- data/.rubocop_todo.yml +8 -0
- data/Gemfile +16 -1
- data/README.adoc +267 -0
- data/Rakefile +166 -4
- data/docs/_guides/schema-import.adoc +42 -0
- data/docs/_guides/xml-mapping.adoc +21 -0
- data/docs/_pages/validation.adoc +65 -0
- data/lib/compat/opal/generate_boot.rb +123 -0
- data/lib/compat/opal/js_bundle_entry.rb +42 -0
- data/lib/compat/opal/lutaml_model_boot.rb +497 -0
- data/lib/compat/opal/moxml_boot.rb +68 -0
- data/lib/compat/opal/yaml_compat.rb +32 -0
- data/lib/lutaml/json.rb +1 -1
- data/lib/lutaml/key_value/transform.rb +3 -8
- data/lib/lutaml/key_value/transformation/value_serializer.rb +14 -1
- data/lib/lutaml/key_value/transformation.rb +17 -5
- data/lib/lutaml/model/adapter_resolver.rb +2 -2
- data/lib/lutaml/model/attribute.rb +88 -11
- data/lib/lutaml/model/cached_type_resolver.rb +1 -1
- data/lib/lutaml/model/error/union_schema_unsupported_error.rb +11 -0
- data/lib/lutaml/model/global_context.rb +11 -8
- data/lib/lutaml/model/instrumentation.rb +2 -2
- data/lib/lutaml/model/mapping/mapping_rule.rb +0 -6
- data/lib/lutaml/model/register.rb +2 -2
- data/lib/lutaml/model/runtime_compatibility.rb +50 -0
- data/lib/lutaml/model/schema/class_loader.rb +58 -0
- data/lib/lutaml/model/schema/compiled_output.rb +83 -0
- data/lib/lutaml/model/schema/definitions/attribute.rb +32 -0
- data/lib/lutaml/model/schema/definitions/choice.rb +20 -0
- data/lib/lutaml/model/schema/definitions/facet.rb +40 -0
- data/lib/lutaml/model/schema/definitions/group_import.rb +22 -0
- data/lib/lutaml/model/schema/definitions/member_walk.rb +33 -0
- data/lib/lutaml/model/schema/definitions/model.rb +40 -0
- data/lib/lutaml/model/schema/definitions/namespace.rb +23 -0
- data/lib/lutaml/model/schema/definitions/restricted_type.rb +30 -0
- data/lib/lutaml/model/schema/definitions/sequence.rb +19 -0
- data/lib/lutaml/model/schema/definitions/simple_content.rb +22 -0
- data/lib/lutaml/model/schema/definitions/transform_facet.rb +21 -0
- data/lib/lutaml/model/schema/definitions/type_ref.rb +20 -0
- data/lib/lutaml/model/schema/definitions/union_type.rb +28 -0
- data/lib/lutaml/model/schema/definitions/xml_root.rb +20 -0
- data/lib/lutaml/model/schema/definitions.rb +24 -0
- data/lib/lutaml/model/schema/file_writer.rb +70 -0
- data/lib/lutaml/model/schema/generator/definitions_collection.rb +16 -2
- data/lib/lutaml/model/schema/generator/property.rb +21 -4
- data/lib/lutaml/model/schema/module_nesting.rb +31 -0
- data/lib/lutaml/model/schema/namespace_naming.rb +46 -0
- data/lib/lutaml/model/schema/registry_generator.rb +115 -0
- data/lib/lutaml/model/schema/renderers/base.rb +40 -0
- data/lib/lutaml/model/schema/renderers/mappings.rb +72 -0
- data/lib/lutaml/model/schema/renderers/member_decls.rb +115 -0
- data/lib/lutaml/model/schema/renderers/model.rb +121 -0
- data/lib/lutaml/model/schema/renderers/namespace.rb +30 -0
- data/lib/lutaml/model/schema/renderers/registration.rb +64 -0
- data/lib/lutaml/model/schema/renderers/required_files_calculator.rb +93 -0
- data/lib/lutaml/model/schema/renderers/restricted_type.rb +88 -0
- data/lib/lutaml/model/schema/renderers/union.rb +83 -0
- data/lib/lutaml/model/schema/renderers.rb +19 -0
- data/lib/lutaml/model/schema/rnc_compiler/source_resolver.rb +47 -0
- data/lib/lutaml/model/schema/rnc_compiler.rb +62 -0
- data/lib/lutaml/model/schema/rng_compiler/define_classifier.rb +91 -0
- data/lib/lutaml/model/schema/rng_compiler/element_visitor.rb +392 -0
- data/lib/lutaml/model/schema/rng_compiler/member_collector.rb +30 -0
- data/lib/lutaml/model/schema/rng_compiler/rng_helpers.rb +152 -0
- data/lib/lutaml/model/schema/rng_compiler/value_type_resolver.rb +125 -0
- data/lib/lutaml/model/schema/rng_compiler.rb +220 -0
- data/lib/lutaml/model/schema/templates.rb +162 -0
- data/lib/lutaml/model/schema/xml_compiler/element_order.rb +41 -0
- data/lib/lutaml/model/schema/xml_compiler/registry_generator.rb +31 -107
- data/lib/lutaml/model/schema/xml_compiler/spec_builder/complex_types.rb +191 -0
- data/lib/lutaml/model/schema/xml_compiler/spec_builder/members.rb +216 -0
- data/lib/lutaml/model/schema/xml_compiler/spec_builder/simple_types.rb +153 -0
- data/lib/lutaml/model/schema/xml_compiler/spec_builder.rb +167 -0
- data/lib/lutaml/model/schema/xml_compiler/supported_data_types.rb +87 -0
- data/lib/lutaml/model/schema/xml_compiler.rb +38 -517
- data/lib/lutaml/model/schema.rb +19 -0
- data/lib/lutaml/model/serialize/attribute_definition.rb +14 -2
- data/lib/lutaml/model/serialize/builder.rb +15 -2
- data/lib/lutaml/model/serialize/value_mapping.rb +9 -57
- data/lib/lutaml/model/serialize.rb +6 -9
- data/lib/lutaml/model/services/rule_value_extractor.rb +2 -3
- data/lib/lutaml/model/services.rb +0 -2
- data/lib/lutaml/model/store.rb +2 -1
- data/lib/lutaml/model/toml.rb +1 -1
- data/lib/lutaml/model/transform.rb +17 -39
- data/lib/lutaml/model/transformation_registry.rb +1 -1
- data/lib/lutaml/model/type.rb +1 -0
- data/lib/lutaml/model/union.rb +320 -0
- data/lib/lutaml/model/utils.rb +6 -0
- data/lib/lutaml/model/validation.rb +1 -4
- data/lib/lutaml/model/version.rb +1 -1
- data/lib/lutaml/model.rb +18 -0
- data/lib/lutaml/toml.rb +1 -1
- data/lib/lutaml/xml/adapter.rb +1 -1
- data/lib/lutaml/xml/adapter_loader.rb +1 -1
- data/lib/lutaml/xml/builder/base.rb +1 -1
- data/lib/lutaml/xml/builder.rb +1 -1
- data/lib/lutaml/xml/error/schema_validation_error.rb +25 -0
- data/lib/lutaml/xml/model_transform.rb +5 -1
- data/lib/lutaml/xml/schema/relaxng_schema.rb +5 -0
- data/lib/lutaml/xml/schema/xsd_schema.rb +4 -0
- data/lib/lutaml/xml/serialization/format_conversion.rb +48 -0
- data/lib/lutaml/xml/serialization/instance_methods.rb +13 -0
- data/lib/lutaml/xml/transformation/element_builder.rb +21 -8
- data/lib/lutaml/xml/transformation/ordered_applier.rb +6 -0
- data/lib/lutaml/xml/xsd_validator.rb +66 -0
- data/lib/lutaml/xml.rb +53 -12
- data/lutaml-model.gemspec +4 -2
- data/spec/fixtures/xml/schema/rnc/address_book.rnc +15 -0
- data/spec/fixtures/xml/schema/rnc/book_features.rnc +18 -0
- data/spec/fixtures/xml/schema/rnc/includes/book.rnc +6 -0
- data/spec/fixtures/xml/schema/rnc/includes/circular_a.rnc +8 -0
- data/spec/fixtures/xml/schema/rnc/includes/circular_b.rnc +8 -0
- data/spec/fixtures/xml/schema/rnc/includes/library.rnc +8 -0
- data/spec/fixtures/xml/schema/rng/address_book.rng +16 -0
- data/spec/fixtures/xml/schema/rng/book.rng +27 -0
- data/spec/fixtures/xml/schema/rng/fixed_value.rng +11 -0
- data/spec/fixtures/xml/schema/rng/fragment_in_choice.rng +30 -0
- data/spec/fixtures/xml/schema/rng/full_name.rng +39 -0
- data/spec/fixtures/xml/schema/rng/integer_range.rng +32 -0
- data/spec/fixtures/xml/schema/rng/list_type.rng +12 -0
- data/spec/fixtures/xml/schema/rng/namespaced.rng +9 -0
- data/spec/fixtures/xml/schema/rng/paragraph.rng +13 -0
- data/spec/fixtures/xml/schema/rng/person.rng +23 -0
- data/spec/fixtures/xml/schema/rng/union.rng +14 -0
- data/spec/fixtures/xml/validate_xml_with_address.xsd +13 -0
- data/spec/fixtures/xml/validate_xml_with_contact.xsd +11 -0
- data/spec/fixtures/xml/validate_xml_with_person.xsd +11 -0
- data/spec/fixtures/xml/validate_xml_with_person_strict.xsd +17 -0
- data/spec/fixtures/xml/validate_xml_with_product.xsd +37 -0
- data/spec/lutaml/model/attribute_apply_value_map_spec.rb +134 -0
- data/spec/lutaml/model/attribute_spec.rb +169 -12
- data/spec/lutaml/model/boot_manifest_spec.rb +30 -0
- data/spec/lutaml/model/collection_spec.rb +18 -0
- data/spec/lutaml/model/mixed_content_spec.rb +171 -0
- data/spec/lutaml/model/opal_smoke_spec.rb +67 -2
- data/spec/lutaml/model/ordered_content_spec.rb +30 -0
- data/spec/lutaml/model/raw_element_spec.rb +125 -0
- data/spec/lutaml/model/rule_value_extractor_spec.rb +7 -14
- data/spec/lutaml/model/runtime_compatibility_spec.rb +25 -0
- data/spec/lutaml/model/schema/renderers/model_spec.rb +149 -0
- data/spec/lutaml/model/schema/renderers/namespace_spec.rb +36 -0
- data/spec/lutaml/model/schema/renderers/restricted_type_spec.rb +75 -0
- data/spec/lutaml/model/schema/renderers/union_spec.rb +58 -0
- data/spec/lutaml/model/transform_apply_value_map_spec.rb +64 -0
- data/spec/lutaml/model/union_attribute_spec.rb +658 -0
- data/spec/lutaml/model/union_spec.rb +257 -0
- data/spec/lutaml/model/utils_spec.rb +14 -0
- data/spec/lutaml/xml/opal_xml_spec.rb +22 -20
- data/spec/lutaml/xml/schema/compiler_spec.rb +21 -4
- data/spec/lutaml/xml/schema/rnc_compiler_spec.rb +404 -0
- data/spec/lutaml/xml/schema/rng_compiler_spec.rb +893 -0
- data/spec/lutaml/xml/validate_xml_with_constructs_spec.rb +222 -0
- data/spec/lutaml/xml/validate_xml_with_spec.rb +186 -0
- data/spec/spec_helper.rb +28 -11
- data/spec/support/opal.rb +5 -2
- metadata +97 -31
- data/lib/lutaml/model/schema/xml_compiler/attribute.rb +0 -106
- data/lib/lutaml/model/schema/xml_compiler/attribute_group.rb +0 -47
- data/lib/lutaml/model/schema/xml_compiler/choice.rb +0 -67
- data/lib/lutaml/model/schema/xml_compiler/complex_content.rb +0 -27
- data/lib/lutaml/model/schema/xml_compiler/complex_content_restriction.rb +0 -34
- data/lib/lutaml/model/schema/xml_compiler/complex_type.rb +0 -173
- data/lib/lutaml/model/schema/xml_compiler/element.rb +0 -121
- data/lib/lutaml/model/schema/xml_compiler/group.rb +0 -113
- data/lib/lutaml/model/schema/xml_compiler/restriction.rb +0 -104
- data/lib/lutaml/model/schema/xml_compiler/sequence.rb +0 -52
- data/lib/lutaml/model/schema/xml_compiler/simple_content.rb +0 -40
- data/lib/lutaml/model/schema/xml_compiler/simple_type.rb +0 -265
- data/lib/lutaml/model/schema/xml_compiler/xml_namespace_class.rb +0 -110
- data/lib/lutaml/model/services/default_value_resolver.rb +0 -60
- data/spec/lutaml/model/services/default_value_resolver_spec.rb +0 -162
- data/spec/lutaml/xml/schema/compiler/attribute_group_spec.rb +0 -71
- data/spec/lutaml/xml/schema/compiler/attribute_spec.rb +0 -67
- data/spec/lutaml/xml/schema/compiler/choice_spec.rb +0 -74
- data/spec/lutaml/xml/schema/compiler/complex_content_restriction_spec.rb +0 -60
- data/spec/lutaml/xml/schema/compiler/complex_content_spec.rb +0 -41
- data/spec/lutaml/xml/schema/compiler/complex_type_spec.rb +0 -202
- data/spec/lutaml/xml/schema/compiler/element_spec.rb +0 -68
- data/spec/lutaml/xml/schema/compiler/group_spec.rb +0 -90
- data/spec/lutaml/xml/schema/compiler/restriction_spec.rb +0 -77
- data/spec/lutaml/xml/schema/compiler/sequence_spec.rb +0 -65
- data/spec/lutaml/xml/schema/compiler/simple_content_spec.rb +0 -61
- data/spec/lutaml/xml/schema/compiler/simple_type_spec.rb +0 -184
|
@@ -1,173 +0,0 @@
|
|
|
1
|
-
module Lutaml
|
|
2
|
-
module Model
|
|
3
|
-
module Schema
|
|
4
|
-
module XmlCompiler
|
|
5
|
-
class ComplexType
|
|
6
|
-
attr_accessor :id,
|
|
7
|
-
:name,
|
|
8
|
-
:mixed,
|
|
9
|
-
:instances,
|
|
10
|
-
:base_class,
|
|
11
|
-
:simple_content
|
|
12
|
-
|
|
13
|
-
SERIALIZABLE_BASE_CLASS = "Lutaml::Model::Serializable".freeze
|
|
14
|
-
|
|
15
|
-
SIMPLE_CONTENT_ATTRIBUTE_TEMPLATE = ERB.new(<<~TEMPLATE, trim_mode: "-")
|
|
16
|
-
<%= @indent %>attribute :content, :<%= simple_content_type %><%= ", collection: true" if mixed && !simple_content? %>
|
|
17
|
-
<%= simple_content.to_attributes(@indent) if simple_content? -%>
|
|
18
|
-
TEMPLATE
|
|
19
|
-
|
|
20
|
-
TEMPLATE = ERB.new(<<~TEMPLATE, trim_mode: "-")
|
|
21
|
-
# frozen_string_literal: true
|
|
22
|
-
|
|
23
|
-
require "lutaml/model"
|
|
24
|
-
<%= required_files.uniq.join("\n") + "\n" -%>
|
|
25
|
-
<%= module_opening -%>
|
|
26
|
-
class <%= Utils.camel_case(name) %> < <%= base_class_name %>
|
|
27
|
-
<%= instances.flat_map { |instance| instance.to_attributes(@indent) }.join + "\n" -%>
|
|
28
|
-
<%= simple_content_attribute -%>
|
|
29
|
-
<%= @indent %>xml do
|
|
30
|
-
<%= extended_indent %>element "<%= name %>"
|
|
31
|
-
<%= extended_indent %><%= mixed_content? %>
|
|
32
|
-
<%= namespace_and_prefix %>
|
|
33
|
-
<%= "\#{extended_indent}map_content to: :content" if simple_content? || mixed %>
|
|
34
|
-
<%= instances.flat_map { |instance| instance.to_xml_mapping(extended_indent) }.join -%>
|
|
35
|
-
<%= simple_content.to_xml_mapping(extended_indent) if simple_content? -%>
|
|
36
|
-
<%= @indent %>end
|
|
37
|
-
<%= registration_methods -%>
|
|
38
|
-
end
|
|
39
|
-
<%= module_closing -%>
|
|
40
|
-
<%= registration_execution -%>
|
|
41
|
-
TEMPLATE
|
|
42
|
-
|
|
43
|
-
def initialize(base_class: SERIALIZABLE_BASE_CLASS)
|
|
44
|
-
@base_class = base_class
|
|
45
|
-
@instances = []
|
|
46
|
-
@module_namespace = nil
|
|
47
|
-
end
|
|
48
|
-
|
|
49
|
-
def <<(instance)
|
|
50
|
-
return if instance.nil?
|
|
51
|
-
|
|
52
|
-
@instances << instance
|
|
53
|
-
end
|
|
54
|
-
|
|
55
|
-
def simple_content?
|
|
56
|
-
Utils.present?(@simple_content)
|
|
57
|
-
end
|
|
58
|
-
|
|
59
|
-
def to_class(options: {})
|
|
60
|
-
setup_options(options)
|
|
61
|
-
TEMPLATE.result(binding)
|
|
62
|
-
end
|
|
63
|
-
|
|
64
|
-
def required_files
|
|
65
|
-
files = []
|
|
66
|
-
# Only include external gem requires, not schema class requires
|
|
67
|
-
# Schema class dependencies are handled via autoload registry
|
|
68
|
-
unless @module_namespace
|
|
69
|
-
files.concat(@instances.map(&:required_files).flatten.compact.uniq)
|
|
70
|
-
files.concat(simple_content.required_files) if simple_content?
|
|
71
|
-
end
|
|
72
|
-
files
|
|
73
|
-
end
|
|
74
|
-
|
|
75
|
-
private
|
|
76
|
-
|
|
77
|
-
def setup_options(options)
|
|
78
|
-
namespace_uri = options[:namespace]
|
|
79
|
-
@prefix = options[:prefix]
|
|
80
|
-
@indent = " " * options&.fetch(:indent, 2)
|
|
81
|
-
@extended_indent = @indent * 2
|
|
82
|
-
@module_namespace = options[:module_namespace]
|
|
83
|
-
@modules = @module_namespace&.split("::") || []
|
|
84
|
-
@register_id = options[:register_id]
|
|
85
|
-
|
|
86
|
-
# Get the namespace class name if namespace URI is provided
|
|
87
|
-
if namespace_uri && XmlCompiler.namespace_classes
|
|
88
|
-
ns_class = XmlCompiler.namespace_classes.values.find do |ns|
|
|
89
|
-
ns.uri == namespace_uri
|
|
90
|
-
end
|
|
91
|
-
@namespace_class_name = ns_class&.class_name
|
|
92
|
-
end
|
|
93
|
-
end
|
|
94
|
-
|
|
95
|
-
def module_opening
|
|
96
|
-
return "" if @modules.empty?
|
|
97
|
-
|
|
98
|
-
@modules.map.with_index do |mod, i|
|
|
99
|
-
"#{' ' * i}module #{mod}"
|
|
100
|
-
end.join("\n") + "\n"
|
|
101
|
-
end
|
|
102
|
-
|
|
103
|
-
def module_closing
|
|
104
|
-
return "" if @modules.empty?
|
|
105
|
-
|
|
106
|
-
@modules.reverse.map.with_index do |_mod, i|
|
|
107
|
-
"#{' ' * (@modules.size - i - 1)}end"
|
|
108
|
-
end.join("\n")
|
|
109
|
-
end
|
|
110
|
-
|
|
111
|
-
def registration_methods
|
|
112
|
-
return "" if @module_namespace
|
|
113
|
-
|
|
114
|
-
<<~REGISTRATION
|
|
115
|
-
|
|
116
|
-
#{@indent}def self.register
|
|
117
|
-
#{extended_indent}Lutaml::Model::Config.default_register
|
|
118
|
-
#{@indent}end
|
|
119
|
-
|
|
120
|
-
#{@indent}def self.register_class_with_id
|
|
121
|
-
#{extended_indent}context = Lutaml::Model::GlobalContext.context(Lutaml::Model::Config.default_register)
|
|
122
|
-
#{extended_indent}context.registry.register(:#{Utils.snake_case(name)}, self)
|
|
123
|
-
#{@indent}end
|
|
124
|
-
REGISTRATION
|
|
125
|
-
end
|
|
126
|
-
|
|
127
|
-
def registration_execution
|
|
128
|
-
return "" if @module_namespace
|
|
129
|
-
|
|
130
|
-
"\n#{Utils.camel_case(name)}.register_class_with_id"
|
|
131
|
-
end
|
|
132
|
-
|
|
133
|
-
def simple_content_type
|
|
134
|
-
return "string" unless simple_content?
|
|
135
|
-
|
|
136
|
-
Utils.snake_case(last_of_split(simple_content.base_class))
|
|
137
|
-
end
|
|
138
|
-
|
|
139
|
-
def simple_content_attribute
|
|
140
|
-
SIMPLE_CONTENT_ATTRIBUTE_TEMPLATE.result(binding) if simple_content? || mixed
|
|
141
|
-
end
|
|
142
|
-
|
|
143
|
-
def mixed_content?
|
|
144
|
-
mixed ? "mixed_content" : ""
|
|
145
|
-
end
|
|
146
|
-
|
|
147
|
-
def namespace_and_prefix
|
|
148
|
-
return "" unless @namespace_class_name
|
|
149
|
-
|
|
150
|
-
"#{@extended_indent}namespace #{@namespace_class_name}"
|
|
151
|
-
end
|
|
152
|
-
|
|
153
|
-
def extended_indent
|
|
154
|
-
@extended_indent
|
|
155
|
-
end
|
|
156
|
-
|
|
157
|
-
def base_class_name
|
|
158
|
-
case base_class
|
|
159
|
-
when SERIALIZABLE_BASE_CLASS
|
|
160
|
-
SERIALIZABLE_BASE_CLASS
|
|
161
|
-
else
|
|
162
|
-
Utils.camel_case(last_of_split(base_class))
|
|
163
|
-
end
|
|
164
|
-
end
|
|
165
|
-
|
|
166
|
-
def last_of_split(field)
|
|
167
|
-
field&.split(":")&.last
|
|
168
|
-
end
|
|
169
|
-
end
|
|
170
|
-
end
|
|
171
|
-
end
|
|
172
|
-
end
|
|
173
|
-
end
|
|
@@ -1,121 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
module Lutaml
|
|
4
|
-
module Model
|
|
5
|
-
module Schema
|
|
6
|
-
module XmlCompiler
|
|
7
|
-
class Element
|
|
8
|
-
attr_accessor :id,
|
|
9
|
-
:ref,
|
|
10
|
-
:name,
|
|
11
|
-
:type,
|
|
12
|
-
:fixed,
|
|
13
|
-
:default,
|
|
14
|
-
:max_occurs,
|
|
15
|
-
:min_occurs
|
|
16
|
-
|
|
17
|
-
def initialize(name: nil, ref: nil)
|
|
18
|
-
@name = name
|
|
19
|
-
@ref = ref
|
|
20
|
-
end
|
|
21
|
-
|
|
22
|
-
def to_attributes(indent)
|
|
23
|
-
return if skippable?
|
|
24
|
-
return unless resolved_type
|
|
25
|
-
|
|
26
|
-
"#{indent}attribute :#{resolved_name}, :#{resolved_type}#{attribute_options}\n"
|
|
27
|
-
end
|
|
28
|
-
|
|
29
|
-
def to_xml_mapping(indent)
|
|
30
|
-
return if skippable?
|
|
31
|
-
return unless resolved_type
|
|
32
|
-
|
|
33
|
-
"#{indent}map_element :#{resolved_name(change_case: false)}, to: :#{resolved_name}#{render_options}\n"
|
|
34
|
-
end
|
|
35
|
-
|
|
36
|
-
def required_files
|
|
37
|
-
return if skippable?
|
|
38
|
-
|
|
39
|
-
element_type = resolved_type(change_case: false)
|
|
40
|
-
return "require \"bigdecimal\"" if element_type == "decimal"
|
|
41
|
-
return if SimpleType.skippable?(element_type)
|
|
42
|
-
|
|
43
|
-
"require_relative \"#{Utils.snake_case(element_type)}\""
|
|
44
|
-
end
|
|
45
|
-
|
|
46
|
-
private
|
|
47
|
-
|
|
48
|
-
def resolved_instance
|
|
49
|
-
@resolved_instance ||= XmlCompiler.instance_variable_get(:@elements)[last_of_split]
|
|
50
|
-
end
|
|
51
|
-
|
|
52
|
-
def resolved_type(change_case: true)
|
|
53
|
-
@current_type ||= type || resolved_instance&.type
|
|
54
|
-
klass_name = last_of_split(@current_type)
|
|
55
|
-
change_case ? Utils.snake_case(klass_name) : klass_name
|
|
56
|
-
end
|
|
57
|
-
|
|
58
|
-
def resolved_name(change_case: true)
|
|
59
|
-
@current_name ||= name || resolved_instance&.name
|
|
60
|
-
change_case ? Utils.snake_case(@current_name) : @current_name
|
|
61
|
-
end
|
|
62
|
-
|
|
63
|
-
def collection_option
|
|
64
|
-
return if min_occurs.nil? && max_occurs.nil?
|
|
65
|
-
|
|
66
|
-
min_value = min_occurs.nil? ? 1 : min_occurs.to_i
|
|
67
|
-
", collection: #{min_value}..#{max_value}"
|
|
68
|
-
end
|
|
69
|
-
|
|
70
|
-
def max_value
|
|
71
|
-
return "Float::INFINITY" if max_occurs == "unbounded"
|
|
72
|
-
return 1 if max_occurs.nil?
|
|
73
|
-
|
|
74
|
-
max_occurs.to_i
|
|
75
|
-
end
|
|
76
|
-
|
|
77
|
-
def default_option
|
|
78
|
-
return if default.nil?
|
|
79
|
-
|
|
80
|
-
", default: -> { #{default.inspect} }"
|
|
81
|
-
end
|
|
82
|
-
|
|
83
|
-
def render_default_option
|
|
84
|
-
return if default.nil?
|
|
85
|
-
|
|
86
|
-
", render_default: true"
|
|
87
|
-
end
|
|
88
|
-
|
|
89
|
-
def render_options
|
|
90
|
-
options = []
|
|
91
|
-
options << render_default_option if default
|
|
92
|
-
options << render_empty_option if required?
|
|
93
|
-
options.compact.join
|
|
94
|
-
end
|
|
95
|
-
|
|
96
|
-
def render_empty_option
|
|
97
|
-
", render_empty: true"
|
|
98
|
-
end
|
|
99
|
-
|
|
100
|
-
def required?
|
|
101
|
-
# Element is required if minOccurs is >= 1 OR minOccurs is nil (schema default is 1)
|
|
102
|
-
# Only NOT required if minOccurs is explicitly 0
|
|
103
|
-
min_occurs.nil? || min_occurs.to_i >= 1
|
|
104
|
-
end
|
|
105
|
-
|
|
106
|
-
def attribute_options
|
|
107
|
-
[collection_option, default_option].compact.join
|
|
108
|
-
end
|
|
109
|
-
|
|
110
|
-
def last_of_split(field = ref)
|
|
111
|
-
field&.split(":")&.last
|
|
112
|
-
end
|
|
113
|
-
|
|
114
|
-
def skippable?
|
|
115
|
-
resolved_name == "schema_location"
|
|
116
|
-
end
|
|
117
|
-
end
|
|
118
|
-
end
|
|
119
|
-
end
|
|
120
|
-
end
|
|
121
|
-
end
|
|
@@ -1,113 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
module Lutaml
|
|
4
|
-
module Model
|
|
5
|
-
module Schema
|
|
6
|
-
module XmlCompiler
|
|
7
|
-
class Group
|
|
8
|
-
attr_accessor :name, :ref, :instance
|
|
9
|
-
|
|
10
|
-
GROUP_TEMPLATE = ERB.new(<<~TEMPLATE, trim_mode: "-")
|
|
11
|
-
# frozen_string_literal: true
|
|
12
|
-
|
|
13
|
-
require "lutaml/model"
|
|
14
|
-
<%= "\n" + required_files.uniq.join("\n") -%>
|
|
15
|
-
|
|
16
|
-
class <%= Utils.camel_case(base_name) %> < Lutaml::Model::Serializable
|
|
17
|
-
<%= definitions_content %>
|
|
18
|
-
<%= xml_mapping_block -%>
|
|
19
|
-
|
|
20
|
-
<%= @indent %>def self.register
|
|
21
|
-
<%= extended_indent %>@register ||= Lutaml::Model::Config.default_register
|
|
22
|
-
<%= @indent %>end
|
|
23
|
-
|
|
24
|
-
<%= @indent %>def self.register_class_with_id
|
|
25
|
-
<%= extended_indent %>context = Lutaml::Model::GlobalContext.context(Lutaml::Model::Config.default_register)
|
|
26
|
-
<%= extended_indent %>context.registry.register(:<%= Utils.snake_case(base_name) %>, self)
|
|
27
|
-
<%= @indent %>end
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
<%= Utils.camel_case(base_name) %>.register_class_with_id
|
|
31
|
-
TEMPLATE
|
|
32
|
-
|
|
33
|
-
XML_MAPPING_TEMPLATE = ERB.new(<<~TEMPLATE, trim_mode: "-")
|
|
34
|
-
<%= @indent %>xml do
|
|
35
|
-
<%= extended_indent %>type_name "<%= base_name %>"
|
|
36
|
-
<%= xml_mapping_content -%>
|
|
37
|
-
<%= @indent %>end
|
|
38
|
-
TEMPLATE
|
|
39
|
-
|
|
40
|
-
def initialize(name = nil, ref = nil)
|
|
41
|
-
@name = name
|
|
42
|
-
@ref = ref
|
|
43
|
-
end
|
|
44
|
-
|
|
45
|
-
def to_xml_mapping(indent = @indent)
|
|
46
|
-
if Utils.present?(@ref)
|
|
47
|
-
"#{indent}import_model_mappings :#{Utils.snake_case(base_name)}\n"
|
|
48
|
-
else
|
|
49
|
-
@instance.to_xml_mapping(indent * 2)
|
|
50
|
-
end
|
|
51
|
-
end
|
|
52
|
-
|
|
53
|
-
def to_class(options: {})
|
|
54
|
-
setup_options(options)
|
|
55
|
-
GROUP_TEMPLATE.result(binding)
|
|
56
|
-
end
|
|
57
|
-
|
|
58
|
-
def required_files
|
|
59
|
-
if Utils.blank?(name) && Utils.present?(ref)
|
|
60
|
-
"require_relative \"#{Utils.snake_case(ref.split(':').last)}\""
|
|
61
|
-
else
|
|
62
|
-
@instance&.required_files
|
|
63
|
-
end
|
|
64
|
-
end
|
|
65
|
-
|
|
66
|
-
def to_attributes(indent = @indent)
|
|
67
|
-
if Utils.present?(@ref)
|
|
68
|
-
"#{indent}import_model_attributes :#{Utils.snake_case(base_name)}\n"
|
|
69
|
-
else
|
|
70
|
-
@instance.to_attributes(indent)
|
|
71
|
-
end
|
|
72
|
-
end
|
|
73
|
-
|
|
74
|
-
def base_name
|
|
75
|
-
(name || ref)&.split(":")&.last
|
|
76
|
-
end
|
|
77
|
-
|
|
78
|
-
private
|
|
79
|
-
|
|
80
|
-
def setup_options(options)
|
|
81
|
-
@indent = " " * options&.fetch(:indent, 2)
|
|
82
|
-
end
|
|
83
|
-
|
|
84
|
-
def definitions_content
|
|
85
|
-
@definitions_content ||= instance.to_attributes(@indent)
|
|
86
|
-
end
|
|
87
|
-
|
|
88
|
-
def extended_indent
|
|
89
|
-
@indent * 2
|
|
90
|
-
end
|
|
91
|
-
|
|
92
|
-
def xml_mapping_block
|
|
93
|
-
XML_MAPPING_TEMPLATE.result(binding)
|
|
94
|
-
end
|
|
95
|
-
|
|
96
|
-
# Generate XML mapping content, unwrapping sequence for importable groups
|
|
97
|
-
def xml_mapping_content
|
|
98
|
-
return "" unless instance
|
|
99
|
-
|
|
100
|
-
# For Groups (importable models without root), unwrap sequence content
|
|
101
|
-
# because sequence requires a root element
|
|
102
|
-
if instance.is_a?(Sequence)
|
|
103
|
-
# Output sequence content directly without the wrapper
|
|
104
|
-
instance.xml_block_content(extended_indent)
|
|
105
|
-
else
|
|
106
|
-
instance.to_xml_mapping(extended_indent)
|
|
107
|
-
end
|
|
108
|
-
end
|
|
109
|
-
end
|
|
110
|
-
end
|
|
111
|
-
end
|
|
112
|
-
end
|
|
113
|
-
end
|
|
@@ -1,104 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
module Lutaml
|
|
4
|
-
module Model
|
|
5
|
-
module Schema
|
|
6
|
-
module XmlCompiler
|
|
7
|
-
class Restriction
|
|
8
|
-
# transform is not a 'xsd' type, but it is used for internal purposes.
|
|
9
|
-
attr_accessor :min_inclusive,
|
|
10
|
-
:max_inclusive,
|
|
11
|
-
:min_exclusive,
|
|
12
|
-
:max_exclusive,
|
|
13
|
-
:enumerations,
|
|
14
|
-
:max_length,
|
|
15
|
-
:min_length,
|
|
16
|
-
:base_class,
|
|
17
|
-
:pattern,
|
|
18
|
-
:length,
|
|
19
|
-
:transform
|
|
20
|
-
|
|
21
|
-
MIN_MAX_BOUNDS = ERB.new(<<~TEMPLATE, trim_mode: "-")
|
|
22
|
-
<%= "\#{indent}options[:max] = \#{max_inclusive || max_exclusive}" if max_bound_exist? %>
|
|
23
|
-
<%= "\#{indent}options[:min] = \#{min_inclusive || min_exclusive}" if min_bound_exist? %>
|
|
24
|
-
TEMPLATE
|
|
25
|
-
|
|
26
|
-
PATTERN = ERB.new(<<~TEMPLATE, trim_mode: "-")
|
|
27
|
-
<%= "\#{indent}options[:pattern] = %r{\#{pattern}}" %>
|
|
28
|
-
TEMPLATE
|
|
29
|
-
|
|
30
|
-
ENUMERATIONS = ERB.new(<<~TEMPLATE, trim_mode: "-")
|
|
31
|
-
<%= "\#{indent}options[:values] = [\#{casted_enumerations}]" %>
|
|
32
|
-
TEMPLATE
|
|
33
|
-
|
|
34
|
-
TRANSFORM = ERB.new(<<~TEMPLATE, trim_mode: "-")
|
|
35
|
-
<%= "\#{indent}value = \#{transform}" %>
|
|
36
|
-
TEMPLATE
|
|
37
|
-
|
|
38
|
-
def to_method_body(indent = nil)
|
|
39
|
-
[
|
|
40
|
-
value_for(ENUMERATIONS, type: :enumerations, indent: indent),
|
|
41
|
-
value_for(MIN_MAX_BOUNDS, type: :min_max_bounds, indent: indent),
|
|
42
|
-
value_for(PATTERN, type: :pattern, indent: indent),
|
|
43
|
-
value_for(TRANSFORM, type: :transform, indent: indent),
|
|
44
|
-
].compact.join
|
|
45
|
-
end
|
|
46
|
-
|
|
47
|
-
def required_files
|
|
48
|
-
if base_class_name == :decimal
|
|
49
|
-
"require \"bigdecimal\""
|
|
50
|
-
elsif !SimpleType::SUPPORTED_DATA_TYPES.dig(base_class_name,
|
|
51
|
-
:skippable)
|
|
52
|
-
"require_relative \"#{Utils.snake_case(base_class_name)}\""
|
|
53
|
-
end
|
|
54
|
-
end
|
|
55
|
-
|
|
56
|
-
private
|
|
57
|
-
|
|
58
|
-
def value_for(constant, type:, indent:)
|
|
59
|
-
return unless send("#{type}_exist?")
|
|
60
|
-
|
|
61
|
-
indent ||= " "
|
|
62
|
-
constant.result(binding)
|
|
63
|
-
end
|
|
64
|
-
|
|
65
|
-
def min_max_bounds_exist?
|
|
66
|
-
min_bound_exist? || max_bound_exist?
|
|
67
|
-
end
|
|
68
|
-
|
|
69
|
-
def min_bound_exist?
|
|
70
|
-
Utils.present?(min_inclusive) || Utils.present?(min_exclusive)
|
|
71
|
-
end
|
|
72
|
-
|
|
73
|
-
def max_bound_exist?
|
|
74
|
-
Utils.present?(max_inclusive) || Utils.present?(max_exclusive)
|
|
75
|
-
end
|
|
76
|
-
|
|
77
|
-
def pattern_exist?
|
|
78
|
-
Utils.present?(pattern)
|
|
79
|
-
end
|
|
80
|
-
|
|
81
|
-
def enumerations_exist?
|
|
82
|
-
Utils.present?(enumerations)
|
|
83
|
-
end
|
|
84
|
-
|
|
85
|
-
def transform_exist?
|
|
86
|
-
Utils.present?(transform)
|
|
87
|
-
end
|
|
88
|
-
|
|
89
|
-
def base_class_name
|
|
90
|
-
return if Utils.blank?(base_class)
|
|
91
|
-
|
|
92
|
-
base_class.split(":").last.to_sym
|
|
93
|
-
end
|
|
94
|
-
|
|
95
|
-
def casted_enumerations
|
|
96
|
-
enumerations.map do |enumeration|
|
|
97
|
-
"super(#{enumeration.inspect})"
|
|
98
|
-
end.join(", ")
|
|
99
|
-
end
|
|
100
|
-
end
|
|
101
|
-
end
|
|
102
|
-
end
|
|
103
|
-
end
|
|
104
|
-
end
|
|
@@ -1,52 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
module Lutaml
|
|
4
|
-
module Model
|
|
5
|
-
module Schema
|
|
6
|
-
module XmlCompiler
|
|
7
|
-
class Sequence
|
|
8
|
-
attr_accessor :instances
|
|
9
|
-
|
|
10
|
-
XML_MAPPING_TEMPLATE = ERB.new(<<~TEMPLATE, trim_mode: "-")
|
|
11
|
-
<%= indent %>sequence do
|
|
12
|
-
<%= content -%>
|
|
13
|
-
<%= indent %>end
|
|
14
|
-
TEMPLATE
|
|
15
|
-
|
|
16
|
-
def initialize
|
|
17
|
-
@instances = []
|
|
18
|
-
end
|
|
19
|
-
|
|
20
|
-
def <<(instance)
|
|
21
|
-
return if instance.nil?
|
|
22
|
-
|
|
23
|
-
@instances << instance
|
|
24
|
-
end
|
|
25
|
-
|
|
26
|
-
def to_attributes(indent)
|
|
27
|
-
instances.filter_map do |instance|
|
|
28
|
-
instance.to_attributes(indent)
|
|
29
|
-
end.join
|
|
30
|
-
end
|
|
31
|
-
|
|
32
|
-
def to_xml_mapping(indent)
|
|
33
|
-
content = xml_block_content(indent)
|
|
34
|
-
return "" if content.empty?
|
|
35
|
-
|
|
36
|
-
XML_MAPPING_TEMPLATE.result(binding)
|
|
37
|
-
end
|
|
38
|
-
|
|
39
|
-
def required_files
|
|
40
|
-
@instances.map(&:required_files)
|
|
41
|
-
end
|
|
42
|
-
|
|
43
|
-
def xml_block_content(indent)
|
|
44
|
-
instances.filter_map do |instance|
|
|
45
|
-
instance.to_xml_mapping(indent * 2)
|
|
46
|
-
end.join
|
|
47
|
-
end
|
|
48
|
-
end
|
|
49
|
-
end
|
|
50
|
-
end
|
|
51
|
-
end
|
|
52
|
-
end
|
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
module Lutaml
|
|
4
|
-
module Model
|
|
5
|
-
module Schema
|
|
6
|
-
module XmlCompiler
|
|
7
|
-
class SimpleContent
|
|
8
|
-
attr_accessor :instances, :base_class
|
|
9
|
-
|
|
10
|
-
def initialize
|
|
11
|
-
@instances = []
|
|
12
|
-
@base_class = nil
|
|
13
|
-
end
|
|
14
|
-
|
|
15
|
-
def <<(instance)
|
|
16
|
-
return if instance.nil?
|
|
17
|
-
|
|
18
|
-
@instances << instance
|
|
19
|
-
end
|
|
20
|
-
|
|
21
|
-
def to_attributes(indent = nil)
|
|
22
|
-
instances.filter_map do |instance|
|
|
23
|
-
instance.to_attributes(indent)
|
|
24
|
-
end.join("\n")
|
|
25
|
-
end
|
|
26
|
-
|
|
27
|
-
def to_xml_mapping(indent = nil)
|
|
28
|
-
instances.filter_map do |instance|
|
|
29
|
-
instance.to_xml_mapping(indent)
|
|
30
|
-
end.join("\n")
|
|
31
|
-
end
|
|
32
|
-
|
|
33
|
-
def required_files
|
|
34
|
-
instances.flat_map(&:required_files).compact.uniq
|
|
35
|
-
end
|
|
36
|
-
end
|
|
37
|
-
end
|
|
38
|
-
end
|
|
39
|
-
end
|
|
40
|
-
end
|