kwalify_to_json_schema 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: dbf127bd97917313787d2e8627ab38a3ef403edbf32bf77af9b1be706525a71e
4
+ data.tar.gz: 2b055ce7452bd80faa88b40c33d11644779f2ada1a2b7b63a0c7a1470fe55a2c
5
+ SHA512:
6
+ metadata.gz: 03533367dd66aed289370d6aa7bfe03578dab440c59498bc030e8e4179d53917577e7064f12bc5e2ca30f32fda464fabf22c47424a70741a209669fef170d357
7
+ data.tar.gz: 00a4daafa64abeebac771e70b8809ad3475a8e97ca4bc8d6dc26a92735e25b2cb9ab573b876d79127e87146b5efd48c60206b11b0ad25edeee71b00493b24c0a
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/ruby
2
+ require "kwalify_to_json_schema"
3
+
4
+ KwalifyToJsonSchema::Cli.start
@@ -0,0 +1,11 @@
1
+ require "json"
2
+ require "yaml"
3
+ require "thor"
4
+ require "coderay"
5
+ require_relative "kwalify_to_json_schema/kwalify_to_json_schema"
6
+ require_relative "kwalify_to_json_schema/serialization"
7
+ require_relative "kwalify_to_json_schema/options"
8
+ require_relative "kwalify_to_json_schema/limitations"
9
+ require_relative "kwalify_to_json_schema/converter"
10
+ require_relative "kwalify_to_json_schema/custom_processing"
11
+ require_relative "kwalify_to_json_schema/cli"
@@ -0,0 +1,108 @@
1
+ module KwalifyToJsonSchema
2
+ class Cli < Thor
3
+ ###############################################################################################################
4
+ CUSTOM_PROCESSING_CODE_DOC = <<~CODE
5
+ class CustomProcessing
6
+ # The method will be called before conversion allowing to customize the input Kwalify schema.
7
+ # The implementation have to return the modified schema.
8
+ # The default implemention don't modify the schema.
9
+ # @param kwalify_schema {Hash}
10
+ # @return modified schema
11
+ def preprocess(kwalify_schema)
12
+ # TODO return modified schema
13
+ end
14
+
15
+ # The method will be called after the conversion allowing to customize the output JSON schema.
16
+ # The implementation have to return the modified schema.
17
+ # The default implemention don't modify the schema.
18
+ # @param json_schema {Hash}
19
+ # @return modified schema
20
+ def postprocess(json_schema)
21
+ # TODO return modified schema
22
+ end
23
+ end
24
+ CODE
25
+
26
+ desc "convert KWALIFY_SCHEMA_FILE, RESULT_FILE",
27
+ "Convert a Kwalify schema file to a JSON schema file. The result file extension will decide the format: .json or .yaml"
28
+ option :issues_to_description,
29
+ :type => :boolean,
30
+ :default => false,
31
+ :desc => "Will append any conversion issue to the schema description"
32
+ option :custom_processing,
33
+ :type => :string,
34
+ :desc => <<~DESC
35
+ Allows to provide a pre/post processing file on handled schemas.
36
+ The given Ruby file have to provide the following class:
37
+ #{CodeRay.scan(CUSTOM_PROCESSING_CODE_DOC, :ruby).encode :terminal}
38
+ DESC
39
+
40
+ def convert(kwalify_schema_file, result_file)
41
+ opts = {
42
+ Options::ISSUES_TO_DESCRIPTION => options[:issues_to_description],
43
+ Options::CUSTOM_PROCESSING => custom_processing(options),
44
+ }
45
+ KwalifyToJsonSchema.convert_file(kwalify_schema_file, result_file, opts)
46
+ end
47
+
48
+ ###############################################################################################################
49
+
50
+ desc "convert_dir KWALIFY_SCHEMA_DIR, RESULT_DIR",
51
+ "Convert all the Kwalify schema from a directory to a JSON schema"
52
+ option :issues_to_description,
53
+ :type => :boolean,
54
+ :default => false,
55
+ :desc => "Will append any conversion issue to the schema description"
56
+ option :format,
57
+ :type => :string,
58
+ :enum => ["json", "yaml"],
59
+ :default => "json",
60
+ :desc => "Select the output file format"
61
+ option :recursive,
62
+ :type => :boolean,
63
+ :default => false,
64
+ :desc => "Process files recursively",
65
+ :long_desc => ""
66
+ option :custom_processing,
67
+ :type => :string,
68
+ :desc => <<~DESC
69
+ Allows to provide a pre/post processing file on handled schemas.
70
+ The given Ruby file have to provide the following class:
71
+ #{CodeRay.scan(CUSTOM_PROCESSING_CODE_DOC, :ruby).encode :terminal}
72
+ DESC
73
+
74
+ def convert_dir(kwalify_schema_dir, result_dir)
75
+ opts = {
76
+ Options::ISSUES_TO_DESCRIPTION => options[:issues_to_description],
77
+ Options::CUSTOM_PROCESSING => custom_processing(options),
78
+ }
79
+
80
+ path = [kwalify_schema_dir, options["recursive"] ? "**" : nil, "*.yaml"].compact
81
+ Dir.glob(File.join(*path)).each { |kwalify_schema_file|
82
+ result_file = File.join(result_dir, File.basename(kwalify_schema_file, File.extname(kwalify_schema_file))) + ".#{options["format"]}"
83
+ KwalifyToJsonSchema.convert_file(kwalify_schema_file, result_file, opts)
84
+ }
85
+ end
86
+
87
+ def self.exit_on_failure?
88
+ false
89
+ end
90
+
91
+ private
92
+
93
+ def custom_processing(options)
94
+ pf = options[:custom_processing]
95
+ custom_processing = nil
96
+ if pf
97
+ require File.expand_path(pf)
98
+ begin
99
+ processing_class = Object.const_get :CustomProcessing
100
+ custom_processing = processing_class.new
101
+ rescue NameError => e
102
+ raise "The 'CustomProcessing' module must be defined in #{pf}"
103
+ end
104
+ end
105
+ custom_processing
106
+ end
107
+ end
108
+ end
@@ -0,0 +1,178 @@
1
+ module KwalifyToJsonSchema
2
+
3
+ # Heart of conversion implementation
4
+ #
5
+ # Example of use:
6
+ #
7
+ # kwalify_schema = YAML.load(File.read("kwalify_schema.yaml"))
8
+ #
9
+ # converter = KwalifyToJsonSchema::Converter.new(options)
10
+ # json_schema = converter.exec(kwalify_schema)
11
+ #
12
+ # File.write("json_schema.json", JSON.pretty_generate(json_schema))
13
+ class Converter
14
+ SCHEMA = "http://json-schema.org/draft-07/schema#"
15
+
16
+ # The options given used to initialized the converter
17
+ attr_reader :options
18
+ # Give the list of issues encontered while converting as array of strings.
19
+ attr_reader :issues
20
+
21
+ # Converter options:
22
+ # | Name | Type | Default value| Description |
23
+ # |-----------------------|--------|--------------|-----------------------------------------------------|
24
+ # | :id | String | nil | The JSON schema identifier |
25
+ # | :title | String | nil | The JSON schema title |
26
+ # | :description | String | nil | The JSON schema description |
27
+ # | :issues_to_description| Boolean| false | To append the issuses to the JSON schema description|
28
+ # | :custom_processing | Object | nil | To customize the conversion |
29
+ # --
30
+ def initialize(options_hash = {})
31
+ @options = Options.new(options_hash)
32
+ @issues = []
33
+ end
34
+
35
+ # Execute the conversion process
36
+ # @param kwalify_schema Kwalify schema as Hash or YAML string to be converted as Hash
37
+ # @return JSON schema as Hash
38
+ def exec(kwalify_schema)
39
+ kwalify_schema = YAML.load(kwalify_schema) if kwalify_schema.is_a? String
40
+ kwalify_schema = preprocess(kwalify_schema.dup)
41
+
42
+ json_schema = process(root, kwalify_schema)
43
+ if issues.any? && options.issues_to_description?
44
+ description = json_schema["description"] ||= ""
45
+ description << "Issues when converting from Kwalify:\n"
46
+ description << issues.map { |issue| "* #{issue}" }.join("\n")
47
+ end
48
+
49
+ postprocess(json_schema)
50
+ end
51
+
52
+ private
53
+
54
+ def root
55
+ {
56
+ "$schema" => SCHEMA,
57
+ "$id" => options.id,
58
+ "title" => options.title,
59
+ "description" => options.description,
60
+ }.reject { |k, v| v.nil? }
61
+ end
62
+
63
+ # @param target Json schema target
64
+ # @param kelem Kwalify element
65
+ def process(target, kelem)
66
+
67
+ # Add description if available
68
+ target["description"] = kelem["desc"] if kelem["desc"]
69
+
70
+ case ktype = kelem["type"]
71
+ when "map"
72
+ target["type"] = "object"
73
+ target["additionalProperties"] = false
74
+ mapping = kelem["mapping"]
75
+ required = []
76
+ if mapping.is_a? Hash
77
+ properties = target["properties"] = {}
78
+ mapping.each_pair { |name, e|
79
+ process(properties[name] = {}, e)
80
+ required << name if e["required"] == true
81
+ }
82
+ target["required"] = required unless required.empty?
83
+ end
84
+ when "seq"
85
+ target["type"] = "array"
86
+ sequence = kelem["sequence"]
87
+ if sequence.is_a? Array
88
+ process(target["items"] = {}, sequence.first)
89
+ end
90
+ when "str"
91
+ target["type"] = "string"
92
+ when "int"
93
+ target["type"] = "integer"
94
+ when "float", "number"
95
+ target["type"] = "number"
96
+ when "text"
97
+ # Use one of
98
+ target["oneOf"] = [
99
+ { "type" => "string" },
100
+ { "type" => "number" },
101
+ ]
102
+ when "bool"
103
+ target["type"] = "boolean"
104
+ when "date"
105
+ # TODO
106
+ new_issue Limitations::DATE_TYPE_NOT_IMPLEMENTED
107
+ when "time"
108
+ # TODO
109
+ new_issue Limitations::TIME_TYPE_NOT_IMPLEMENTED
110
+ when "timestamp"
111
+ # TODO
112
+ new_issue Limitations::TIMESTAMP_TYPE_NOT_IMPLEMENTED
113
+ when "scalar"
114
+ # Use one of
115
+ target["oneOf"] = [
116
+ { "type" => "string" },
117
+ { "type" => "number" },
118
+ { "type" => "integer" },
119
+ { "type" => "boolean" },
120
+ ]
121
+ when "any"
122
+ # Don't put type
123
+ else
124
+ new_issue("Unknown Kwalify type #{ktype}")
125
+ end
126
+
127
+ target["enum"] = kelem["enum"] if kelem["enum"]
128
+ if range = kelem["range"]
129
+ target["minimum"] = range["min"] if range["min"]
130
+ target["maximum"] = range["max"] if range["max"]
131
+ if range["min-ex"]
132
+ target["minimum"] = range["min-ex"]
133
+ target["exclusiveMinimum"] = true
134
+ end
135
+ if range["max-ex"]
136
+ target["maximum"] = range["max-ex"]
137
+ target["exclusiveMaximum"] = true
138
+ end
139
+ end
140
+ if pa = kelem["pattern"]
141
+ # Remove leading and trailing slash
142
+ target["pattern"] = pa.sub(/^\//, "").sub(/\/$/, "")
143
+ end
144
+
145
+ if length = kelem["length"]
146
+ case ktype
147
+ when "str", "text"
148
+ target["minLength"] = length["min"] if length["min"]
149
+ target["maxLength"] = length["max"] if length["max"]
150
+ target["minLength"] = length["min-ex"] + 1 if length["min-ex"]
151
+ target["maxLength"] = length["max-ex"] + -1 if length["max-ex"]
152
+ end
153
+ end
154
+
155
+ new_issue "'unique' is not supported by JSON Schema" if kelem["unique"]
156
+
157
+ target
158
+ end
159
+
160
+ def preprocess(kwalify_schema)
161
+ ep = options.custom_processing
162
+ return kwalify_schema unless ep.respond_to? :preprocess
163
+ kwalify_schema = ep.preprocess(kwalify_schema.dup)
164
+ end
165
+
166
+ def postprocess(json_schema)
167
+ ep = options.custom_processing
168
+ return json_schema unless ep.respond_to? :postprocess
169
+ ep.postprocess(json_schema)
170
+ end
171
+
172
+ def new_issue(description)
173
+ @issues << description
174
+ end
175
+ end
176
+
177
+
178
+ end
@@ -0,0 +1,14 @@
1
+ module KwalifyToJsonSchema
2
+ # Template class for custom processing
3
+ class CustomProcessing
4
+ # The method will be called before conversion allowing to customize the input Kwalify schema.
5
+ # The implementation have to return the modified schema.
6
+ # The default implemention don't modify the schema.
7
+ def preproces(kwalify_schema); kwalify_schema; end
8
+
9
+ # The method will be called after the conversion allowing to customize the output JSON schema.
10
+ # The implementation have to return the modified schema.
11
+ # The default implemention don't modify the schema.
12
+ def postprocess(json_schema); json_schema; end
13
+ end
14
+ end
@@ -0,0 +1,51 @@
1
+ module KwalifyToJsonSchema
2
+
3
+ # Convert a Kwalify schema file to JSON .schema.
4
+ # The destination file can be JSON or YAML.
5
+ # The file extension is used to select the format: .json or .yaml.
6
+ # Other extension will fallback to JSON.
7
+ # Converter options:
8
+ # | Name | Type | Default value| Description |
9
+ # |-----------------------|--------|--------------|-----------------------------------------------------|
10
+ # | :id | String | nil | The JSON schema identifier |
11
+ # | :title | String | nil | The JSON schema title |
12
+ # | :description | String | nil | The JSON schema description |
13
+ # | :issues_to_description| Boolean| false | To append the issuses to the JSON schema description|
14
+ # | :custom_processing | Object | nil | To customize the conversion |
15
+ # --
16
+ # @param source Path to Kwalify YAML schema
17
+ # @param dest Path to resulting JSON schema
18
+ def self.convert_file(source, dest, options = {})
19
+ # Get a converter
20
+ converter = Converter.new(options)
21
+ # Convert
22
+ converted = converter.exec(Serialization.deserialize_from_file(source))
23
+ # Serialize
24
+ Serialization.serialize_to_file(dest, converted)
25
+ end
26
+
27
+ # Convert a Kwalify schema string to JSON .schema.
28
+ # The source and destination strings can be JSON or YAML.
29
+ # Other extension will fallback to JSON.
30
+ # Converter options:
31
+ # | Name | Type | Default value| Description |
32
+ # |-----------------------|--------|--------------|-----------------------------------------------------|
33
+ # | :id | String | nil | The JSON schema identifier |
34
+ # | :title | String | nil | The JSON schema title |
35
+ # | :description | String | nil | The JSON schema description |
36
+ # | :issues_to_description| Boolean| false | To append the issuses to the JSON schema description|
37
+ # | :custom_processing | Object | nil | To customize the conversion |
38
+ # --
39
+ # @param kwalify_schema Kwalify schema as YAML or JSON
40
+ # @param source_format format of the source schema
41
+ # @param dest_format format of the destination schema
42
+ # @param options
43
+ def self.convert_string(kwalify_schema, source_format = "yaml", dest_format = "json", options = {})
44
+ # Get a converter
45
+ converter = Converter.new(options)
46
+ # Convert
47
+ converted = converter.exec(Serialization.deserialize_from_string(kwalify_schema, source_format))
48
+ # Serialize
49
+ Serialization.serialize_to_string(converted, dest_format)
50
+ end
51
+ end
@@ -0,0 +1,8 @@
1
+ module KwalifyToJsonSchema
2
+ # Enumeration of known implementation limitation
3
+ module Limitations
4
+ DATE_TYPE_NOT_IMPLEMENTED = "Kwalify 'date' type is not supported and is ignored"
5
+ TIME_TYPE_NOT_IMPLEMENTED = "Kwalify 'time' type is not supported and is ignored"
6
+ TIMESTAMP_TYPE_NOT_IMPLEMENTED = "Kwalify 'timestamp' type is not supported and is ignored"
7
+ end
8
+ end
@@ -0,0 +1,74 @@
1
+ module KwalifyToJsonSchema
2
+ # The possible options for the conversion and the associated accessors
3
+ class Options
4
+ # Converter options:
5
+ # | Name | Type | Default value| Description |
6
+ # |-----------------------|--------|--------------|-----------------------------------------------------|
7
+ # | :id | String | nil | The JSON schema identifier |
8
+ # | :title | String | nil | The JSON schema title |
9
+ # | :description | String | nil | The JSON schema description |
10
+ # | :issues_to_description| Boolean| false | To append the issuses to the JSON schema description|
11
+ # | :custom_processing | Object | nil | To customize the conversion |
12
+ # --
13
+ DECLARATION = %q(
14
+ ID # The JSON schema identifier [String] (nil)
15
+ TITLE # The JSON schema title [String] (nil)
16
+ DESCRIPTION # The JSON schema description [String] (nil)
17
+ ISSUES_TO_DESCRIPTION # To append the issuses to the JSON schema description [Boolean] (false)
18
+ CUSTOM_PROCESSING # To customize the conversion [Object] (nil)
19
+ )
20
+
21
+ # The options as Hash
22
+ attr_reader :options_hash
23
+
24
+ def initialize(options_hash)
25
+ @options_hash = options_hash
26
+ end
27
+
28
+ # Parse options declaration text and give an array of Hash
29
+ def self.parse
30
+ DECLARATION.lines.map { |l|
31
+ next nil if l.strip.empty?
32
+
33
+ # Parse line
34
+ const_name, comment = l.split("#", 2).map(&:strip)
35
+ name = const_name.downcase.to_s
36
+ description = comment.split("[").first.strip
37
+ # Get type and default value
38
+ m = comment.match(/\[(.+)\].*\((.+)\)/)
39
+ type, default_value = m.captures
40
+ default_value = eval(default_value)
41
+
42
+ # Create read accessor
43
+ attr_reader_name = "#{name}#{type == "Boolean" ? "?" : ""}"
44
+
45
+ # Array entry as Hash for the option
46
+ {
47
+ const_name: const_name,
48
+ const_name_full: "#{Options.name}::#{const_name}",
49
+ name: name,
50
+ description: description,
51
+ type: type,
52
+ default_value: default_value,
53
+ attr_reader_name: attr_reader_name,
54
+ }
55
+ }.compact
56
+ end
57
+
58
+ # Setup the constants and methods for the options
59
+ # Example: ID will lead to get ID constant and :id method
60
+ def self.setup
61
+ parse.each { |o|
62
+ # Create constant
63
+ const_set o[:const_name], o[:name]
64
+
65
+ # Create read accessor
66
+ define_method(o[:attr_reader_name]) {
67
+ options_hash[o[:name]] || o[:default_value]
68
+ }
69
+ }
70
+ end
71
+
72
+ setup
73
+ end
74
+ end
@@ -0,0 +1,45 @@
1
+ module KwalifyToJsonSchema
2
+
3
+ # Abstract JSON/YAML serialization/deserialization
4
+ module Serialization
5
+ def self.deserialize_from_file(file)
6
+ serialization_for_file(file).deserialize(File.read(file))
7
+ end
8
+
9
+ def self.serialize_to_file(file, object)
10
+ File.write(file, serialization_for_file(file).serialize(object))
11
+ end
12
+
13
+ def self.deserialize_from_string(string, format = "yaml")
14
+ serialization_for_format(format).deserialize(string)
15
+ end
16
+
17
+ def self.serialize_to_string(object, format = "json")
18
+ serialization_for_format(format).serialize(object)
19
+ end
20
+
21
+ # @return a Hash giving serialization/deserialization module and methods for a given file extension (.json/.yaml)
22
+ def self.serialization_for_file(file)
23
+ serialization_for_format(File.extname(file)[1..-1])
24
+ end
25
+
26
+ # @return a Hash giving serialization/deserialization module and methods for a format (json/yaml)
27
+ def self.serialization_for_format(format)
28
+ serializer = { "json" => Json, "yaml" => Yaml }[format] || Json
29
+ end
30
+
31
+ class Language
32
+ def self.normalize(string); serialize(deserialize(string)); end
33
+ end
34
+
35
+ class Json < Language
36
+ def self.serialize(object); JSON.pretty_generate(object); end
37
+ def self.deserialize(string); JSON.parse(string); end
38
+ end
39
+
40
+ class Yaml < Language
41
+ def self.serialize(object); YAML.dump(object); end
42
+ def self.deserialize(string); YAML.load(string); end
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,14 @@
1
+ # Customization of Kwalify to JSON schema
2
+ class CustomProcessing
3
+ def preprocess(kwalify_schema)
4
+ # Remove and keep the wrapping name
5
+ head = kwalify_schema.first
6
+ @name = head.first
7
+ head.last
8
+ end
9
+
10
+ def postprocess(json_schema)
11
+ # Restore the wrapping name
12
+ { @name => json_schema }
13
+ end
14
+ end
@@ -0,0 +1,75 @@
1
+ require "minitest/autorun"
2
+ require "json-schema"
3
+ require_relative "../lib/kwalify_to_json_schema"
4
+
5
+ module KwalifyToJsonSchema
6
+ class Test < Minitest::Test
7
+ @@debug = false
8
+ @@tmpdir = Dir.mktmpdir
9
+
10
+ [
11
+ { test_group: "conversion", cli_options: [] },
12
+ { test_group: "custom_processing", cli_options: ["--custom-processing", File.join(__dir__, "custom_processing.rb")] },
13
+ ].each { |entry|
14
+ test_group = entry[:test_group]
15
+ cli_options = entry[:cli_options]
16
+
17
+ # Create a test method for every Kwalify schema
18
+ Dir.glob(File.join(__dir__, test_group, "kwalify", "*.yaml")).each { |source|
19
+ test_file_base = File.basename(source, File.extname(source))
20
+ test_name_base = test_file_base.gsub("#", "_")
21
+ expected_formats = %w(json yaml)
22
+
23
+ # Define a method for the test JSON output
24
+ define_method("test_#{test_group}_#{test_name_base}_output".to_sym) {
25
+ formats_done = 0
26
+ expected_formats.map { |expected_format|
27
+ output_file = test_file_base + ".#{expected_format}"
28
+ expected = File.join(File.join(__dir__, test_group, "json_schema", expected_format, output_file))
29
+
30
+ next unless File.exist?(expected)
31
+ formats_done += 1
32
+
33
+ ser = KwalifyToJsonSchema::Serialization::serialization_for_format(expected_format)
34
+ dest = File.join(@@tmpdir, output_file)
35
+
36
+ args = ["convert", source, dest]
37
+ # Add issues to description if filename include "#issues_to_description"
38
+ args << "--issues_to_description" if output_file.include?("#issues_to_description")
39
+ args.concat cli_options
40
+
41
+ # Convert
42
+ # KwalifyToJsonSchema.convert_file(source, dest, options)
43
+ KwalifyToJsonSchema::Cli.start(args)
44
+
45
+ # Validate schema
46
+ validate_json_schema_file(dest)
47
+
48
+ if @@debug
49
+ puts test_name_base
50
+ puts ser.normalize(File.read(dest))
51
+ end
52
+ # Compare to expected result
53
+ assert_equal(
54
+ ser.normalize(File.read(expected)),
55
+ ser.normalize(File.read(dest))
56
+ )
57
+ }
58
+
59
+ skip "None of the expected #{expected_formats.join(", ")} result for test #{test_name_base} was found" if formats_done == 0
60
+ }
61
+ }
62
+ }
63
+
64
+ def validate_json_schema_file(schema_file)
65
+ schema = KwalifyToJsonSchema::Serialization::deserialize_from_file(schema_file)
66
+ validate_json_schema(schema)
67
+ end
68
+
69
+ def validate_json_schema(schema)
70
+ # FIXME draft7 is not available in current json-schema gem
71
+ metaschema = JSON::Validator.validator_for_name("draft4").metaschema
72
+ JSON::Validator.validate!(metaschema, schema)
73
+ end
74
+ end
75
+ end
@@ -0,0 +1,4 @@
1
+ require_relative "../lib/kwalify_to_json_schema"
2
+ require_relative "doc_template"
3
+ require_relative "limitations"
4
+ require_relative "options"
@@ -0,0 +1,13 @@
1
+ require "erb"
2
+
3
+ module DocTemplate
4
+ def self.render(template_file, dest_file)
5
+ template = ERB.new(File.read(template_file), nil, "-")
6
+ File.write(dest_file, template.result(get_binding(template_file)))
7
+ end
8
+
9
+ def self.get_binding(template_file)
10
+ template_dir = File.dirname template_file
11
+ binding
12
+ end
13
+ end
@@ -0,0 +1,19 @@
1
+ require_relative "../lib/kwalify_to_json_schema/limitations"
2
+
3
+ # Gives implementation limitations
4
+ module Limitations
5
+
6
+ # @return list of limitation as array of strings
7
+ def self.list
8
+ KwalifyToJsonSchema::Limitations.constants.map { |cst|
9
+ KwalifyToJsonSchema::Limitations.const_get(cst)
10
+ }
11
+ end
12
+
13
+ # @return limitation as markdown text
14
+ def self.markdown
15
+ list.map { |l|
16
+ "* #{l}"
17
+ }.join("\n")
18
+ end
19
+ end
@@ -0,0 +1,96 @@
1
+ require "yaml"
2
+ require_relative "../lib/kwalify_to_json_schema/options"
3
+
4
+ # Gives implementation limitations
5
+ module Options
6
+
7
+ # @return list of limitation as array of strings
8
+ def self.list
9
+ KwalifyToJsonSchema::Options.parse
10
+ end
11
+
12
+ # @return limitation as markdown text
13
+ def self.ascii_table(formatting = ["%s"] * 4)
14
+ header = ["Name", "Type", "Default value", "Description"]
15
+
16
+ nb_cols = header.length
17
+
18
+ table = [header] +
19
+ [[""] * nb_cols] +
20
+ list.map { |o|
21
+ [
22
+ formatting[0] % o[:name].to_sym.inspect,
23
+ formatting[1] % o[:type],
24
+ formatting[2] % o[:default_value].inspect,
25
+ formatting[3] % o[:description],
26
+ ]
27
+ }
28
+ nb_rows = table.length
29
+
30
+ cols_max_length = (0..nb_cols - 1).map { |c|
31
+ (0..nb_rows - 1).map { |r|
32
+ cell = table[r][c]
33
+ cell.length
34
+ }.max
35
+ }
36
+
37
+ table.map.each_with_index { |row, r|
38
+ row.map.each_with_index { |cell, c|
39
+ max_length = cols_max_length[c]
40
+ if r == 1
41
+ "|-" + cell + ("-" * (max_length - cell.length))
42
+ else
43
+ "| " + cell + (" " * (max_length - cell.length))
44
+ end
45
+ }.join + "|"
46
+ }.join "\n"
47
+ end
48
+
49
+ def self.markdown
50
+ ascii_table [
51
+ "`%s`",
52
+ "`%s`",
53
+ "`%s`",
54
+ "_%s_",
55
+ ]
56
+ end
57
+
58
+ def self.inject_as_code_comment(file)
59
+ new_lines = []
60
+ state = :init
61
+ count = 0
62
+
63
+ options_start = "Converter options:"
64
+ options_stop = "--"
65
+
66
+ File.read(file).each_line { |line|
67
+ if line.strip.start_with? "#"
68
+ content = line.strip[1..-1].strip
69
+ case state
70
+ when :init
71
+ new_lines << line
72
+ if content == options_start
73
+ count += 1
74
+ state = :in_options
75
+ padding = line.index("#")
76
+ new_lines.concat(ascii_table.lines.map { |l| "#{" " * padding}# #{l.chomp}\n" })
77
+ end
78
+ when :in_options
79
+ if content.start_with? options_stop
80
+ new_lines << line
81
+ state = :init
82
+ end
83
+ end
84
+ else
85
+ state = :error unless state == :init
86
+ new_lines << line
87
+ end
88
+ }
89
+
90
+ if state == :error
91
+ puts "Missing '#{options_stop}' delimiter after '#{options_start}' in file://#{file}"
92
+ else
93
+ File.write(file, new_lines.join) if count > 0
94
+ end
95
+ end
96
+ end
metadata ADDED
@@ -0,0 +1,128 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: kwalify_to_json_schema
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Sylvain Gamot
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2020-06-10 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: thor
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '1.0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '1.0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: coderay
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '1.0'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '1.0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: kwalify
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: 0.7.2
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: 0.7.2
55
+ - !ruby/object:Gem::Dependency
56
+ name: json-schema
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: '2.0'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: '2.0'
69
+ - !ruby/object:Gem::Dependency
70
+ name: rake
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - "~>"
74
+ - !ruby/object:Gem::Version
75
+ version: 12.3.0
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - "~>"
81
+ - !ruby/object:Gem::Version
82
+ version: 12.3.0
83
+ description: Allows to convert Kwalify schemas to JSON schemas Draft 7
84
+ email: ''
85
+ executables:
86
+ - kwalify_to_json_schema
87
+ extensions: []
88
+ extra_rdoc_files: []
89
+ files:
90
+ - "/home/sylvain/kwalify_to_json_schema/lib/kwalify_to_json_schema.rb"
91
+ - "/home/sylvain/kwalify_to_json_schema/lib/kwalify_to_json_schema/cli.rb"
92
+ - "/home/sylvain/kwalify_to_json_schema/lib/kwalify_to_json_schema/converter.rb"
93
+ - "/home/sylvain/kwalify_to_json_schema/lib/kwalify_to_json_schema/custom_processing.rb"
94
+ - "/home/sylvain/kwalify_to_json_schema/lib/kwalify_to_json_schema/kwalify_to_json_schema.rb"
95
+ - "/home/sylvain/kwalify_to_json_schema/lib/kwalify_to_json_schema/limitations.rb"
96
+ - "/home/sylvain/kwalify_to_json_schema/lib/kwalify_to_json_schema/options.rb"
97
+ - "/home/sylvain/kwalify_to_json_schema/lib/kwalify_to_json_schema/serialization.rb"
98
+ - "/home/sylvain/kwalify_to_json_schema/test/custom_processing.rb"
99
+ - "/home/sylvain/kwalify_to_json_schema/test/test_kwalify_to_json_schema.rb"
100
+ - "/home/sylvain/kwalify_to_json_schema/tools/all.rb"
101
+ - "/home/sylvain/kwalify_to_json_schema/tools/doc_template.rb"
102
+ - "/home/sylvain/kwalify_to_json_schema/tools/limitations.rb"
103
+ - "/home/sylvain/kwalify_to_json_schema/tools/options.rb"
104
+ - bin/kwalify_to_json_schema
105
+ homepage: https://rubygems.org/gems/kwalify_to_json_schema
106
+ licenses:
107
+ - MIT
108
+ metadata: {}
109
+ post_install_message:
110
+ rdoc_options: []
111
+ require_paths:
112
+ - lib
113
+ required_ruby_version: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - ">="
116
+ - !ruby/object:Gem::Version
117
+ version: '0'
118
+ required_rubygems_version: !ruby/object:Gem::Requirement
119
+ requirements:
120
+ - - ">="
121
+ - !ruby/object:Gem::Version
122
+ version: '0'
123
+ requirements: []
124
+ rubygems_version: 3.1.2
125
+ signing_key:
126
+ specification_version: 4
127
+ summary: Kwalify schemas to JSON schemas conversion
128
+ test_files: []