ducktrap 0.0.1
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 +7 -0
- data/.circle.yml +6 -0
- data/.gitignore +5 -0
- data/.rspec +1 -0
- data/.travis.yml +16 -0
- data/Gemfile +6 -0
- data/Gemfile.devtools +59 -0
- data/Guardfile +18 -0
- data/LICENSE +20 -0
- data/README.md +47 -0
- data/Rakefile +2 -0
- data/TODO +4 -0
- data/config/devtools.yml +2 -0
- data/config/flay.yml +3 -0
- data/config/flog.yml +2 -0
- data/config/heckle.yml +3 -0
- data/config/mutant.yml +2 -0
- data/config/reek.yml +98 -0
- data/config/yardstick.yml +2 -0
- data/ducktrap.gemspec +23 -0
- data/lib/ducktrap.rb +73 -0
- data/lib/ducktrap/builder.rb +36 -0
- data/lib/ducktrap/error.rb +48 -0
- data/lib/ducktrap/evaluator.rb +127 -0
- data/lib/ducktrap/evaluator/invalid.rb +30 -0
- data/lib/ducktrap/evaluator/static.rb +25 -0
- data/lib/ducktrap/formatter.rb +138 -0
- data/lib/ducktrap/mapper.rb +59 -0
- data/lib/ducktrap/nary.rb +148 -0
- data/lib/ducktrap/node.rb +94 -0
- data/lib/ducktrap/node/anima.rb +40 -0
- data/lib/ducktrap/node/anima/dump.rb +39 -0
- data/lib/ducktrap/node/anima/load.rb +39 -0
- data/lib/ducktrap/node/block.rb +44 -0
- data/lib/ducktrap/node/coercion.rb +7 -0
- data/lib/ducktrap/node/custom.rb +121 -0
- data/lib/ducktrap/node/disjunction.rb +8 -0
- data/lib/ducktrap/node/forward.rb +55 -0
- data/lib/ducktrap/node/guard_nil.rb +42 -0
- data/lib/ducktrap/node/hash.rb +7 -0
- data/lib/ducktrap/node/hash/transform.rb +53 -0
- data/lib/ducktrap/node/invalid.rb +29 -0
- data/lib/ducktrap/node/inverse.rb +46 -0
- data/lib/ducktrap/node/key.rb +61 -0
- data/lib/ducktrap/node/key/add.rb +42 -0
- data/lib/ducktrap/node/key/delete.rb +44 -0
- data/lib/ducktrap/node/key/dump.rb +38 -0
- data/lib/ducktrap/node/key/fetch.rb +49 -0
- data/lib/ducktrap/node/map.rb +42 -0
- data/lib/ducktrap/node/noop.rb +30 -0
- data/lib/ducktrap/node/primitive.rb +61 -0
- data/lib/ducktrap/node/static.rb +33 -0
- data/lib/ducktrap/nullary.rb +41 -0
- data/lib/ducktrap/pretty_dump.rb +31 -0
- data/lib/ducktrap/registry.rb +60 -0
- data/lib/ducktrap/singleton.rb +55 -0
- data/lib/ducktrap/unary.rb +153 -0
- data/spec/rcov.opts +7 -0
- data/spec/shared/inverse_behavior.rb +7 -0
- data/spec/spec_helper.rb +20 -0
- data/spec/support/ice_nine_config.rb +8 -0
- data/spec/support/let_mock_helper.rb +13 -0
- data/spec/unit/ducktrap/builder/class_methods/new_spec.rb +41 -0
- data/spec/unit/ducktrap/builder/new_spec.rb +41 -0
- data/spec/unit/ducktrap/class_methods/build_spec.rb +11 -0
- data/spec/unit/ducktrap/error/exception/pretty_inspect_spec.rb +22 -0
- data/spec/unit/ducktrap/error/pretty_inspect_spec.rb +19 -0
- data/spec/unit/ducktrap/evaluator/assert_successful_spec.rb +38 -0
- data/spec/unit/ducktrap/evaluator/invalid/output_spec.rb +14 -0
- data/spec/unit/ducktrap/evaluator/noop/output_spec.rb +14 -0
- data/spec/unit/ducktrap/evaluator/output_spec.rb +52 -0
- data/spec/unit/ducktrap/evaluator/pretty_inspect_spec.rb +63 -0
- data/spec/unit/ducktrap/evaluator/successful_predicate_spec.rb +36 -0
- data/spec/unit/ducktrap/failed_transformation_error/message_spec.rb +10 -0
- data/spec/unit/ducktrap/formatter/attribute_spec.rb +24 -0
- data/spec/unit/ducktrap/formatter/body_spec.rb +19 -0
- data/spec/unit/ducktrap/formatter/class_methods/new_spec.rb +14 -0
- data/spec/unit/ducktrap/formatter/initialize_spec.rb +14 -0
- data/spec/unit/ducktrap/formatter/name_spec.rb +25 -0
- data/spec/unit/ducktrap/formatter/nest_spec.rb +48 -0
- data/spec/unit/ducktrap/formatter/puts_spec.rb +36 -0
- data/spec/unit/ducktrap/mapper/builder/dumper_spec.rb +20 -0
- data/spec/unit/ducktrap/mapper/builder/loader_spec.rb +20 -0
- data/spec/unit/ducktrap/mapper/builder/object_spec.rb +90 -0
- data/spec/unit/ducktrap/mapper/class_methods/build_spec.rb +20 -0
- data/spec/unit/ducktrap/nary/builder/add_spec.rb +16 -0
- data/spec/unit/ducktrap/nary/builder/method_missing_spec.rb +44 -0
- data/spec/unit/ducktrap/nary/builder/output_spec.rb +16 -0
- data/spec/unit/ducktrap/nary/class_methods/build_spec.rb +22 -0
- data/spec/unit/ducktrap/nary/class_methods/included_spec.rb +13 -0
- data/spec/unit/ducktrap/nary/evaluator/output_spec.rb +79 -0
- data/spec/unit/ducktrap/nary/instance_methods/inverse_spec.rb +24 -0
- data/spec/unit/ducktrap/nary/instance_methods/pretty_inspect_spec.rb +31 -0
- data/spec/unit/ducktrap/node/anima/dump/evaluator/output_spec.rb +18 -0
- data/spec/unit/ducktrap/node/anima/dump/inverse_spec.rb +10 -0
- data/spec/unit/ducktrap/node/anima/dump/pretty_inspect_spec.rb +15 -0
- data/spec/unit/ducktrap/node/anima/evaluator/output_spec.rb +18 -0
- data/spec/unit/ducktrap/node/anima/load/evaluator/output_spec.rb +35 -0
- data/spec/unit/ducktrap/node/anima/load/inverse_spec.rb +10 -0
- data/spec/unit/ducktrap/node/anima/load/pretty_inspect_spec.rb +15 -0
- data/spec/unit/ducktrap/node/anima/pretty_inspect_spec.rb +15 -0
- data/spec/unit/ducktrap/node/block/evaluator/output_spec.rb +79 -0
- data/spec/unit/ducktrap/node/block/inverse_spec.rb +24 -0
- data/spec/unit/ducktrap/node/call_spec.rb +21 -0
- data/spec/unit/ducktrap/node/class_methods/build_spec.rb +11 -0
- data/spec/unit/ducktrap/node/class_methods/register_spec.rb +16 -0
- data/spec/unit/ducktrap/node/custom/builder/forward_spec.rb +54 -0
- data/spec/unit/ducktrap/node/custom/builder/inverse_spec.rb +54 -0
- data/spec/unit/ducktrap/node/custom/builder/object_spec.rb +54 -0
- data/spec/unit/ducktrap/node/custom/call_spec.rb +21 -0
- data/spec/unit/ducktrap/node/custom/class_methods/build_spec.rb +20 -0
- data/spec/unit/ducktrap/node/custom/inverse_spec.rb +12 -0
- data/spec/unit/ducktrap/node/custom/pretty_inspect_spec.rb +15 -0
- data/spec/unit/ducktrap/node/forward/evaluator/output_spec.rb +13 -0
- data/spec/unit/ducktrap/node/forward/inverse_spec.rb +14 -0
- data/spec/unit/ducktrap/node/forward/pretty_inspect_spec.rb +19 -0
- data/spec/unit/ducktrap/node/guard_nil/call_spec.rb +21 -0
- data/spec/unit/ducktrap/node/guard_nil/evaluator/output_spec.rb +27 -0
- data/spec/unit/ducktrap/node/guard_nil/inverse_spec.rb +12 -0
- data/spec/unit/ducktrap/node/hash/transform/evaluator/output_spec.rb +51 -0
- data/spec/unit/ducktrap/node/hash/transform/inverse_spec.rb +27 -0
- data/spec/unit/ducktrap/node/invalid/call_spec.rb +13 -0
- data/spec/unit/ducktrap/node/invalid/inverse_spec.rb +11 -0
- data/spec/unit/ducktrap/node/inverse/call_spec.rb +11 -0
- data/spec/unit/ducktrap/node/inverse/inverse_spec.rb +14 -0
- data/spec/unit/ducktrap/node/inverse/pretty_inspect_spec.rb +19 -0
- data/spec/unit/ducktrap/node/key/add/call_spec.rb +15 -0
- data/spec/unit/ducktrap/node/key/add/evaluator/call_spec.rb +15 -0
- data/spec/unit/ducktrap/node/key/add/inverse_spec.rb +14 -0
- data/spec/unit/ducktrap/node/key/delete/call_spec.rb +13 -0
- data/spec/unit/ducktrap/node/key/delete/evaluator/call_spec.rb +13 -0
- data/spec/unit/ducktrap/node/key/delete/inverse_spec.rb +13 -0
- data/spec/unit/ducktrap/node/key/dump/evaluator/output_spec.rb +37 -0
- data/spec/unit/ducktrap/node/key/dump/inverse_spec.rb +14 -0
- data/spec/unit/ducktrap/node/key/evaluator/key_spec.rb +26 -0
- data/spec/unit/ducktrap/node/key/fetch/evaluator/output_spec.rb +48 -0
- data/spec/unit/ducktrap/node/key/fetch/inverse_spec.rb +14 -0
- data/spec/unit/ducktrap/node/key/pretty_inspect_spec.rb +20 -0
- data/spec/unit/ducktrap/node/map/evaluator/output_spec.rb +22 -0
- data/spec/unit/ducktrap/node/map/inverse_spec.rb +15 -0
- data/spec/unit/ducktrap/node/noop/call_spec.rb +11 -0
- data/spec/unit/ducktrap/node/noop/inverse_spec.rb +9 -0
- data/spec/unit/ducktrap/node/pretty_inspect_spec.rb +17 -0
- data/spec/unit/ducktrap/node/primitive/call_spec.rb +19 -0
- data/spec/unit/ducktrap/node/primitive/inverse_spec.rb +13 -0
- data/spec/unit/ducktrap/node/primitive/pretty_inspect_spec.rb +15 -0
- data/spec/unit/ducktrap/node/run_spec.rb +46 -0
- data/spec/unit/ducktrap/node/static/call_spec.rb +13 -0
- data/spec/unit/ducktrap/node/static/inverse_spec.rb +14 -0
- data/spec/unit/ducktrap/nullary/class_methods/build_spec.rb +37 -0
- data/spec/unit/ducktrap/nullary/class_methods/included_spec.rb +7 -0
- data/spec/unit/ducktrap/pretty_dump/pretty_dump_spec.rb +47 -0
- data/spec/unit/ducktrap/pretty_dump/pretty_inspect_spec.rb +22 -0
- data/spec/unit/ducktrap/registry/lookup_spec.rb +27 -0
- data/spec/unit/ducktrap/registry/register_spec.rb +21 -0
- data/spec/unit/ducktrap/singleton/class_methods/included_spec.rb +13 -0
- data/spec/unit/ducktrap/singleton/class_methods/instance_spec.rb +19 -0
- data/spec/unit/ducktrap/singleton/instance_methods/inspect_spec.rb +19 -0
- data/spec/unit/ducktrap/singleton/instance_methods/pretty_inspect_spec.rb +17 -0
- data/spec/unit/ducktrap/unary/class_methods/build_spec.rb +18 -0
- data/spec/unit/ducktrap/unary/class_methods/included_spec.rb +14 -0
- data/spec/unit/ducktrap/unary/evaluator/output2_spec.rb +48 -0
- data/spec/unit/ducktrap/unary/evaluator/output_spec.rb +37 -0
- data/spec/unit/ducktrap/unary/instance_methods/pretty_inspect_spec.rb +15 -0
- metadata +399 -0
@@ -0,0 +1,19 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Formatter, '#body' do
|
4
|
+
let(:object) { described_class.new(output) }
|
5
|
+
|
6
|
+
let(:output) { StringIO.new }
|
7
|
+
|
8
|
+
subject { object.body(node) }
|
9
|
+
|
10
|
+
let(:node) { [Ducktrap::Node::Noop.instance, Ducktrap::Node::Noop.instance] }
|
11
|
+
|
12
|
+
it 'should print node with members' do
|
13
|
+
subject
|
14
|
+
output.rewind
|
15
|
+
output.read.should eql(" body:\n Ducktrap::Node::Noop\n Ducktrap::Node::Noop\n")
|
16
|
+
end
|
17
|
+
|
18
|
+
it_should_behave_like 'a command method'
|
19
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Formatter, '.new' do
|
4
|
+
subject { object.new(*arguments) }
|
5
|
+
let(:object) { described_class }
|
6
|
+
|
7
|
+
context 'with defaults' do
|
8
|
+
let(:arguments) { [] }
|
9
|
+
it 'should write to stderr' do
|
10
|
+
$stderr.should_receive(:puts).with('Class').and_return($stderr)
|
11
|
+
subject.name(described_class)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Formatter, '.new' do
|
4
|
+
subject { object.new(*arguments) }
|
5
|
+
let(:object) { described_class }
|
6
|
+
|
7
|
+
context 'with defaults' do
|
8
|
+
let(:arguments) { [] }
|
9
|
+
it 'should write to stderr' do
|
10
|
+
$stderr.should_receive(:puts).with('Class').and_return($stderr)
|
11
|
+
subject.name(described_class)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Formatter, '#name' do
|
4
|
+
subject { object.name(target) }
|
5
|
+
|
6
|
+
let(:object) { described_class.new(io) }
|
7
|
+
let(:io) { StringIO.new }
|
8
|
+
|
9
|
+
def output
|
10
|
+
io.rewind
|
11
|
+
io.read
|
12
|
+
end
|
13
|
+
|
14
|
+
before { subject }
|
15
|
+
|
16
|
+
let(:target) do
|
17
|
+
mock(:class => mock(:name => 'Target'))
|
18
|
+
end
|
19
|
+
|
20
|
+
it 'should print name of targets class' do
|
21
|
+
output.should eql("Target\n")
|
22
|
+
end
|
23
|
+
|
24
|
+
it_should_behave_like 'a command method'
|
25
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Formatter, '#nest' do
|
4
|
+
subject { object.nest(label, nested) }
|
5
|
+
|
6
|
+
let(:label) { 'the-label' }
|
7
|
+
let(:nested) { mock }
|
8
|
+
|
9
|
+
let(:object) { described_class.new(io) }
|
10
|
+
let(:io) { StringIO.new }
|
11
|
+
|
12
|
+
before do
|
13
|
+
nested.should_receive(:pretty_dump).with(indented).and_return(nested)
|
14
|
+
end
|
15
|
+
|
16
|
+
def output
|
17
|
+
io.rewind
|
18
|
+
io.read
|
19
|
+
end
|
20
|
+
|
21
|
+
let(:string) { 'the-string' }
|
22
|
+
|
23
|
+
before { subject }
|
24
|
+
|
25
|
+
let(:indented) do
|
26
|
+
object.indent.indent
|
27
|
+
end
|
28
|
+
|
29
|
+
context 'unindented' do
|
30
|
+
it 'should write the string to io' do
|
31
|
+
output.should eql(" the-label:\n")
|
32
|
+
end
|
33
|
+
|
34
|
+
it_should_behave_like 'a command method'
|
35
|
+
end
|
36
|
+
|
37
|
+
context 'indented' do
|
38
|
+
|
39
|
+
let(:object) { super().indent }
|
40
|
+
|
41
|
+
it 'should write the indeted string to io' do
|
42
|
+
output.should eql(" the-label:\n")
|
43
|
+
end
|
44
|
+
|
45
|
+
it_should_behave_like 'a command method'
|
46
|
+
end
|
47
|
+
|
48
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Formatter, '#puts' do
|
4
|
+
subject { object.puts(string) }
|
5
|
+
|
6
|
+
let(:object) { described_class.new(io) }
|
7
|
+
let(:io) { StringIO.new }
|
8
|
+
|
9
|
+
def output
|
10
|
+
io.rewind
|
11
|
+
io.read
|
12
|
+
end
|
13
|
+
|
14
|
+
let(:string) { 'the-string' }
|
15
|
+
|
16
|
+
before { subject }
|
17
|
+
|
18
|
+
context 'unindented' do
|
19
|
+
it 'should write the string to io' do
|
20
|
+
output.should eql("the-string\n")
|
21
|
+
end
|
22
|
+
|
23
|
+
it_should_behave_like 'a command method'
|
24
|
+
end
|
25
|
+
|
26
|
+
context 'indented' do
|
27
|
+
let(:object) { super().indent }
|
28
|
+
|
29
|
+
it 'should write the indeted string to io' do
|
30
|
+
output.should eql(" the-string\n")
|
31
|
+
end
|
32
|
+
|
33
|
+
it_should_behave_like 'a command method'
|
34
|
+
end
|
35
|
+
|
36
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Mapper::Builder, '#dumper' do
|
4
|
+
subject do
|
5
|
+
block = self.block
|
6
|
+
described_class.new(Ducktrap::Mapper) do |mapper|
|
7
|
+
mapper.dumper(&block).should be(mapper)
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
let(:block) { dumper = self.dumper; proc { add(dumper) } }
|
12
|
+
let(:dumper) { mock('Dumper', :inverse => loader, :frozen? => true) }
|
13
|
+
let(:loader) { mock('Loader') }
|
14
|
+
|
15
|
+
its(:object) do
|
16
|
+
loader = Ducktrap::Node::Block.new([self.loader])
|
17
|
+
dumper = Ducktrap::Node::Block.new([self.dumper])
|
18
|
+
should eql(Ducktrap::Mapper.new(loader, dumper))
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Mapper::Builder, '#loader' do
|
4
|
+
subject do
|
5
|
+
block = self.block
|
6
|
+
described_class.new(Ducktrap::Mapper) do |mapper|
|
7
|
+
mapper.loader(&block).should be(mapper)
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
let(:block) { loader = self.loader; proc { add(loader) } }
|
12
|
+
let(:loader) { mock('Loader', :inverse => dumper, :frozen? => true) }
|
13
|
+
let(:dumper) { mock('Dumper') }
|
14
|
+
|
15
|
+
its(:object) do
|
16
|
+
loader = Ducktrap::Node::Block.new([self.loader])
|
17
|
+
dumper = Ducktrap::Node::Block.new([self.dumper])
|
18
|
+
should eql(Ducktrap::Mapper.new(loader, dumper))
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,90 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Mapper::Builder, '#object' do
|
4
|
+
let(:object) do
|
5
|
+
described_class.new(Ducktrap::Mapper, &block)
|
6
|
+
end
|
7
|
+
|
8
|
+
subject { object.object }
|
9
|
+
|
10
|
+
let(:loader) { mock('Loader', :frozen? => true) }
|
11
|
+
let(:dumper) { mock('Dumper', :frozen? => true) }
|
12
|
+
|
13
|
+
context 'with loader' do
|
14
|
+
let(:block) do
|
15
|
+
node = self.loader
|
16
|
+
proc do
|
17
|
+
loader do
|
18
|
+
add(node)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
before do
|
24
|
+
loader.stub(:inverse => dumper)
|
25
|
+
end
|
26
|
+
|
27
|
+
specify do
|
28
|
+
loader = Ducktrap::Node::Block.new([self.loader])
|
29
|
+
dumper = Ducktrap::Node::Block.new([self.dumper])
|
30
|
+
should eql(Ducktrap::Mapper.new(loader, dumper))
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
context 'with dumper' do
|
35
|
+
let(:block) do
|
36
|
+
node = self.dumper
|
37
|
+
proc do
|
38
|
+
dumper do
|
39
|
+
add(node)
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
before do
|
45
|
+
dumper.stub(:inverse => loader)
|
46
|
+
end
|
47
|
+
|
48
|
+
specify do
|
49
|
+
loader = Ducktrap::Node::Block.new([self.loader])
|
50
|
+
dumper = Ducktrap::Node::Block.new([self.dumper])
|
51
|
+
should eql(Ducktrap::Mapper.new(loader, dumper))
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
context 'with loader and dumper' do
|
56
|
+
let(:block) do
|
57
|
+
dumper = self.dumper
|
58
|
+
loader = self.loader
|
59
|
+
proc do
|
60
|
+
dumper do
|
61
|
+
add(dumper)
|
62
|
+
end
|
63
|
+
|
64
|
+
loader do
|
65
|
+
add(loader)
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
70
|
+
before do
|
71
|
+
dumper.stub(:inverse => loader)
|
72
|
+
loader.stub(:inverse => dumper)
|
73
|
+
end
|
74
|
+
|
75
|
+
specify do
|
76
|
+
loader = Ducktrap::Node::Block.new([self.loader])
|
77
|
+
dumper = Ducktrap::Node::Block.new([self.dumper])
|
78
|
+
should eql(Ducktrap::Mapper.new(loader, dumper))
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
context 'without loader or dumper' do
|
83
|
+
let(:block) do
|
84
|
+
end
|
85
|
+
|
86
|
+
it 'should raise error' do
|
87
|
+
expect { subject }.to raise_error(RuntimeError, 'Did not specify loader or dumper or both')
|
88
|
+
end
|
89
|
+
end
|
90
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Mapper do
|
4
|
+
|
5
|
+
let(:object) { described_class }
|
6
|
+
|
7
|
+
subject { described_class.build(&block) }
|
8
|
+
|
9
|
+
let(:block) { proc {} }
|
10
|
+
let(:builder) { mock('Builder', :object => mapper) }
|
11
|
+
let(:mapper) { mock('Mapper') }
|
12
|
+
|
13
|
+
it 'should call Ducktrap::Mapper::Builder' do
|
14
|
+
Ducktrap::Mapper::Builder.should_receive(:new).with(described_class) do |&block|
|
15
|
+
block.should be(self.block)
|
16
|
+
builder
|
17
|
+
end
|
18
|
+
subject.should be(mapper)
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Nary::Builder, '#add' do
|
4
|
+
let(:object) { described_class.new(klass) }
|
5
|
+
let(:klass) { Ducktrap::Node::Block }
|
6
|
+
|
7
|
+
let(:node) { Ducktrap::Node::Noop.instance }
|
8
|
+
|
9
|
+
subject { object.add(node) }
|
10
|
+
|
11
|
+
it 'should add node to body' do
|
12
|
+
expect { subject }.to change { object.body }.from([]).to([node])
|
13
|
+
end
|
14
|
+
|
15
|
+
it_should_behave_like 'a command method'
|
16
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Nary::Builder, '#method_missing' do
|
4
|
+
let(:object) { described_class.new(klass) }
|
5
|
+
let(:klass) { Ducktrap::Node::Block }
|
6
|
+
|
7
|
+
context 'known nullary DSL method' do
|
8
|
+
subject { object.noop }
|
9
|
+
it 'should add node to body' do
|
10
|
+
node = Ducktrap::Node::Noop.instance
|
11
|
+
expect { subject }.to change { object.body }.from([]).to([node])
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
context 'known unary DSL method' do
|
16
|
+
subject { object.guard_nil { noop } }
|
17
|
+
it 'should add node to body' do
|
18
|
+
node = Ducktrap::Node::GuardNil.new(
|
19
|
+
Ducktrap::Node::Block.new(
|
20
|
+
[Ducktrap::Node::Noop.instance]
|
21
|
+
)
|
22
|
+
)
|
23
|
+
expect { subject }.to change { object.body }.from([]).to([node])
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
context 'unknown DSL method' do
|
28
|
+
subject { object.unknown }
|
29
|
+
|
30
|
+
it 'should raise error' do
|
31
|
+
message =
|
32
|
+
if Devtools.rbx?
|
33
|
+
%q(undefined method `unknown' on an instance of Ducktrap::Nary::Builder.)
|
34
|
+
else
|
35
|
+
%q(undefined method `unknown' for #<Ducktrap::Nary::Builder klass=Ducktrap::Node::Block>)
|
36
|
+
end
|
37
|
+
|
38
|
+
expect { subject }.to raise_error(
|
39
|
+
NoMethodError,
|
40
|
+
message
|
41
|
+
)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Nary::Builder, '#output' do
|
4
|
+
let(:object) { described_class.new(klass) }
|
5
|
+
let(:klass) { Ducktrap::Node::Block }
|
6
|
+
let(:node) { Ducktrap::Node::Noop.instance }
|
7
|
+
|
8
|
+
subject { object.object }
|
9
|
+
|
10
|
+
it 'should add node to body' do
|
11
|
+
object.add(node)
|
12
|
+
should eql(Ducktrap::Node::Block.new([node]))
|
13
|
+
end
|
14
|
+
|
15
|
+
it_should_behave_like 'an idempotent method'
|
16
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Nary::ClassMethods, '#build' do
|
4
|
+
let(:object) { Object.new.extend(described_class) }
|
5
|
+
|
6
|
+
subject { object.build(:foo, :bar, &block) }
|
7
|
+
|
8
|
+
let(:block) { proc {} }
|
9
|
+
|
10
|
+
let(:output) { mock('Output') }
|
11
|
+
|
12
|
+
it 'should delegate to nary builder' do
|
13
|
+
Ducktrap::Nary::Builder.should_receive(:new) do |first, second, third, &block|
|
14
|
+
first.should be(object)
|
15
|
+
second.should be(:foo)
|
16
|
+
third.should be(:bar)
|
17
|
+
block.should be(self.block)
|
18
|
+
mock(:object => output)
|
19
|
+
end
|
20
|
+
subject.should be(output)
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,13 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Nary, '.included' do
|
4
|
+
subject { described_class = self.described_class; Class.new { include described_class } }
|
5
|
+
|
6
|
+
its(:ancestors) { should include(Ducktrap::Nary::InstanceMethods) }
|
7
|
+
it { should respond_to(:build) }
|
8
|
+
|
9
|
+
specify do
|
10
|
+
subject.new(:foo).should eql(subject.new(:foo))
|
11
|
+
subject.new(:foo).should_not eql(subject.new(:bar))
|
12
|
+
end
|
13
|
+
end
|
@@ -0,0 +1,79 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Ducktrap::Node::Block::Evaluator, '#output' do
|
4
|
+
subject { object.output }
|
5
|
+
|
6
|
+
let(:object) { described_class.new(context, input) }
|
7
|
+
let(:context) { mymock('Context', :body => body) }
|
8
|
+
let(:input) { :input }
|
9
|
+
|
10
|
+
def mymock(name, attributes={})
|
11
|
+
mock(name, attributes.merge(:frozen? => true))
|
12
|
+
end
|
13
|
+
|
14
|
+
context 'without elements in block' do
|
15
|
+
let(:body) { [] }
|
16
|
+
|
17
|
+
it { should be(input) }
|
18
|
+
|
19
|
+
it_should_behave_like 'an idempotent method'
|
20
|
+
end
|
21
|
+
|
22
|
+
context 'with elements in block' do
|
23
|
+
let(:body) { [trap_a, trap_b] }
|
24
|
+
|
25
|
+
context 'without failures' do
|
26
|
+
let(:trap_a) { Ducktrap::Node::Noop.instance }
|
27
|
+
let(:trap_b) { Ducktrap::Node::Noop.instance }
|
28
|
+
|
29
|
+
it { should be(input) }
|
30
|
+
|
31
|
+
it_should_behave_like 'an idempotent method'
|
32
|
+
end
|
33
|
+
|
34
|
+
context 'with late failure' do
|
35
|
+
let(:trap_a) { Ducktrap::Node::Static.new(:forward, :inverse) }
|
36
|
+
let(:trap_b) { Ducktrap::Node::Invalid.instance }
|
37
|
+
|
38
|
+
its(:pretty_inspect) do
|
39
|
+
should eql(strip(<<-STR))
|
40
|
+
Ducktrap::Error
|
41
|
+
input: :input
|
42
|
+
context:
|
43
|
+
Ducktrap::Evaluator::Invalid
|
44
|
+
input: :forward
|
45
|
+
error:
|
46
|
+
Ducktrap::Error
|
47
|
+
input: :forward
|
48
|
+
context:
|
49
|
+
Ducktrap::Node::Invalid
|
50
|
+
context:
|
51
|
+
Ducktrap::Node::Invalid
|
52
|
+
STR
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
context 'with early failure' do
|
57
|
+
let(:trap_a) { Ducktrap::Node::Invalid.instance }
|
58
|
+
let(:trap_b) { mock('Late Node') }
|
59
|
+
|
60
|
+
its(:pretty_inspect) do
|
61
|
+
should eql(strip(<<-STR))
|
62
|
+
Ducktrap::Error
|
63
|
+
input: :input
|
64
|
+
context:
|
65
|
+
Ducktrap::Evaluator::Invalid
|
66
|
+
input: :input
|
67
|
+
error:
|
68
|
+
Ducktrap::Error
|
69
|
+
input: :input
|
70
|
+
context:
|
71
|
+
Ducktrap::Node::Invalid
|
72
|
+
context:
|
73
|
+
Ducktrap::Node::Invalid
|
74
|
+
STR
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
end
|
79
|
+
end
|