delorean_lang 0.1.7 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +8 -8
- data/lib/delorean/base.rb +0 -1
- data/lib/delorean/container.rb +3 -42
- data/lib/delorean/delorean.rb +1 -17
- data/lib/delorean/delorean.treetop +1 -1
- data/lib/delorean/engine.rb +18 -18
- data/lib/delorean/nodes.rb +3 -3
- data/lib/delorean/version.rb +1 -1
- data/spec/eval_spec.rb +25 -23
- data/spec/parse_spec.rb +13 -59
- data/spec/spec_helper.rb +10 -8
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,15 +1,15 @@
|
|
1
1
|
---
|
2
2
|
!binary "U0hBMQ==":
|
3
3
|
metadata.gz: !binary |-
|
4
|
-
|
4
|
+
NzA4ZGU5ZGEwNmIwNjU0NzYyYWZkMTU4MTAxNzdiMzg3ZjFjODQyNA==
|
5
5
|
data.tar.gz: !binary |-
|
6
|
-
|
6
|
+
ZmNkNTk2Y2Y2YzU5NzJiZTE5MzNmYTU4ODAwYzU3NTAyNmY5ZTJiNg==
|
7
7
|
SHA512:
|
8
8
|
metadata.gz: !binary |-
|
9
|
-
|
10
|
-
|
11
|
-
|
9
|
+
MzY1ZTk3YWMyYTgzODY5ZjM1YjFmODAxM2JlZWJlNDQ4NTg4Yzg1ODNjNGFm
|
10
|
+
NGQwYzM1MmE4YTYxZDVhNzA0NDlhYmFiZGM1NjJhNTVlOGEzYjViYmRiYzA2
|
11
|
+
NGFhMDQyZWEwYjUxOTdiOTc2ZDAyYjE5M2M1NjZlMzgxMDU3OTc=
|
12
12
|
data.tar.gz: !binary |-
|
13
|
-
|
14
|
-
|
15
|
-
|
13
|
+
MzkwMmQwOGUxN2U2MjJmZjJhZjQ0MmU0NGY0Mzg4ZmQ2NmVhZGRlNzI0YjNi
|
14
|
+
NzQyNGE2MTRiYzRkNTdiMTRiMDNmNmNlYzJmOTMyYWU5MDM4ZmY1NjRlM2Y5
|
15
|
+
ZmQxZWNmMmQyZjAyYzE3NmQ0ODg0YWUxZDY2MjAzMTNjOWFiYmU=
|
data/lib/delorean/base.rb
CHANGED
data/lib/delorean/container.rb
CHANGED
@@ -1,46 +1,7 @@
|
|
1
1
|
require 'delorean/base'
|
2
2
|
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
@engines = {}
|
7
|
-
end
|
8
|
-
|
9
|
-
def names
|
10
|
-
@engines.keys.map {|n, v| n}
|
11
|
-
end
|
12
|
-
|
13
|
-
def get(name, version)
|
14
|
-
@engines[ [name, version] ]
|
15
|
-
end
|
16
|
-
|
17
|
-
def add(name, version, engine)
|
18
|
-
if names.member? name
|
19
|
-
n, v = @engines.keys.detect {|n, v| n == name}
|
20
|
-
|
21
|
-
raise "Can't import #{name} version #{version}. " +
|
22
|
-
"Collides with imported version #{v}."
|
23
|
-
end
|
24
|
-
|
25
|
-
@engines[ [name, version] ] = engine
|
26
|
-
end
|
27
|
-
|
28
|
-
def add_imports(engine)
|
29
|
-
# Given an engine, make sure that all of its imports are added
|
30
|
-
# to the script container. This makes sure we don't have
|
31
|
-
# version conflict among different scripts.
|
32
|
-
engine.imports.each { |name, ev|
|
33
|
-
get(name, ev[1]) || add(name, ev[1], ev[0])
|
34
|
-
}
|
35
|
-
end
|
36
|
-
|
37
|
-
def import(name, version)
|
38
|
-
get(name, version) ||
|
39
|
-
add(name, version, get_engine(name, version))
|
40
|
-
end
|
41
|
-
|
42
|
-
def get_engine(name, version)
|
43
|
-
raise "get_engine needs to be overriden"
|
44
|
-
end
|
3
|
+
class Delorean::AbstractContainer
|
4
|
+
def get_engine(name)
|
5
|
+
raise "get_engine needs to be overriden"
|
45
6
|
end
|
46
7
|
end
|
data/lib/delorean/delorean.rb
CHANGED
@@ -165,21 +165,13 @@ module Delorean
|
|
165
165
|
end
|
166
166
|
|
167
167
|
module Formula6
|
168
|
-
def
|
168
|
+
def sp
|
169
169
|
elements[1]
|
170
170
|
end
|
171
171
|
|
172
172
|
def n
|
173
173
|
elements[2]
|
174
174
|
end
|
175
|
-
|
176
|
-
def sp2
|
177
|
-
elements[3]
|
178
|
-
end
|
179
|
-
|
180
|
-
def v
|
181
|
-
elements[4]
|
182
|
-
end
|
183
175
|
end
|
184
176
|
|
185
177
|
def _nt_formula
|
@@ -430,14 +422,6 @@ module Delorean
|
|
430
422
|
if r40
|
431
423
|
r41 = _nt_class_name
|
432
424
|
s38 << r41
|
433
|
-
if r41
|
434
|
-
r42 = _nt_sp
|
435
|
-
s38 << r42
|
436
|
-
if r42
|
437
|
-
r43 = _nt_integer
|
438
|
-
s38 << r43
|
439
|
-
end
|
440
|
-
end
|
441
425
|
end
|
442
426
|
end
|
443
427
|
if s38.last
|
data/lib/delorean/engine.rb
CHANGED
@@ -5,12 +5,13 @@ require 'pp'
|
|
5
5
|
|
6
6
|
module Delorean
|
7
7
|
class Engine
|
8
|
-
attr_reader :last_node, :module_name, :
|
9
|
-
:
|
8
|
+
attr_reader :last_node, :module_name, :line_no,
|
9
|
+
:comp_set, :pm, :m, :imports, :sset
|
10
10
|
|
11
|
-
def initialize(module_name,
|
11
|
+
def initialize(module_name, sset=nil)
|
12
12
|
# name of current module
|
13
|
-
@module_name
|
13
|
+
@module_name = module_name
|
14
|
+
@sset = sset
|
14
15
|
reset
|
15
16
|
end
|
16
17
|
|
@@ -32,30 +33,30 @@ module Delorean
|
|
32
33
|
@multi_no || @line_no
|
33
34
|
end
|
34
35
|
|
35
|
-
def parse_import(
|
36
|
+
def parse_import(name)
|
36
37
|
err(ParseError, "No script set") unless sset
|
37
38
|
|
38
39
|
err(ParseError, "Module #{name} importing itself") if
|
39
40
|
name == module_name
|
40
41
|
|
41
42
|
begin
|
42
|
-
@imports[name] =
|
43
|
+
@imports[name] = sset.get_engine(name)
|
43
44
|
rescue => exc
|
44
45
|
err(ImportError, exc.to_s)
|
45
46
|
end
|
46
47
|
|
47
|
-
@pm.const_set("#{MOD}#{name}", @imports[name]
|
48
|
+
@pm.const_set("#{MOD}#{name}", @imports[name].pm)
|
48
49
|
end
|
49
50
|
|
50
|
-
def gen_import(name
|
51
|
-
@imports.merge!(@imports[name]
|
51
|
+
def gen_import(name)
|
52
|
+
@imports.merge!(@imports[name].imports)
|
52
53
|
|
53
|
-
@m.const_set("#{MOD}#{name}", @imports[name]
|
54
|
+
@m.const_set("#{MOD}#{name}", @imports[name].m)
|
54
55
|
end
|
55
56
|
|
56
57
|
def get_import_engine(name)
|
57
58
|
err(ParseError, "#{name} not imported") unless @imports[name]
|
58
|
-
@imports[name]
|
59
|
+
@imports[name]
|
59
60
|
end
|
60
61
|
|
61
62
|
def is_node_defined(name)
|
@@ -212,8 +213,8 @@ module Delorean
|
|
212
213
|
@@parser ||= DeloreanParser.new
|
213
214
|
end
|
214
215
|
|
215
|
-
def generate(t
|
216
|
-
t.check(self
|
216
|
+
def generate(t)
|
217
|
+
t.check(self)
|
217
218
|
|
218
219
|
begin
|
219
220
|
# generate ruby code
|
@@ -233,7 +234,7 @@ module Delorean
|
|
233
234
|
end
|
234
235
|
end
|
235
236
|
|
236
|
-
def parse(source
|
237
|
+
def parse(source)
|
237
238
|
raise "can't call parse again without reset" if @pm
|
238
239
|
|
239
240
|
# @m module is used at runtime for code evaluation. @pm module
|
@@ -263,7 +264,7 @@ module Delorean
|
|
263
264
|
|
264
265
|
if t
|
265
266
|
multi_line, @multi_no = nil, nil
|
266
|
-
generate(t
|
267
|
+
generate(t)
|
267
268
|
end
|
268
269
|
|
269
270
|
else
|
@@ -275,7 +276,7 @@ module Delorean
|
|
275
276
|
multi_line = line
|
276
277
|
@multi_no = @line_no
|
277
278
|
else
|
278
|
-
generate(t
|
279
|
+
generate(t)
|
279
280
|
end
|
280
281
|
end
|
281
282
|
end
|
@@ -295,9 +296,8 @@ module Delorean
|
|
295
296
|
|
296
297
|
# enumerate qualified list of all attrs
|
297
298
|
def enumerate_attrs
|
298
|
-
@node_attrs.keys.
|
299
|
+
@node_attrs.keys.each_with_object({}) { |node, h|
|
299
300
|
h[node] = enumerate_attrs_by_node(node)
|
300
|
-
h
|
301
301
|
}
|
302
302
|
end
|
303
303
|
|
data/lib/delorean/nodes.rb
CHANGED
@@ -52,12 +52,12 @@ eos
|
|
52
52
|
end
|
53
53
|
|
54
54
|
class Import < SNode
|
55
|
-
def check(context
|
56
|
-
context.parse_import(
|
55
|
+
def check(context)
|
56
|
+
context.parse_import(n.text_value)
|
57
57
|
end
|
58
58
|
|
59
59
|
def rewrite(context)
|
60
|
-
context.gen_import(n.text_value
|
60
|
+
context.gen_import(n.text_value)
|
61
61
|
""
|
62
62
|
end
|
63
63
|
end
|
data/lib/delorean/version.rb
CHANGED
data/spec/eval_spec.rb
CHANGED
@@ -2,13 +2,9 @@ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
|
|
2
2
|
|
3
3
|
describe "Delorean" do
|
4
4
|
|
5
|
-
let(:engine) {
|
6
|
-
Delorean::Engine.new "XXX"
|
7
|
-
}
|
8
|
-
|
9
5
|
let(:sset) {
|
10
6
|
TestContainer.new({
|
11
|
-
|
7
|
+
"AAA" =>
|
12
8
|
defn("X:",
|
13
9
|
" a =? 123",
|
14
10
|
" b = a*2",
|
@@ -16,6 +12,10 @@ describe "Delorean" do
|
|
16
12
|
})
|
17
13
|
}
|
18
14
|
|
15
|
+
let(:engine) {
|
16
|
+
Delorean::Engine.new "XXX", sset
|
17
|
+
}
|
18
|
+
|
19
19
|
it "evaluate simple expressions" do
|
20
20
|
engine.parse defn("A:",
|
21
21
|
" a = 123",
|
@@ -308,7 +308,7 @@ eoc
|
|
308
308
|
engine.evaluate("E", "xx").should == [1,2,3]
|
309
309
|
end
|
310
310
|
|
311
|
-
it "should be able to call class methods on
|
311
|
+
it "should be able to call class methods on AR classes in modules" do
|
312
312
|
engine.parse defn("A:",
|
313
313
|
" b = M::LittleDummy.heres_my_number(867, 5309)",
|
314
314
|
)
|
@@ -433,7 +433,8 @@ eof
|
|
433
433
|
engin2.evaluate_attrs("A", ["a", "b"]).should == [222.0, 222.0/5]
|
434
434
|
|
435
435
|
engine.evaluate_attrs("B", ["a", "b", "c"]).should == [123, 123*3, 123*3*2]
|
436
|
-
engin2.evaluate_attrs("B", ["a", "b", "c"]).should ==
|
436
|
+
engin2.evaluate_attrs("B", ["a", "b", "c"]).should ==
|
437
|
+
[222.0, 222.0/5, 222.0/5*3]
|
437
438
|
|
438
439
|
engin2.evaluate("C", "d").should == 111
|
439
440
|
lambda {
|
@@ -662,29 +663,29 @@ eof
|
|
662
663
|
end
|
663
664
|
|
664
665
|
it "should eval imports" do
|
665
|
-
engine.parse defn("import AAA
|
666
|
+
engine.parse defn("import AAA",
|
666
667
|
"A:",
|
667
668
|
" b = 456",
|
668
669
|
"B: AAA::X",
|
669
670
|
" a = 111",
|
670
671
|
" c = AAA::X(a: 456).b",
|
671
|
-
)
|
672
|
+
)
|
672
673
|
engine.evaluate_attrs("B", ["a", "b", "c"], {}).should ==
|
673
674
|
[111, 222, 456*2]
|
674
675
|
end
|
675
676
|
|
676
677
|
it "should eval imports (2)" do
|
677
678
|
sset.merge({
|
678
|
-
|
679
|
-
defn("import AAA
|
679
|
+
"BBB" =>
|
680
|
+
defn("import AAA",
|
680
681
|
"B: AAA::X",
|
681
682
|
" a = 111",
|
682
683
|
" c = AAA::X(a: -1).b",
|
683
684
|
" d = a * 2",
|
684
685
|
),
|
685
|
-
|
686
|
-
defn("import BBB
|
687
|
-
"import AAA
|
686
|
+
"CCC" =>
|
687
|
+
defn("import BBB",
|
688
|
+
"import AAA",
|
688
689
|
"B: BBB::B",
|
689
690
|
" e = d * 3",
|
690
691
|
"C: AAA::X",
|
@@ -692,20 +693,20 @@ eof
|
|
692
693
|
),
|
693
694
|
})
|
694
695
|
|
695
|
-
e2 = sset.get_engine("BBB"
|
696
|
+
e2 = sset.get_engine("BBB")
|
696
697
|
|
697
698
|
e2.evaluate_attrs("B", ["a", "b", "c", "d"]).should ==
|
698
699
|
[111, 222, -2, 222]
|
699
700
|
|
700
|
-
engine.parse defn("import BBB
|
701
|
+
engine.parse defn("import BBB",
|
701
702
|
"B: BBB::B",
|
702
703
|
" e = d + 3",
|
703
|
-
)
|
704
|
+
)
|
704
705
|
|
705
706
|
engine.evaluate_attrs("B", ["a", "b", "c", "d", "e"]).should ==
|
706
707
|
[111, 222, -2, 222, 225]
|
707
708
|
|
708
|
-
e4 = sset.get_engine("CCC"
|
709
|
+
e4 = sset.get_engine("CCC")
|
709
710
|
|
710
711
|
e4.evaluate_attrs("B", ["a", "b", "c", "d", "e"]).should ==
|
711
712
|
[111, 222, -2, 222, 666]
|
@@ -715,16 +716,16 @@ eof
|
|
715
716
|
|
716
717
|
it "should eval imports (3)" do
|
717
718
|
sset.merge({
|
718
|
-
|
719
|
-
|
720
|
-
defn("import BBB
|
719
|
+
"BBB" => getattr_code,
|
720
|
+
"CCC" =>
|
721
|
+
defn("import BBB",
|
721
722
|
"X:",
|
722
723
|
" xx = [n.x for n in BBB::D().xs]",
|
723
724
|
" yy = [n.x for n in BBB::D.xs]",
|
724
725
|
),
|
725
726
|
})
|
726
727
|
|
727
|
-
e4 = sset.get_engine("CCC"
|
728
|
+
e4 = sset.get_engine("CCC")
|
728
729
|
e4.evaluate("X", "xx").should == [1,2,3]
|
729
730
|
e4.evaluate("X", "yy").should == [1,2,3]
|
730
731
|
end
|
@@ -750,7 +751,8 @@ eof
|
|
750
751
|
" d = c['b'].x * c['a'] - c['b'].y",
|
751
752
|
)
|
752
753
|
r = engine.evaluate_attrs("A", ["a", "b", "c", "d"])
|
753
|
-
r.should ==
|
754
|
+
r.should ==
|
755
|
+
[1, {"x"=>123, "y"=>456}, {"a"=>1, "b"=>{"x"=>123, "y"=>456}}, -333]
|
754
756
|
end
|
755
757
|
|
756
758
|
it "should properly eval overridden attrs" do
|
data/spec/parse_spec.rb
CHANGED
@@ -2,13 +2,9 @@ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
|
|
2
2
|
|
3
3
|
describe "Delorean" do
|
4
4
|
|
5
|
-
let(:engine) {
|
6
|
-
Delorean::Engine.new "YYY"
|
7
|
-
}
|
8
|
-
|
9
5
|
let(:sset) {
|
10
6
|
TestContainer.new({
|
11
|
-
|
7
|
+
"AAA" =>
|
12
8
|
defn("X:",
|
13
9
|
" a = 123",
|
14
10
|
" b = a",
|
@@ -16,6 +12,10 @@ describe "Delorean" do
|
|
16
12
|
})
|
17
13
|
}
|
18
14
|
|
15
|
+
let(:engine) {
|
16
|
+
Delorean::Engine.new "YYY", sset
|
17
|
+
}
|
18
|
+
|
19
19
|
it "can parse very simple calls" do
|
20
20
|
engine.parse defn("X:",
|
21
21
|
" a = 123",
|
@@ -702,71 +702,25 @@ describe "Delorean" do
|
|
702
702
|
end
|
703
703
|
|
704
704
|
it "should parse imports" do
|
705
|
-
engine.parse defn("import AAA
|
705
|
+
engine.parse defn("import AAA",
|
706
706
|
"A:",
|
707
707
|
" b = 456",
|
708
708
|
"B: AAA::X",
|
709
|
-
)
|
710
|
-
|
709
|
+
)
|
711
710
|
end
|
712
711
|
|
713
712
|
it "should disallow import loops" do
|
714
713
|
pending
|
715
714
|
sset.merge({
|
716
|
-
|
717
|
-
defn("import AAA
|
718
|
-
"import CCC
|
715
|
+
"BBB" =>
|
716
|
+
defn("import AAA",
|
717
|
+
"import CCC",
|
719
718
|
),
|
720
|
-
|
721
|
-
defn("import BBB
|
719
|
+
"CCC" =>
|
720
|
+
defn("import BBB",
|
722
721
|
),
|
723
722
|
})
|
724
|
-
sset.get_engine("CCC"
|
725
|
-
end
|
726
|
-
|
727
|
-
it "should disallow multiple versions of same script" do
|
728
|
-
sset.merge({
|
729
|
-
["AAA", "0002"] =>
|
730
|
-
defn("A:",
|
731
|
-
),
|
732
|
-
["BBB", "0001"] =>
|
733
|
-
defn("import AAA 0001",
|
734
|
-
),
|
735
|
-
["CCC", "0001"] =>
|
736
|
-
defn("import BBB 0001",
|
737
|
-
"import AAA 0002",
|
738
|
-
),
|
739
|
-
})
|
740
|
-
begin
|
741
|
-
sset.get_engine("CCC", "0001")
|
742
|
-
rescue Delorean::ImportError => exc
|
743
|
-
exc.line.should == 2
|
744
|
-
end
|
745
|
-
end
|
746
|
-
|
747
|
-
it "should disallow multiple versions of same script (2)" do
|
748
|
-
sset.merge({
|
749
|
-
["BBB", "0001"] =>
|
750
|
-
defn("import AAA 0001",
|
751
|
-
),
|
752
|
-
["CCC", "0001"] =>
|
753
|
-
defn("import AAA 0001",
|
754
|
-
"import BBB 0001",
|
755
|
-
),
|
756
|
-
["AAA", "0002"] =>
|
757
|
-
defn("A:",
|
758
|
-
),
|
759
|
-
["CCC", "0002"] =>
|
760
|
-
defn("import AAA 0002",
|
761
|
-
"import BBB 0001",
|
762
|
-
),
|
763
|
-
})
|
764
|
-
begin
|
765
|
-
sset.get_engine("CCC", "0002")
|
766
|
-
rescue Delorean::ImportError => exc
|
767
|
-
exc.line.should == 2
|
768
|
-
end
|
723
|
+
sset.get_engine("CCC")
|
769
724
|
end
|
770
725
|
|
771
726
|
end
|
772
|
-
|
data/spec/spec_helper.rb
CHANGED
@@ -10,7 +10,7 @@ require 'active_record'
|
|
10
10
|
Dir["#{File.dirname(__FILE__)}/support/**/*.rb"].each {|f| require f}
|
11
11
|
|
12
12
|
RSpec.configure do |config|
|
13
|
-
|
13
|
+
|
14
14
|
end
|
15
15
|
|
16
16
|
def defn(*l)
|
@@ -18,7 +18,7 @@ def defn(*l)
|
|
18
18
|
end
|
19
19
|
|
20
20
|
######################################################################
|
21
|
-
# ActiveRecord related
|
21
|
+
# ActiveRecord related
|
22
22
|
|
23
23
|
ActiveRecord::Base.establish_connection adapter: "sqlite3", database: ":memory:"
|
24
24
|
|
@@ -79,22 +79,24 @@ class TestContainer < Delorean::AbstractContainer
|
|
79
79
|
def initialize(scripts={})
|
80
80
|
super()
|
81
81
|
@scripts = scripts
|
82
|
+
@engines = {}
|
82
83
|
end
|
83
84
|
|
84
85
|
def merge(scripts)
|
85
86
|
@scripts.merge!(scripts)
|
86
87
|
end
|
87
88
|
|
88
|
-
def get_engine(name
|
89
|
-
|
89
|
+
def get_engine(name)
|
90
|
+
return @engines[name] if @engines[name]
|
91
|
+
|
92
|
+
script = @scripts[name]
|
90
93
|
|
91
|
-
raise "can't find #{name}
|
94
|
+
raise "can't find #{name}" unless script
|
92
95
|
|
93
|
-
engine = Delorean::Engine.new name
|
94
|
-
engine.parse script
|
96
|
+
engine = Delorean::Engine.new name, self
|
97
|
+
engine.parse script
|
95
98
|
engine
|
96
99
|
end
|
97
100
|
end
|
98
101
|
|
99
102
|
######################################################################
|
100
|
-
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: delorean_lang
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Arman Bostani
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2014-
|
11
|
+
date: 2014-03-05 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: treetop
|