rdl 1.0.0.rc3 → 1.0.0.rc4
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/.gitignore +44 -0
- data/.travis.yml +19 -0
- data/LICENSE +29 -0
- data/README.md +509 -0
- data/Rakefile +27 -0
- data/gemfiles/Gemfile.travis +5 -0
- data/lib/rdl/wrap.rb +1 -1
- data/lib/rdl_types.rb +4 -2
- data/rdl.gemspec +23 -0
- data/test/disabled_test_coverage.rb +156 -0
- data/test/disabled_test_rdoc.rb +116 -0
- data/test/test_alias.rb +66 -0
- data/test/test_contract.rb +70 -0
- data/test/test_dsl.rb +85 -0
- data/test/test_generic.rb +188 -0
- data/test/test_intersection.rb +41 -0
- data/test/test_le.rb +193 -0
- data/test/test_lib_types.rb +194 -0
- data/test/test_member.rb +148 -0
- data/test/test_parser.rb +196 -0
- data/test/test_rdl.rb +301 -0
- data/test/test_rdl_type.rb +70 -0
- data/test/test_type_contract.rb +187 -0
- data/test/test_types.rb +221 -0
- data/test/test_wrap.rb +46 -0
- data/types/{ruby-2.2.0 → ruby-2.x}/_aliases.rb +0 -0
- data/types/{ruby-2.2.0 → ruby-2.x}/abbrev.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/array.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/base64.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/basic_object.rb +2 -1
- data/types/{ruby-2.2.0 → ruby-2.x}/benchmark.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/bigdecimal.rb +4 -4
- data/types/{ruby-2.2.0 → ruby-2.x}/bigmath.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/class.rb +3 -3
- data/types/{ruby-2.2.0 → ruby-2.x}/complex.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/coverage.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/csv.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/date.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/dir.rb +3 -3
- data/types/{ruby-2.2.0 → ruby-2.x}/encoding.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/enumerable.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/enumerator.rb +1 -1
- data/types/{ruby-2.2.0 → ruby-2.x}/exception.rb +2 -0
- data/types/{ruby-2.2.0 → ruby-2.x}/file.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/fileutils.rb +1 -1
- data/types/{ruby-2.2.0 → ruby-2.x}/fixnum.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/float.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/gem.rb +3 -1
- data/types/{ruby-2.2.0 → ruby-2.x}/hash.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/integer.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/io.rb +1 -1
- data/types/{ruby-2.2.0 → ruby-2.x}/kernel.rb +1 -1
- data/types/{ruby-2.2.0 → ruby-2.x}/marshal.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/matchdata.rb +3 -3
- data/types/{ruby-2.2.0 → ruby-2.x}/math.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/numeric.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/object.rb +1 -1
- data/types/{ruby-2.2.0 → ruby-2.x}/pathname.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/process.rb +8 -8
- data/types/{ruby-2.2.0 → ruby-2.x}/random.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/range.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/rational.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/regexp.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/set.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/string.rb +1 -1
- data/types/{ruby-2.2.0 → ruby-2.x}/strscan.rb +3 -3
- data/types/{ruby-2.2.0 → ruby-2.x}/symbol.rb +2 -2
- data/types/{ruby-2.2.0 → ruby-2.x}/time.rb +2 -2
- data/types/ruby-2.x/uri.rb +20 -0
- data/types/{ruby-2.2.0 → ruby-2.x}/yaml.rb +3 -3
- metadata +70 -51
- data/lib/rdl/types/wild.rb +0 -26
- data/types/other/chronic.rb +0 -5
- data/types/other/paperclip_attachment.rb +0 -7
- data/types/other/securerandom.rb +0 -4
- data/types/ruby-2.2.0/uri.rb +0 -18
data/test/test_rdl.rb
ADDED
@@ -0,0 +1,301 @@
|
|
1
|
+
require 'minitest/autorun'
|
2
|
+
require_relative '../lib/rdl.rb'
|
3
|
+
|
4
|
+
class TestRDL < Minitest::Test
|
5
|
+
|
6
|
+
# Test wrapping with no types or contracts
|
7
|
+
def test_wrap
|
8
|
+
def m1(x) return x; end
|
9
|
+
def m2(x) return x; end
|
10
|
+
def m3(x) return x; end
|
11
|
+
def m4(x) return x; end
|
12
|
+
assert(not(RDL::Wrap.wrapped?(TestRDL, :m1)))
|
13
|
+
assert(not(RDL::Wrap.wrapped?(TestRDL, :m2)))
|
14
|
+
assert(not(RDL::Wrap.wrapped?(TestRDL, :m3)))
|
15
|
+
assert(not(RDL::Wrap.wrapped?(TestRDL, :m4)))
|
16
|
+
RDL::Wrap.wrap(TestRDL, :m1)
|
17
|
+
RDL::Wrap.wrap("TestRDL", :m2)
|
18
|
+
RDL::Wrap.wrap(:TestRDL, :m3)
|
19
|
+
RDL::Wrap.wrap(TestRDL, "m4")
|
20
|
+
assert(RDL::Wrap.wrapped?(TestRDL, :m1))
|
21
|
+
assert(RDL::Wrap.wrapped?(TestRDL, :m2))
|
22
|
+
assert(RDL::Wrap.wrapped?(TestRDL, :m3))
|
23
|
+
assert(RDL::Wrap.wrapped?(TestRDL, :m4))
|
24
|
+
assert_equal 3, m1(3)
|
25
|
+
assert_equal 3, m2(3)
|
26
|
+
assert_equal 3, m3(3)
|
27
|
+
assert_equal 3, m4(3)
|
28
|
+
end
|
29
|
+
|
30
|
+
def test_process_pre_post_args
|
31
|
+
ppos = RDL::Contract::FlatContract.new("Positive") { |x| x > 0 }
|
32
|
+
assert_equal ["TestRDL", :m1, ppos], RDL::Wrap.process_pre_post_args(self.class, "C", TestRDL, :m1, ppos)
|
33
|
+
assert_equal ["TestRDL", :m1, ppos], RDL::Wrap.process_pre_post_args(self.class, "C", TestRDL, "m1", ppos)
|
34
|
+
assert_equal ["[singleton]TestRDL", :m1, ppos], RDL::Wrap.process_pre_post_args(self.class, "C", TestRDL, "self.m1", ppos)
|
35
|
+
assert_equal ["TestRDL", :m1, ppos], RDL::Wrap.process_pre_post_args(self.class, "C", :m1, ppos)
|
36
|
+
assert_equal ["TestRDL", nil, ppos], RDL::Wrap.process_pre_post_args(self.class, "C", ppos)
|
37
|
+
klass1, meth1, c1 = RDL::Wrap.process_pre_post_args(self.class, "C", TestRDL, :m1) { |x| x > 0 }
|
38
|
+
assert_equal ["TestRDL", :m1], [klass1, meth1]
|
39
|
+
assert (c1.is_a? RDL::Contract::FlatContract)
|
40
|
+
|
41
|
+
klass2, meth2, c2 = RDL::Wrap.process_pre_post_args(self.class, "C", :m1) { |x| x > 0 }
|
42
|
+
assert_equal ["TestRDL", :m1], [klass2, meth2]
|
43
|
+
assert (c2.is_a? RDL::Contract::FlatContract)
|
44
|
+
|
45
|
+
klass3, meth3, c3 = RDL::Wrap.process_pre_post_args(self.class, "C") { |x| x > 0 }
|
46
|
+
assert_equal ["TestRDL", nil], [klass3, meth3]
|
47
|
+
assert (c3.is_a? RDL::Contract::FlatContract)
|
48
|
+
|
49
|
+
assert_raises(ArgumentError) { RDL::Wrap.process_pre_post_args(self.class, "C") }
|
50
|
+
assert_raises(ArgumentError) { RDL::Wrap.process_pre_post_args(self.class, "C", 42) }
|
51
|
+
assert_raises(ArgumentError) { RDL::Wrap.process_pre_post_args(self.class, "C", 42) { |x| x > 0} }
|
52
|
+
assert_raises(ArgumentError) { RDL::Wrap.process_pre_post_args(self.class, "C", ppos) { |x| x > 0 } }
|
53
|
+
assert_raises(ArgumentError) { RDL::Wrap.process_pre_post_args(self.class, "C", :m1) }
|
54
|
+
assert_raises(ArgumentError) { RDL::Wrap.process_pre_post_args(self.class, "C", TestRDL) }
|
55
|
+
assert_raises(ArgumentError) { RDL::Wrap.process_pre_post_args(self.class, "C", TestRDL) { |x| x > 0 } }
|
56
|
+
assert_raises(ArgumentError) { RDL::Wrap.process_pre_post_args(self.class, "C", TestRDL, ppos) }
|
57
|
+
assert_raises(ArgumentError) { RDL::Wrap.process_pre_post_args(self.class, "C", TestRDL, :m1, ppos, 42) }
|
58
|
+
end
|
59
|
+
|
60
|
+
def test_pre_contract
|
61
|
+
pos = RDL::Contract::FlatContract.new("Positive") { |x| x > 0 }
|
62
|
+
def m5(x) return x; end
|
63
|
+
pre TestRDL, :m5, pos
|
64
|
+
assert_equal 3, m5(3)
|
65
|
+
assert_raises(RDL::Contract::ContractError) { m5(-1) }
|
66
|
+
end
|
67
|
+
|
68
|
+
def test_post_contract
|
69
|
+
neg = RDL::Contract::FlatContract.new("Negative") { |x| x < 0 }
|
70
|
+
def m6(x) return 3; end
|
71
|
+
post TestRDL, :m6, neg
|
72
|
+
assert_raises(RDL::Contract::ContractError) { m6(42) }
|
73
|
+
end
|
74
|
+
|
75
|
+
def test_pre_post_contract
|
76
|
+
pos = RDL::Contract::FlatContract.new("Positive") { |x| x > 0 }
|
77
|
+
ppos = RDL::Contract::FlatContract.new("Positive") { |r, x| r > 0 }
|
78
|
+
def m7(x) return x; end
|
79
|
+
pre TestRDL, :m7, pos
|
80
|
+
post TestRDL, :m7, ppos
|
81
|
+
assert_equal 3, m7(3)
|
82
|
+
end
|
83
|
+
|
84
|
+
def test_and_contract
|
85
|
+
pos = RDL::Contract::FlatContract.new("Positive") { |x| x > 0 }
|
86
|
+
five = RDL::Contract::FlatContract.new("Five") { |x| x == 5 }
|
87
|
+
gt = RDL::Contract::FlatContract.new("Greater Than 3") { |x| x > 3 }
|
88
|
+
def m8(x) return x; end
|
89
|
+
pre TestRDL, :m8, pos
|
90
|
+
pre TestRDL, :m8, gt
|
91
|
+
assert_equal 5, m8(5)
|
92
|
+
assert_equal 4, m8(4)
|
93
|
+
assert_raises(RDL::Contract::ContractError) { m8 3 }
|
94
|
+
def m9(x) return x; end
|
95
|
+
pre TestRDL, :m9, pos
|
96
|
+
pre TestRDL, :m9, gt
|
97
|
+
pre TestRDL, :m9, five
|
98
|
+
assert_equal 5, m9(5)
|
99
|
+
assert_raises(RDL::Contract::ContractError) { m9 4 }
|
100
|
+
assert_raises(RDL::Contract::ContractError) { m9 3 }
|
101
|
+
|
102
|
+
ppos = RDL::Contract::FlatContract.new("Positive") { |r, x| r > 0 }
|
103
|
+
pfive = RDL::Contract::FlatContract.new("Five") { |r, x| r == 5 }
|
104
|
+
pgt = RDL::Contract::FlatContract.new("Greater Than 3") { |r, x| r > 3 }
|
105
|
+
def m10(x) return x; end
|
106
|
+
post TestRDL, :m10, ppos
|
107
|
+
post TestRDL, :m10, pgt
|
108
|
+
assert_equal 5, m10(5)
|
109
|
+
assert_equal 4, m10(4)
|
110
|
+
assert_raises(RDL::Contract::ContractError) { m10 3 }
|
111
|
+
def m11(x) return x; end
|
112
|
+
post TestRDL, :m11, ppos
|
113
|
+
post TestRDL, :m11, pgt
|
114
|
+
post TestRDL, :m11, pfive
|
115
|
+
assert_equal 5, m11(5)
|
116
|
+
assert_raises(RDL::Contract::ContractError) { m11 4 }
|
117
|
+
assert_raises(RDL::Contract::ContractError) { m11 3 }
|
118
|
+
end
|
119
|
+
|
120
|
+
def test_deferred_wrap
|
121
|
+
pos = RDL::Contract::FlatContract.new("Positive") { |x| x > 0 }
|
122
|
+
pre TestRDL, :m12, pos
|
123
|
+
def m12(x) return x; end
|
124
|
+
assert_equal 3, m12(3)
|
125
|
+
assert_raises(RDL::Contract::ContractError) { m12(-1) }
|
126
|
+
|
127
|
+
ppos = RDL::Contract::FlatContract.new("Positive") { |r, x| r > 0 }
|
128
|
+
post TestRDL, :m13, ppos
|
129
|
+
def m13(x) return x; end
|
130
|
+
assert_equal 3, m13(3)
|
131
|
+
assert_raises(RDL::Contract::ContractError) { m13(-1) }
|
132
|
+
|
133
|
+
self.class.class_eval {
|
134
|
+
pre(pos)
|
135
|
+
def m14(x) return x; end
|
136
|
+
}
|
137
|
+
assert_equal 3, m14(3)
|
138
|
+
assert_raises(RDL::Contract::ContractError) { m14(-1) }
|
139
|
+
|
140
|
+
self.class.class_eval {
|
141
|
+
pre { |x| x > 0 }
|
142
|
+
def m15(x) return x; end
|
143
|
+
}
|
144
|
+
assert_equal 3, m15(3)
|
145
|
+
assert_raises(RDL::Contract::ContractError) { m15(-1) }
|
146
|
+
|
147
|
+
self.class.class_eval {
|
148
|
+
pre { |x| x > 0 }
|
149
|
+
post { |r, x| x > 0 }
|
150
|
+
def m17(x) return x; end
|
151
|
+
}
|
152
|
+
assert_equal 3, m17(3)
|
153
|
+
assert_raises(RDL::Contract::ContractError) { m17(-1) }
|
154
|
+
|
155
|
+
self.class.class_eval {
|
156
|
+
pre { |x| x > 0 }
|
157
|
+
post { |r, x| x < 0 }
|
158
|
+
def m18(x) return x; end
|
159
|
+
}
|
160
|
+
assert_raises(RDL::Contract::ContractError) { m18(-1) }
|
161
|
+
|
162
|
+
self.class.class_eval {
|
163
|
+
pre { |x| x > 0 }
|
164
|
+
pre { |x| x < 5 }
|
165
|
+
def m19(x) return x; end
|
166
|
+
}
|
167
|
+
assert_equal 3, m19(3)
|
168
|
+
assert_raises(RDL::Contract::ContractError) { m19(6) }
|
169
|
+
assert_raises(RDL::Contract::ContractError) { m19(-1) }
|
170
|
+
|
171
|
+
assert_raises(RuntimeError) {
|
172
|
+
self.class.class_eval <<-RUBY, __FILE__, __LINE__
|
173
|
+
pre { |x| x > 0 }
|
174
|
+
class Inner
|
175
|
+
def m20(x)
|
176
|
+
return x
|
177
|
+
end
|
178
|
+
end
|
179
|
+
RUBY
|
180
|
+
}
|
181
|
+
end
|
182
|
+
|
183
|
+
def test_special_method_names
|
184
|
+
self.class.class_eval {
|
185
|
+
pre { |x| x > 0 }
|
186
|
+
def [](x) return x end
|
187
|
+
}
|
188
|
+
assert_equal 3, self[3]
|
189
|
+
assert_raises(RDL::Contract::ContractError) { self[-1] }
|
190
|
+
self.class.class_eval {
|
191
|
+
pre { |x| x > 0 }
|
192
|
+
def foo?(x) return x end
|
193
|
+
}
|
194
|
+
assert_equal 3, foo?(3)
|
195
|
+
assert_raises(RDL::Contract::ContractError) { foo?(-1) }
|
196
|
+
self.class.class_eval {
|
197
|
+
pre(:"bar!") { |x| x > 0 }
|
198
|
+
def bar!(x) return x end
|
199
|
+
}
|
200
|
+
assert_equal 3, bar!(3)
|
201
|
+
assert_raises(RDL::Contract::ContractError) { bar!(-1) }
|
202
|
+
end
|
203
|
+
|
204
|
+
def test_wrap_access_control
|
205
|
+
def m20(x) return x; end
|
206
|
+
def m21(x) return x; end
|
207
|
+
def m22(x) return x; end
|
208
|
+
self.class.class_eval { public(:m20) }
|
209
|
+
self.class.class_eval { protected(:m21) }
|
210
|
+
self.class.class_eval { private(:m22) }
|
211
|
+
RDL::Wrap.wrap(TestRDL, :m20)
|
212
|
+
RDL::Wrap.wrap(TestRDL, :m21)
|
213
|
+
RDL::Wrap.wrap(TestRDL, :m22)
|
214
|
+
assert (self.class.class_eval { public_method_defined? :m20 })
|
215
|
+
assert (self.class.class_eval { protected_method_defined? :m21 })
|
216
|
+
assert (self.class.class_eval { private_method_defined? :m22 })
|
217
|
+
end
|
218
|
+
|
219
|
+
def test_type_params
|
220
|
+
self.class.class_eval "class TP1; type_params [:t], :all? end"
|
221
|
+
assert_equal [[:t], [:~], :all?], RDL::Wrap.get_type_params(TestRDL::TP1)
|
222
|
+
self.class.class_eval "class TP2; type_params([:t], nil) { |t| true } end"
|
223
|
+
tp2 = RDL::Wrap.get_type_params(TestRDL::TP2)
|
224
|
+
assert_equal [:t], tp2[0]
|
225
|
+
assert_equal [:~], tp2[1]
|
226
|
+
assert_raises(RuntimeError) { self.class.class_eval "class TP1; type_params [:t], :all? end" }
|
227
|
+
self.class.class_eval "class TP3; type_params [:t, :u], :all? end"
|
228
|
+
assert_equal [[:t, :u], [:~, :~], :all?], RDL::Wrap.get_type_params(TestRDL::TP3)
|
229
|
+
|
230
|
+
self.class.class_eval "class TP4; type_params [:t, :u, :v], :all?, variance: [:+, :-, :~] end"
|
231
|
+
assert_equal [[:t, :u, :v], [:+, :-, :~], :all?], RDL::Wrap.get_type_params(TestRDL::TP4)
|
232
|
+
assert_raises(RuntimeError) { self.class.class_eval "class TP5; type_params([], :all?) { true } end" }
|
233
|
+
assert_raises(RuntimeError) { self.class.class_eval "class TP6; type_params [:t, :u], :all?, variance: [:+] end" }
|
234
|
+
assert_raises(RuntimeError) { self.class.class_eval "class TP7; type_params [:t, :u], :all?, variance: [:a, :b] end" }
|
235
|
+
assert_raises(RuntimeError) { self.class.class_eval "class TP8; type_params([:t], :all?) { |t| true } end" }
|
236
|
+
assert_raises(RuntimeError) { self.class.class_eval "class TP8; type_params [:t], 42 end" }
|
237
|
+
end
|
238
|
+
|
239
|
+
def test_wrap_new
|
240
|
+
self.class.class_eval "class B; def initialize(x); @x = x end; def get(); return @x end end"
|
241
|
+
pre("TestRDL::B", "self.new") { |x| x > 0 }
|
242
|
+
assert_equal 3, TestRDL::B.new(3).get
|
243
|
+
assert_raises(RDL::Contract::ContractError) { TestRDL::B.new(-3) }
|
244
|
+
|
245
|
+
self.class.class_eval "class C; pre { |x| x > 0 }; def initialize(x); @x = x end; def get(); return @x end end"
|
246
|
+
assert_equal 3, TestRDL::C.new(3).get
|
247
|
+
assert_raises(RDL::Contract::ContractError) { TestRDL::C.new(-3) }
|
248
|
+
|
249
|
+
self.class.class_eval "class D; def get(); return @x end end"
|
250
|
+
pre("TestRDL::D", "self.new") { |x| x > 0 }
|
251
|
+
self.class.class_eval "class D; def initialize(x); @x = x end end"
|
252
|
+
assert_equal 3, TestRDL::D.new(3).get
|
253
|
+
assert_raises(RDL::Contract::ContractError) { TestRDL::D.new(-3) }
|
254
|
+
|
255
|
+
skip "Can't defer contracts on new yet"
|
256
|
+
pre("TestRDL::E", "self.new") { |x| x > 0 }
|
257
|
+
self.class.class_eval "class E; def initialize(x); @x = x end end"
|
258
|
+
assert (TestRDL::E.new(3))
|
259
|
+
assert_raises(RDL::Contract::ContractError) { TestRDL::E.new(-3) }
|
260
|
+
end
|
261
|
+
|
262
|
+
def test_class_method
|
263
|
+
pos = RDL::Contract::FlatContract.new("Positive") { |x| x > 0 }
|
264
|
+
self.class.class_eval { def self.cm1(x) return x; end }
|
265
|
+
pre TestRDL, "self.cm1", pos
|
266
|
+
assert_equal 3, TestRDL.cm1(3)
|
267
|
+
assert_raises(RDL::Contract::ContractError) { TestRDL.cm1(-1) }
|
268
|
+
|
269
|
+
assert_raises(RuntimeError) { pre TestRDL, "TestRDL.cm1", pos }
|
270
|
+
|
271
|
+
pre TestRDL, "self.cm2", pos
|
272
|
+
self.class.class_eval { def self.cm2(x) return x; end }
|
273
|
+
assert_equal 3, TestRDL.cm2(3)
|
274
|
+
assert_raises(RDL::Contract::ContractError) { TestRDL.cm2(-1) }
|
275
|
+
|
276
|
+
self.class.class_eval {
|
277
|
+
pre { |x| x > 0 }
|
278
|
+
def self.cm3(x) return x; end
|
279
|
+
}
|
280
|
+
assert_equal 3, TestRDL.cm3(3)
|
281
|
+
assert_raises(RDL::Contract::ContractError) { TestRDL.cm3(-1) }
|
282
|
+
end
|
283
|
+
|
284
|
+
def test_cast
|
285
|
+
ntyp = RDL::Type::NilType.new
|
286
|
+
obj1 = 3.type_cast(ntyp)
|
287
|
+
assert (ntyp.member? obj1)
|
288
|
+
obj2 = 3.type_cast('nil')
|
289
|
+
assert (ntyp.member? obj2)
|
290
|
+
end
|
291
|
+
|
292
|
+
def test_pre_post_self
|
293
|
+
self.class.class_eval {
|
294
|
+
pre { |x| self.instance_of? TestRDL }
|
295
|
+
post { |r, x| self.instance_of? TestRDL }
|
296
|
+
def m23(x) return x; end
|
297
|
+
}
|
298
|
+
assert_equal 3, m23(3)
|
299
|
+
end
|
300
|
+
|
301
|
+
end
|
@@ -0,0 +1,70 @@
|
|
1
|
+
require 'minitest/autorun'
|
2
|
+
require_relative '../lib/rdl.rb'
|
3
|
+
|
4
|
+
class TestRDLType < Minitest::Test
|
5
|
+
def test_single_type_contract
|
6
|
+
def m1(x) return x; end
|
7
|
+
type TestRDLType, :m1, "(Fixnum) -> Fixnum"
|
8
|
+
assert_equal 5, m1(5)
|
9
|
+
assert_raises(RDL::Type::TypeError) { m1("foo") }
|
10
|
+
|
11
|
+
self.class.class_eval {
|
12
|
+
type :m2, "(Fixnum) -> Fixnum"
|
13
|
+
def m2(x) return x; end
|
14
|
+
}
|
15
|
+
assert_equal 5, m2(5)
|
16
|
+
assert_raises(RDL::Type::TypeError) { m2("foo") }
|
17
|
+
|
18
|
+
self.class.class_eval {
|
19
|
+
type "(Fixnum) -> Fixnum"
|
20
|
+
def m3(x) return x; end
|
21
|
+
}
|
22
|
+
assert_equal 5, m3(5)
|
23
|
+
assert_raises(RDL::Type::TypeError) { m3("foo") }
|
24
|
+
end
|
25
|
+
|
26
|
+
def test_intersection_type_contract
|
27
|
+
self.class.class_eval {
|
28
|
+
type "(Fixnum) -> Fixnum"
|
29
|
+
type "(String) -> String"
|
30
|
+
def m4(x) return x; end
|
31
|
+
}
|
32
|
+
assert_equal 5, m4(5)
|
33
|
+
assert_equal "foo", m4("foo")
|
34
|
+
assert_raises(RDL::Type::TypeError) { m4(:foo) }
|
35
|
+
|
36
|
+
self.class.class_eval {
|
37
|
+
type "(Fixnum) -> Fixnum"
|
38
|
+
type "(String) -> String"
|
39
|
+
def m5(x) return 42; end
|
40
|
+
}
|
41
|
+
assert_equal 42, m5(3)
|
42
|
+
assert_raises(RDL::Type::TypeError) { m5("foo") }
|
43
|
+
|
44
|
+
self.class.class_eval {
|
45
|
+
type "(Fixnum) -> Fixnum"
|
46
|
+
type "(Fixnum) -> String"
|
47
|
+
def m6(x) if x > 10 then :oops elsif x > 5 then x else "small" end end
|
48
|
+
}
|
49
|
+
assert_equal 8, m6(8)
|
50
|
+
assert_equal "small", m6(1)
|
51
|
+
assert_raises(RDL::Type::TypeError) { m6(42) }
|
52
|
+
end
|
53
|
+
|
54
|
+
def test_fixnum_type_contract
|
55
|
+
self.class.class_eval {
|
56
|
+
type "(0) -> Fixnum"
|
57
|
+
def m7(x) return x; end
|
58
|
+
}
|
59
|
+
assert_equal 0, m7(0)
|
60
|
+
assert_raises(RDL::Type::TypeError) { m7(1) }
|
61
|
+
end
|
62
|
+
|
63
|
+
def test_wrap_new_inherited
|
64
|
+
self.class.class_eval "class NI_A; def initialize(x); @x = x; end; end; class NI_B < NI_A; end"
|
65
|
+
type "TestRDLType::NI_A", "self.new", "(Fixnum) -> TestRDLType::NI_A"
|
66
|
+
assert (TestRDLType::NI_B.new(3))
|
67
|
+
assert_raises(RDL::Type::TypeError) { TestRDLType::NI_B.new("3") }
|
68
|
+
end
|
69
|
+
|
70
|
+
end
|
@@ -0,0 +1,187 @@
|
|
1
|
+
require 'minitest/autorun'
|
2
|
+
require_relative '../lib/rdl.rb'
|
3
|
+
|
4
|
+
class TestTypeContract < Minitest::Test
|
5
|
+
include RDL::Type
|
6
|
+
include RDL::Contract
|
7
|
+
|
8
|
+
def setup
|
9
|
+
@p = Parser.new
|
10
|
+
end
|
11
|
+
|
12
|
+
def test_flat
|
13
|
+
tnil = NilType.new
|
14
|
+
cnil = tnil.to_contract
|
15
|
+
assert (cnil.check self, nil)
|
16
|
+
assert_raises(TypeError) { cnil.check self, true }
|
17
|
+
tfixnum = NominalType.new :Fixnum
|
18
|
+
cfixnum = tfixnum.to_contract
|
19
|
+
assert (cfixnum.check self, 42)
|
20
|
+
assert (cfixnum.check self, nil)
|
21
|
+
assert_raises(TypeError) { cfixnum.check self, "42" }
|
22
|
+
end
|
23
|
+
|
24
|
+
def test_proc
|
25
|
+
t1 = @p.scan_str "(nil) -> nil"
|
26
|
+
p1 = t1.to_contract.wrap(self) { |x| nil }
|
27
|
+
assert_nil p1.call(nil)
|
28
|
+
assert_raises(TypeError) { p1.call(42) }
|
29
|
+
p1b = t1.to_contract.wrap(self) { |x| 42 }
|
30
|
+
assert_raises(TypeError) { p1b.call(nil) }
|
31
|
+
|
32
|
+
t2 = @p.scan_str "(Fixnum, Fixnum) -> Fixnum"
|
33
|
+
p2 = t2.to_contract.wrap(self) { |x, y| x }
|
34
|
+
assert_equal 42, p2.call(42, 43)
|
35
|
+
assert_equal 42, p2.call(42, nil)
|
36
|
+
assert_raises(TypeError) { p2.call(42, 43, 44) }
|
37
|
+
assert_raises(TypeError) { p2.call(42, 43, 44, 45) }
|
38
|
+
assert_raises(TypeError) { p2.call(42) }
|
39
|
+
assert_raises(TypeError) { p2.call }
|
40
|
+
|
41
|
+
t3 = @p.scan_str "() -> nil"
|
42
|
+
p3 = t3.to_contract.wrap(self) { nil }
|
43
|
+
assert_nil p3.call
|
44
|
+
assert_raises(TypeError) { p3.call(42) }
|
45
|
+
|
46
|
+
t4 = @p.scan_str "(Fixnum, ?Fixnum) -> Fixnum"
|
47
|
+
p4 = t4.to_contract.wrap(self) { |x| x }
|
48
|
+
assert_equal 42, p4.call(42)
|
49
|
+
assert_equal 42, p4.call(42, 43)
|
50
|
+
assert_raises(TypeError) { p4.call(42, 43, 44) }
|
51
|
+
assert_raises(TypeError) { p4.call }
|
52
|
+
|
53
|
+
t5 = @p.scan_str "(Fixnum, *Fixnum) -> Fixnum"
|
54
|
+
p5 = t5.to_contract.wrap(self) { |x| x }
|
55
|
+
assert_equal 42, p5.call(42)
|
56
|
+
assert_equal 42, p5.call(42, 43)
|
57
|
+
assert_equal 42, p5.call(42, 43, 44)
|
58
|
+
assert_equal 42, p5.call(42, 43, 44, 45)
|
59
|
+
assert_raises(TypeError) { p5.call }
|
60
|
+
assert_raises(TypeError) { p5.call("42") }
|
61
|
+
assert_raises(TypeError) { p5.call(42, "43") }
|
62
|
+
assert_raises(TypeError) { p5.call(42, 43, "44") }
|
63
|
+
assert_raises(TypeError) { p5.call(42, 43, 44, "45") }
|
64
|
+
|
65
|
+
t6 = @p.scan_str "(Fixnum, ?Fixnum, ?Fixnum, *Fixnum) -> Fixnum"
|
66
|
+
p6 = t6.to_contract.wrap(self) { |x| x }
|
67
|
+
assert_equal 42, p6.call(42)
|
68
|
+
assert_equal 42, p6.call(42, 43)
|
69
|
+
assert_equal 42, p6.call(42, 43, 44)
|
70
|
+
assert_equal 42, p6.call(42, 43, 44, 45)
|
71
|
+
assert_equal 42, p6.call(42, 43, 44, 45, 46)
|
72
|
+
assert_raises(TypeError) { p6.call }
|
73
|
+
assert_raises(TypeError) { p6.call("42") }
|
74
|
+
assert_raises(TypeError) { p6.call(42, "43") }
|
75
|
+
assert_raises(TypeError) { p6.call(42, 43, "44") }
|
76
|
+
assert_raises(TypeError) { p6.call(42, 43, 44, "45") }
|
77
|
+
assert_raises(TypeError) { p6.call(42, 43, 44, 45, "46") }
|
78
|
+
|
79
|
+
t7 = @p.scan_str "(?Fixnum) -> nil"
|
80
|
+
p7 = t7.to_contract.wrap(self) { nil }
|
81
|
+
assert_nil p7.call
|
82
|
+
assert_nil p7.call(42)
|
83
|
+
assert_raises(TypeError) { p7.call("42") }
|
84
|
+
assert_raises(TypeError) { p7.call(42, 43) }
|
85
|
+
assert_raises(TypeError) { p7.call(42, 43, 44) }
|
86
|
+
|
87
|
+
t8 = @p.scan_str "(*Fixnum) -> nil"
|
88
|
+
p8 = t8.to_contract.wrap(self) { nil }
|
89
|
+
assert_nil p8.call
|
90
|
+
assert_nil p8.call(42)
|
91
|
+
assert_nil p8.call(42, 43)
|
92
|
+
assert_nil p8.call(42, 43, 44)
|
93
|
+
assert_raises(TypeError) { p8.call("42") }
|
94
|
+
assert_raises(TypeError) { p8.call(42, "43") }
|
95
|
+
assert_raises(TypeError) { p8.call(42, 43, "44") }
|
96
|
+
|
97
|
+
t9 = @p.scan_str "(Fixnum arg1, ?Fixnum arg2) -> Fixnum"
|
98
|
+
p9 = t9.to_contract.wrap(self) { |x| x }
|
99
|
+
assert_equal 42, p9.call(42)
|
100
|
+
assert_equal 42, p9.call(42, 43)
|
101
|
+
assert_raises(TypeError) { p9.call(42, 43, 44) }
|
102
|
+
assert_raises(TypeError) { p9.call }
|
103
|
+
|
104
|
+
t10 = @p.scan_str "(?Fixnum, String) -> Fixnum"
|
105
|
+
p10 = t10.to_contract.wrap(self) { |*args| 42 }
|
106
|
+
assert_equal 42, p10.call("44")
|
107
|
+
assert_equal 42, p10.call(43, "44")
|
108
|
+
assert_raises(TypeError) { p10.call() }
|
109
|
+
assert_raises(TypeError) { p10.call(43, "44", 45) }
|
110
|
+
end
|
111
|
+
|
112
|
+
def test_proc_names
|
113
|
+
t1 = @p.scan_str "(x: Fixnum) -> Fixnum"
|
114
|
+
p1 = t1.to_contract.wrap(self) { |x:| x }
|
115
|
+
assert_equal 42, p1.call(x: 42)
|
116
|
+
assert_raises(TypeError) { p1.call(x: "42") }
|
117
|
+
assert_raises(TypeError) { p1.call() }
|
118
|
+
assert_raises(TypeError) { p1.call(x: 42, y: 42) }
|
119
|
+
assert_raises(TypeError) { p1.call(y: 42) }
|
120
|
+
assert_raises(TypeError) { p1.call(42) }
|
121
|
+
assert_raises(TypeError) { p1.call(42, x: 42) }
|
122
|
+
t2 = @p.scan_str "(x: Fixnum, y: String) -> Fixnum"
|
123
|
+
p2 = t2.to_contract.wrap(self) { |x:,y:| x }
|
124
|
+
assert_equal 42, p2.call(x: 42, y: "33")
|
125
|
+
assert_raises(TypeError) { p2.call() }
|
126
|
+
assert_raises(TypeError) { p2.call(x: 42) }
|
127
|
+
assert_raises(TypeError) { p2.call(x: "42", y: "33") }
|
128
|
+
assert_raises(TypeError) { p2.call(42, "43") }
|
129
|
+
assert_raises(TypeError) { p2.call(42, x: 42, y: "33") }
|
130
|
+
assert_raises(TypeError) { p2.call(x: 42, y: "33", z: 44) }
|
131
|
+
t3 = @p.scan_str "(Fixnum, y: String) -> Fixnum"
|
132
|
+
p3 = t3.to_contract.wrap(self) { |x, y:| x }
|
133
|
+
assert_equal 42, p3.call(42, y:"43")
|
134
|
+
assert_raises(TypeError) { p3.call(42) }
|
135
|
+
assert_raises(TypeError) { p3.call(42, y: 43) }
|
136
|
+
assert_raises(TypeError) { p3.call() }
|
137
|
+
assert_raises(TypeError) { p3.call(42, 43, y: 44) }
|
138
|
+
assert_raises(TypeError) { p3.call(42, y: 43, z: 44) }
|
139
|
+
t4 = @p.scan_str "(Fixnum, x: Fixnum, y: String) -> Fixnum"
|
140
|
+
p4 = t4.to_contract.wrap(self) { |a, x:, y:| a }
|
141
|
+
assert_equal 42, p4.call(42, x: 43, y: "44")
|
142
|
+
assert_raises(TypeError) { p4.call(42, x: 43) }
|
143
|
+
assert_raises(TypeError) { p4.call(42, y: "43") }
|
144
|
+
assert_raises(TypeError) { p4.call() }
|
145
|
+
assert_raises(TypeError) { p4.call(42, 43, x: 44, y: "45") }
|
146
|
+
assert_raises(TypeError) { p4.call(42, x: 43, y: "44", z: 45) }
|
147
|
+
t5 = @p.scan_str "(x: Fixnum, y: ?String) -> Fixnum"
|
148
|
+
p5 = t5.to_contract.wrap(self) { |x:, **ys| x }
|
149
|
+
assert_equal 42, p5.call(x: 42, y: "43")
|
150
|
+
assert_equal 42, p5.call(x: 42)
|
151
|
+
assert_raises(TypeError) { p5.call() }
|
152
|
+
assert_raises(TypeError) { p5.call(x: 42, y: 43) }
|
153
|
+
assert_raises(TypeError) { p5.call(x: 42, y: 43, z: 44) }
|
154
|
+
assert_raises(TypeError) { p5.call(3, x: 42, y: 43) }
|
155
|
+
assert_raises(TypeError) { p5.call(3, x: 42) }
|
156
|
+
t6 = @p.scan_str "(x: ?Fixnum, y: String) -> Fixnum"
|
157
|
+
p6 = t6.to_contract.wrap(self) { |y:, **xs| 42 }
|
158
|
+
assert_equal 42, p6.call(x: 43, y: "44")
|
159
|
+
assert_equal 42, p6.call(y: "44")
|
160
|
+
assert_raises(TypeError) { p6.call() }
|
161
|
+
assert_raises(TypeError) { p6.call(x: "43", y: "44") }
|
162
|
+
assert_raises(TypeError) { p6.call(42, x: 43, y: "44") }
|
163
|
+
assert_raises(TypeError) { p6.call(x: 43, y: "44", z: 45) }
|
164
|
+
t7 = @p.scan_str "(x: ?Fixnum, y: ?String) -> Fixnum"
|
165
|
+
p7 = t7.to_contract.wrap(self) { |**args| 42 }
|
166
|
+
assert_equal 42, p7.call()
|
167
|
+
assert_equal 42, p7.call(x: 43)
|
168
|
+
assert_equal 42, p7.call(y: "44")
|
169
|
+
assert_equal 42, p7.call(x: 43, y: "44")
|
170
|
+
assert_raises(TypeError) { p7.call(x: "43", y: "44") }
|
171
|
+
assert_raises(TypeError) { p7.call(41, x: 43, y: "44") }
|
172
|
+
assert_raises(TypeError) { p7.call(x: 43, y: "44", z: 45) }
|
173
|
+
t8 = @p.scan_str "(?Fixnum, x: ?Symbol, y: ?String) -> Fixnum"
|
174
|
+
p8 = t8.to_contract.wrap(self) { |*args| 42 }
|
175
|
+
assert_equal 42, p8.call()
|
176
|
+
assert_equal 42, p8.call(43)
|
177
|
+
assert_equal 42, p8.call(x: :foo)
|
178
|
+
assert_equal 42, p8.call(43, x: :foo)
|
179
|
+
assert_equal 42, p8.call(y: "foo")
|
180
|
+
assert_equal 42, p8.call(43, y: "foo")
|
181
|
+
assert_equal 42, p8.call(x: :foo, y: "foo")
|
182
|
+
assert_equal 42, p8.call(43, x: :foo, y: "foo")
|
183
|
+
assert_raises(TypeError) { p8.call(43, 44, x: :foo, y: "foo") }
|
184
|
+
assert_raises(TypeError) { p8.call(43, x: "foo", y: "foo") }
|
185
|
+
assert_raises(TypeError) { p8.call(43, x: :foo, y: "foo", z: 44) }
|
186
|
+
end
|
187
|
+
end
|