finitio 0.11.3 → 0.11.4
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/CHANGELOG.md +15 -0
- data/Gemfile.lock +1 -1
- data/lib/finitio/generation/proxy_type.rb +11 -0
- data/lib/finitio/generation.rb +1 -0
- data/lib/finitio/json_schema/hash_based_type.rb +1 -1
- data/lib/finitio/json_schema/proxy_type.rb +4 -5
- data/lib/finitio/support/compilation.rb +0 -4
- data/lib/finitio/support/proxy_resolver.rb +52 -0
- data/lib/finitio/support.rb +1 -0
- data/lib/finitio/syntax.rb +4 -4
- data/lib/finitio/system.rb +5 -16
- data/lib/finitio/type/high_order_type.rb +3 -1
- data/lib/finitio/type/proxy_type.rb +19 -1
- data/lib/finitio/type.rb +4 -2
- data/lib/finitio/version.rb +1 -1
- data/spec/inference/test_inference.rb +1 -1
- data/spec/json_schema/test_recursive_type.rb +2 -12
- data/spec/regression/test_dress_on_recursive_type.rb +53 -0
- data/spec/regression/test_name_of_generic_types.rb +18 -0
- data/spec/syntax/test_compile.rb +19 -1
- metadata +8 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 29fd883abee1e98b436a1c8aa80ee32ffc9740dc
|
4
|
+
data.tar.gz: 9aa135c687855dbdfb6a52e245d21c3488ef0128
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 0af6653c37bc1fdb2e5aeef7f0d43e70f92d967658219b638c58a8039b975460f64ab80339d7d727aed716175cc722614973e387c5720315868bd6b8a6d1fc7c
|
7
|
+
data.tar.gz: ef96c4bd3a7f4910b83acab224940afe7a1885be98eeddf5ce8542c0037d0c702da98e372f55a42638cb7cef3cfbf9394dd8c0d162daace35c6731e86083c061
|
data/CHANGELOG.md
CHANGED
@@ -1,3 +1,18 @@
|
|
1
|
+
# 0.11.4 - 2023/01/06
|
2
|
+
|
3
|
+
* The proxy resolution is fixed and clarified. When compiling
|
4
|
+
a system, all proxies are actually replaced by their actual
|
5
|
+
Type instance. Only recursive types still keep ProxyType
|
6
|
+
instances (as sentinels) ; they are bound to their target
|
7
|
+
type and delete dress and include? to them.
|
8
|
+
|
9
|
+
Given that ProxyType is a sentinel on recursive types, calls
|
10
|
+
to generate_data and to_json_schema are not delegated to the
|
11
|
+
target type, to avoid infinite recursions.
|
12
|
+
|
13
|
+
* Generated names of instantiated high order types are better
|
14
|
+
(e.g. Collection<String>).
|
15
|
+
|
1
16
|
# 0.11.3 - 2023/01/06
|
2
17
|
|
3
18
|
* Fix json_schema generation on unresolved ProxyTypes. We use
|
data/Gemfile.lock
CHANGED
data/lib/finitio/generation.rb
CHANGED
@@ -7,7 +7,7 @@ module Finitio
|
|
7
7
|
}
|
8
8
|
unless heading.empty?
|
9
9
|
base[:properties] = heading.inject({}){|ps,a|
|
10
|
-
|
10
|
+
ps.merge(a.name => a.type.to_json_schema(*args, &bl))
|
11
11
|
}
|
12
12
|
end
|
13
13
|
unless (reqs = heading.select{|a| a.required? }).empty?
|
@@ -2,11 +2,10 @@ module Finitio
|
|
2
2
|
class ProxyType
|
3
3
|
|
4
4
|
def to_json_schema(*args, &bl)
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
end
|
5
|
+
# ProxyType is supposed to be used only for recursive types.
|
6
|
+
# We don't have support for references yet, so let just
|
7
|
+
# generate an object here in the mean time.
|
8
|
+
{ type: "object" }
|
10
9
|
end
|
11
10
|
|
12
11
|
end # module ProxyType
|
@@ -0,0 +1,52 @@
|
|
1
|
+
module Finitio
|
2
|
+
# Part of the compilation schema, this proxy resolver replaces
|
3
|
+
# proxies by their real Type instance.
|
4
|
+
#
|
5
|
+
# Given that Finitio can support recursive types, we do this in
|
6
|
+
# two passes:
|
7
|
+
# 1. Replace proxy types by rewrite (see Type#resolve_proxies)
|
8
|
+
# in a depth first search.
|
9
|
+
# 2. If a loop is found, recreate a late ProxyType, that is then
|
10
|
+
# bound later by mutation.
|
11
|
+
#
|
12
|
+
# So ProxyType may still be present in the type chain, but will
|
13
|
+
# only correspond to recursive types.
|
14
|
+
class ProxyResolver
|
15
|
+
def resolve!(system)
|
16
|
+
@system = system
|
17
|
+
@built = {}
|
18
|
+
@building = {}
|
19
|
+
@late_proxies = []
|
20
|
+
system.types.each_key do |name|
|
21
|
+
fetch(name)
|
22
|
+
end
|
23
|
+
@late_proxies.each do |proxy|
|
24
|
+
proxy.bind!(self)
|
25
|
+
end
|
26
|
+
system.dup(@built)
|
27
|
+
end
|
28
|
+
|
29
|
+
def fetch(name, &bl)
|
30
|
+
@built[name] || build_it(name) || import_it(name, &bl)
|
31
|
+
end
|
32
|
+
|
33
|
+
def build_it(name)
|
34
|
+
if under_build = @building[name]
|
35
|
+
proxy = ProxyType.new(name)
|
36
|
+
@late_proxies << proxy
|
37
|
+
proxy
|
38
|
+
else
|
39
|
+
return nil unless type = @system.fetch(name, false){ nil }
|
40
|
+
|
41
|
+
@building[name] = type
|
42
|
+
@built[name] = type.resolve_proxies(self)
|
43
|
+
@building[name] = nil
|
44
|
+
@built[name]
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
def import_it(name, &bl)
|
49
|
+
@system.fetch_on_imports(name, &bl)
|
50
|
+
end
|
51
|
+
end # class ProxyResolver
|
52
|
+
end # module Finitio
|
data/lib/finitio/support.rb
CHANGED
data/lib/finitio/syntax.rb
CHANGED
@@ -21,18 +21,18 @@ module Finitio
|
|
21
21
|
end
|
22
22
|
|
23
23
|
def self.ast(source)
|
24
|
-
parse(source, root:
|
24
|
+
parse(source, root: 'system').to_ast
|
25
25
|
end
|
26
26
|
|
27
27
|
def self.compile(source, cpl = nil)
|
28
28
|
cpl = Compilation.coerce(cpl, source)
|
29
|
-
parse(source, root:
|
30
|
-
cpl.
|
29
|
+
parse(source, root: 'system').compile(cpl)
|
30
|
+
ProxyResolver.new.resolve!(cpl.system)
|
31
31
|
end
|
32
32
|
|
33
33
|
def self.compile_type(source, cpl = nil)
|
34
34
|
cpl = Compilation.coerce(cpl, source)
|
35
|
-
parse(source, root:
|
35
|
+
parse(source, root: 'type').compile(cpl)
|
36
36
|
end
|
37
37
|
|
38
38
|
end # module Syntax
|
data/lib/finitio/system.rb
CHANGED
@@ -50,24 +50,23 @@ module Finitio
|
|
50
50
|
def fetch(name, with_imports = true, &bl)
|
51
51
|
if with_imports
|
52
52
|
@types.fetch(name) do
|
53
|
-
|
53
|
+
fetch_on_imports(name, &bl)
|
54
54
|
end
|
55
55
|
else
|
56
56
|
@types.fetch(name, &bl)
|
57
57
|
end
|
58
58
|
end
|
59
59
|
|
60
|
-
def
|
60
|
+
def fetch_on_imports(name, imports = @imports, &bl)
|
61
61
|
if imports.empty?
|
62
62
|
raise KeyError, %Q{key not found: "#{name}"} unless bl
|
63
63
|
bl.call(name)
|
64
64
|
else
|
65
65
|
imports.first.fetch(name, false) do
|
66
|
-
|
66
|
+
fetch_on_imports(name, imports[1..-1], &bl)
|
67
67
|
end
|
68
68
|
end
|
69
69
|
end
|
70
|
-
private :_fetch
|
71
70
|
|
72
71
|
def factory
|
73
72
|
@factory ||= TypeFactory.new
|
@@ -89,22 +88,12 @@ module Finitio
|
|
89
88
|
Syntax.compile(source, self.dup)
|
90
89
|
end
|
91
90
|
|
92
|
-
def resolve_proxies(recurse = true)
|
93
|
-
rebuilt = {}
|
94
|
-
scope = FetchScope.new(self, rebuilt)
|
95
|
-
types.each_with_object(rebuilt) do |(name,type),memo|
|
96
|
-
rebuilt[name] = type.resolve_proxies(scope)
|
97
|
-
end
|
98
|
-
resolved = System.new(rebuilt, imports)
|
99
|
-
recurse ? resolved.resolve_proxies(false) : resolved
|
100
|
-
end
|
101
|
-
|
102
91
|
def inspect
|
103
92
|
@types.each_pair.map{|k,v| "#{k} = #{v}" }.join("\n")
|
104
93
|
end
|
105
94
|
|
106
|
-
def dup
|
107
|
-
System.new(
|
95
|
+
def dup(types = @types.dup, imports = @imports.dup)
|
96
|
+
System.new(types, imports)
|
108
97
|
end
|
109
98
|
|
110
99
|
def check_and_warn(logger = nil)
|
@@ -28,7 +28,9 @@ module Finitio
|
|
28
28
|
|
29
29
|
def instantiate(compilation, sub_types)
|
30
30
|
overrides = Hash[vars.zip(sub_types)]
|
31
|
-
defn.resolve_proxies(compilation.with_scope(overrides))
|
31
|
+
defn.resolve_proxies(compilation.with_scope(overrides)).dup.tap{|x|
|
32
|
+
x.send(:name=, "#{name}<#{overrides.values.join(',')}>", true)
|
33
|
+
}
|
32
34
|
end
|
33
35
|
|
34
36
|
def unconstrained
|
@@ -15,8 +15,26 @@ module Finitio
|
|
15
15
|
"_#{target_name}_"
|
16
16
|
end
|
17
17
|
|
18
|
+
def include?(*args, &bl)
|
19
|
+
raise Error, "Proxy not resolved: #{target_name}" unless @target
|
20
|
+
|
21
|
+
@target.include?(*args, &bl)
|
22
|
+
end
|
23
|
+
|
24
|
+
def dress(*args, &bl)
|
25
|
+
raise Error, "Proxy not resolved: #{target_name}" unless @target
|
26
|
+
|
27
|
+
@target.dress(*args, &bl)
|
28
|
+
end
|
29
|
+
|
30
|
+
def bind!(system)
|
31
|
+
@target = system.fetch(target_name) {
|
32
|
+
raise Error, "No such type `#{target_name}` in #{system}"
|
33
|
+
}
|
34
|
+
end
|
35
|
+
|
18
36
|
def resolve_proxies(system)
|
19
|
-
system.fetch(target_name){
|
37
|
+
system.fetch(target_name) {
|
20
38
|
raise Error, "No such type `#{target_name}` in #{system}"
|
21
39
|
}
|
22
40
|
end
|
data/lib/finitio/type.rb
CHANGED
@@ -32,8 +32,10 @@ module Finitio
|
|
32
32
|
@name || default_name
|
33
33
|
end
|
34
34
|
|
35
|
-
def name=(n)
|
36
|
-
|
35
|
+
def name=(n, force = false)
|
36
|
+
if !@name.nil? && !force
|
37
|
+
raise Error, "Name already set to `#{@name}` on #{self.class}"
|
38
|
+
end
|
37
39
|
@name = n
|
38
40
|
end
|
39
41
|
|
data/lib/finitio/version.rb
CHANGED
@@ -15,24 +15,14 @@ module Finitio
|
|
15
15
|
system['Tree']
|
16
16
|
}
|
17
17
|
|
18
|
-
|
18
|
+
it 'works as expected' do
|
19
19
|
expect(type.to_json_schema).to eql({
|
20
20
|
type: "object",
|
21
21
|
properties: {
|
22
22
|
children: {
|
23
23
|
type: "array",
|
24
24
|
items: {
|
25
|
-
type: "object"
|
26
|
-
properties: {
|
27
|
-
children: {
|
28
|
-
type: "array",
|
29
|
-
items: "object"
|
30
|
-
}
|
31
|
-
},
|
32
|
-
required: [
|
33
|
-
:children
|
34
|
-
],
|
35
|
-
additionalProperties: false
|
25
|
+
type: "object"
|
36
26
|
}
|
37
27
|
}
|
38
28
|
},
|
@@ -0,0 +1,53 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe "Dress on a recursive type" do
|
4
|
+
let(:schema){
|
5
|
+
Finitio.system <<~F
|
6
|
+
Tree = {
|
7
|
+
children: [Tree]
|
8
|
+
}
|
9
|
+
Tree
|
10
|
+
F
|
11
|
+
}
|
12
|
+
|
13
|
+
it 'works on an empty tree' do
|
14
|
+
expect(->(){
|
15
|
+
schema.dress({children: []})
|
16
|
+
}).not_to raise_error
|
17
|
+
end
|
18
|
+
|
19
|
+
it 'works on a non empty tree' do
|
20
|
+
expect(->(){
|
21
|
+
schema.dress({
|
22
|
+
children: [{
|
23
|
+
children: [{
|
24
|
+
children: [{
|
25
|
+
children: []
|
26
|
+
}]
|
27
|
+
}]
|
28
|
+
}]
|
29
|
+
})
|
30
|
+
}).not_to raise_error
|
31
|
+
end
|
32
|
+
|
33
|
+
it 'detects deep error' do
|
34
|
+
expect(->(){
|
35
|
+
schema.dress({
|
36
|
+
children: [{
|
37
|
+
children: [{
|
38
|
+
children: [{
|
39
|
+
children: [{
|
40
|
+
children: [{
|
41
|
+
children: [{
|
42
|
+
unrecognized: true,
|
43
|
+
children: []
|
44
|
+
}]
|
45
|
+
}]
|
46
|
+
}]
|
47
|
+
}]
|
48
|
+
}]
|
49
|
+
}]
|
50
|
+
})
|
51
|
+
}).to raise_error(Finitio::Error)
|
52
|
+
end
|
53
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe "The types of generics definitions" do
|
4
|
+
describe "When the extra map to a type" do
|
5
|
+
let(:schema){
|
6
|
+
Finitio.system <<~F
|
7
|
+
Collection<T> = [T]
|
8
|
+
|
9
|
+
String = .String
|
10
|
+
Collection<String>
|
11
|
+
F
|
12
|
+
}
|
13
|
+
|
14
|
+
it 'works' do
|
15
|
+
expect(schema['Main'].target.name).to eql("Collection<String>")
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
data/spec/syntax/test_compile.rb
CHANGED
@@ -77,6 +77,24 @@ module Finitio
|
|
77
77
|
end
|
78
78
|
|
79
79
|
context 'with AD types' do
|
80
|
+
let(:source){
|
81
|
+
<<-EOF.strip
|
82
|
+
Int = .Integer
|
83
|
+
Byte = Int(i | i>0)
|
84
|
+
Color = .Color <rgb> { r: Byte, g: Byte, b: Byte }
|
85
|
+
Colors = [Color]
|
86
|
+
EOF
|
87
|
+
}
|
88
|
+
|
89
|
+
it{ should be_a(System) }
|
90
|
+
|
91
|
+
it 'should work fine' do
|
92
|
+
got = subject['Colors'].dress([{ r: 10, g: 15, b: 20 }])
|
93
|
+
expect(got.first).to be_a(Color)
|
94
|
+
end
|
95
|
+
end
|
96
|
+
|
97
|
+
context 'with AD types that make forward references' do
|
80
98
|
let(:source){
|
81
99
|
<<-EOF.strip
|
82
100
|
Colors = [Color]
|
@@ -88,7 +106,7 @@ module Finitio
|
|
88
106
|
|
89
107
|
it{ should be_a(System) }
|
90
108
|
|
91
|
-
it 'should work
|
109
|
+
it 'should work fine' do
|
92
110
|
got = subject['Colors'].dress([{ r: 10, g: 15, b: 20 }])
|
93
111
|
expect(got.first).to be_a(Color)
|
94
112
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: finitio
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.11.
|
4
|
+
version: 0.11.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Bernard Lambeau
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-01-
|
11
|
+
date: 2023-01-07 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: citrus
|
@@ -163,6 +163,7 @@ files:
|
|
163
163
|
- lib/finitio/generation/heuristic.rb
|
164
164
|
- lib/finitio/generation/heuristic/constant.rb
|
165
165
|
- lib/finitio/generation/heuristic/random.rb
|
166
|
+
- lib/finitio/generation/proxy_type.rb
|
166
167
|
- lib/finitio/generation/rel_based_type.rb
|
167
168
|
- lib/finitio/generation/seq_type.rb
|
168
169
|
- lib/finitio/generation/set_type.rb
|
@@ -193,6 +194,7 @@ files:
|
|
193
194
|
- lib/finitio/support/heading.rb
|
194
195
|
- lib/finitio/support/metadata.rb
|
195
196
|
- lib/finitio/support/proc_with_code.rb
|
197
|
+
- lib/finitio/support/proxy_resolver.rb
|
196
198
|
- lib/finitio/support/type_factory.rb
|
197
199
|
- lib/finitio/syntax.rb
|
198
200
|
- lib/finitio/syntax/definitions.rb
|
@@ -317,7 +319,9 @@ files:
|
|
317
319
|
- spec/json_schema/test_sub_type.rb
|
318
320
|
- spec/json_schema/test_tuple_type.rb
|
319
321
|
- spec/json_schema/test_union_type.rb
|
322
|
+
- spec/regression/test_dress_on_recursive_type.rb
|
320
323
|
- spec/regression/test_heading_extra_are_proxy_resolved.rb
|
324
|
+
- spec/regression/test_name_of_generic_types.rb
|
321
325
|
- spec/spec_helper.rb
|
322
326
|
- spec/support/test_compare_attrs.rb
|
323
327
|
- spec/support/test_proc_with_code.rb
|
@@ -488,6 +492,8 @@ signing_key:
|
|
488
492
|
specification_version: 4
|
489
493
|
summary: Finitio - in Ruby
|
490
494
|
test_files:
|
495
|
+
- spec/regression/test_dress_on_recursive_type.rb
|
496
|
+
- spec/regression/test_name_of_generic_types.rb
|
491
497
|
- spec/regression/test_heading_extra_are_proxy_resolved.rb
|
492
498
|
- spec/test_finitio.rb
|
493
499
|
- spec/constraint/test_named.rb
|