debugger-xml 0.0.1
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +20 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.md +24 -0
- data/Rakefile +10 -0
- data/bin/rdebug-ide +90 -0
- data/debugger-xml.gemspec +25 -0
- data/lib/debugger/printers/texts/xml.yml +121 -0
- data/lib/debugger/printers/xml.rb +195 -0
- data/lib/debugger/xml.rb +3 -0
- data/lib/debugger/xml/extensions/commands/edit.rb +13 -0
- data/lib/debugger/xml/extensions/commands/frame.rb +14 -0
- data/lib/debugger/xml/extensions/commands/help.rb +13 -0
- data/lib/debugger/xml/extensions/commands/info.rb +13 -0
- data/lib/debugger/xml/extensions/commands/irb.rb +13 -0
- data/lib/debugger/xml/extensions/commands/kill.rb +13 -0
- data/lib/debugger/xml/extensions/commands/tmate.rb +13 -0
- data/lib/debugger/xml/extensions/commands/trace.rb +13 -0
- data/lib/debugger/xml/extensions/commands/variables.rb +16 -0
- data/lib/debugger/xml/extensions/debugger.rb +28 -0
- data/lib/debugger/xml/extensions/processor.rb +9 -0
- data/lib/debugger/xml/ide_processor.rb +149 -0
- data/lib/debugger/xml/interface.rb +65 -0
- data/lib/debugger/xml/version.rb +5 -0
- data/test/breakpoints_test.rb +190 -0
- data/test/conditions_test.rb +32 -0
- data/test/continue_test.rb +12 -0
- data/test/display_test.rb +25 -0
- data/test/edit_test.rb +12 -0
- data/test/eval_test.rb +20 -0
- data/test/examples/breakpoint1.rb +15 -0
- data/test/examples/breakpoint2.rb +7 -0
- data/test/examples/conditions.rb +4 -0
- data/test/examples/continue.rb +4 -0
- data/test/examples/display.rb +5 -0
- data/test/examples/edit.rb +3 -0
- data/test/examples/eval.rb +4 -0
- data/test/examples/frame.rb +31 -0
- data/test/examples/help.rb +2 -0
- data/test/examples/info.rb +48 -0
- data/test/examples/irb.rb +6 -0
- data/test/examples/jump.rb +14 -0
- data/test/examples/kill.rb +2 -0
- data/test/examples/method.rb +15 -0
- data/test/examples/reload.rb +6 -0
- data/test/examples/restart.rb +6 -0
- data/test/examples/set.rb +3 -0
- data/test/examples/stepping.rb +21 -0
- data/test/examples/thread.rb +32 -0
- data/test/examples/tmate.rb +10 -0
- data/test/examples/trace.rb +7 -0
- data/test/examples/variables.rb +26 -0
- data/test/examples/variables_xml.rb +31 -0
- data/test/frame_test.rb +29 -0
- data/test/help_test.rb +13 -0
- data/test/ide_control_command_processor_test.rb +62 -0
- data/test/ide_processor_test.rb +118 -0
- data/test/info_test.rb +12 -0
- data/test/irb_test.rb +12 -0
- data/test/jump_test.rb +22 -0
- data/test/kill_test.rb +13 -0
- data/test/method_test.rb +36 -0
- data/test/printers/xml_test.rb +193 -0
- data/test/reload_test.rb +14 -0
- data/test/restart_test.rb +50 -0
- data/test/set_test.rb +12 -0
- data/test/stepping_test.rb +15 -0
- data/test/test_helper.rb +6 -0
- data/test/thread_test.rb +20 -0
- data/test/tmate_test.rb +15 -0
- data/test/trace_test.rb +12 -0
- data/test/variables_test.rb +84 -0
- metadata +253 -0
data/test/frame_test.rb
ADDED
@@ -0,0 +1,29 @@
|
|
1
|
+
require_relative 'test_helper'
|
2
|
+
|
3
|
+
describe "Frame Command" do
|
4
|
+
include TestDsl
|
5
|
+
temporary_change_method_value(Debugger, :printer, Printers::Xml.new)
|
6
|
+
|
7
|
+
it "must print current stack frame when without arguments" do
|
8
|
+
enter 'break 25', 'cont', 'up', 'frame'
|
9
|
+
debug_file('frame')
|
10
|
+
check_output_includes %{<frame no="0" file="#{fullpath('frame')}" line="25" current="false"/>}
|
11
|
+
end
|
12
|
+
|
13
|
+
describe "full path settings" do
|
14
|
+
temporary_change_hash_value(Debugger::Command.settings, :full_path, false)
|
15
|
+
|
16
|
+
it "must display current backtrace with full path = true" do
|
17
|
+
enter 'set fullpath', 'break 25', 'cont', 'where'
|
18
|
+
debug_file('frame')
|
19
|
+
check_output_includes(Regexp.new(
|
20
|
+
"<frames>" +
|
21
|
+
%{<frame no="0" file="#{fullpath('frame')}" line="25" current="true"/>} +
|
22
|
+
%{<frame no="1" file="#{fullpath('frame')}" line="21" current="false"/>} +
|
23
|
+
%{<frame no="2" file="#{fullpath('frame')}" line="17" current="false"/>} +
|
24
|
+
%{<frame no="3" file="#{fullpath('frame')}" line="14" current="false"/>.*} +
|
25
|
+
"</frames>",
|
26
|
+
Regexp::MULTILINE))
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
data/test/help_test.rb
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
require_relative 'test_helper'
|
2
|
+
|
3
|
+
describe "Help Command" do
|
4
|
+
include TestDsl
|
5
|
+
temporary_change_method_value(Debugger, :printer, Printers::Xml.new)
|
6
|
+
|
7
|
+
it "must be unsupported for XML printer" do
|
8
|
+
enter 'help'
|
9
|
+
debug_file 'help'
|
10
|
+
check_output_includes "<error>Unsupported command 'help'</error>", interface.error_queue
|
11
|
+
end
|
12
|
+
|
13
|
+
end
|
@@ -0,0 +1,62 @@
|
|
1
|
+
require_relative 'test_helper'
|
2
|
+
require 'debugger/xml/ide_processor'
|
3
|
+
|
4
|
+
describe Debugger::Xml::IdeControlCommandProcessor do
|
5
|
+
include TestDsl
|
6
|
+
|
7
|
+
let(:klass) { Debugger::Xml::IdeControlCommandProcessor }
|
8
|
+
let(:interface) { Debugger.handler.interface }
|
9
|
+
let(:file) { fullpath('jump') }
|
10
|
+
let(:context) { stub(frame_binding: stub, stop_reason: nil, thread: stub, thnum: 1, stack_size: 2, dead?: false) }
|
11
|
+
subject { klass.new(interface) }
|
12
|
+
temporary_change_method_value(Debugger, :handler, Debugger::Xml::IdeProcessor.new(TestInterface.new))
|
13
|
+
|
14
|
+
before do
|
15
|
+
Thread.stubs(:stop)
|
16
|
+
Debugger.handler.instance_variable_set("@context", context)
|
17
|
+
Debugger.handler.instance_variable_set("@file", file)
|
18
|
+
Debugger.handler.instance_variable_set("@line", 30)
|
19
|
+
end
|
20
|
+
|
21
|
+
it "must process a control command" do
|
22
|
+
Debugger::AddBreakpoint.any_instance.expects(:execute).with()
|
23
|
+
enter 'break 5'
|
24
|
+
subject.process_commands
|
25
|
+
end
|
26
|
+
|
27
|
+
it "must process several commands, separated by ;" do
|
28
|
+
Debugger::AddBreakpoint.any_instance.expects(:execute).with()
|
29
|
+
Debugger::DeleteBreakpointCommand.any_instance.expects(:execute).with()
|
30
|
+
enter 'break 5; delete 1'
|
31
|
+
subject.process_commands
|
32
|
+
end
|
33
|
+
|
34
|
+
it "must show error if there is no such command" do
|
35
|
+
enter 'bla'
|
36
|
+
subject.process_commands
|
37
|
+
check_output_includes "Unknown command: bla"
|
38
|
+
end
|
39
|
+
|
40
|
+
it "must show error if context is dead" do
|
41
|
+
context.expects(:dead?).returns(true)
|
42
|
+
enter 'step'
|
43
|
+
subject.process_commands
|
44
|
+
check_output_includes "Command is unavailable"
|
45
|
+
end
|
46
|
+
|
47
|
+
it "must show error if no suspended thread" do
|
48
|
+
Debugger.handler.stubs(:at_line?).returns(false)
|
49
|
+
enter 'step'
|
50
|
+
subject.process_commands
|
51
|
+
check_output_includes(
|
52
|
+
"There is no thread suspended at the time and therefore no context to execute 'step'",
|
53
|
+
interface.error_queue)
|
54
|
+
end
|
55
|
+
|
56
|
+
it "must run stopped thread after stepping command" do
|
57
|
+
context.expects(:step).with(1, false)
|
58
|
+
context.thread.expects(:run)
|
59
|
+
enter 'step'
|
60
|
+
subject.process_commands
|
61
|
+
end
|
62
|
+
end
|
@@ -0,0 +1,118 @@
|
|
1
|
+
require_relative 'test_helper'
|
2
|
+
require 'debugger/xml/ide_processor'
|
3
|
+
|
4
|
+
describe Debugger::Xml::IdeProcessor do
|
5
|
+
include TestDsl
|
6
|
+
|
7
|
+
before { Thread.stubs(:stop) }
|
8
|
+
|
9
|
+
let(:klass) { Debugger::Xml::IdeProcessor }
|
10
|
+
let(:interface) { TestInterface.new }
|
11
|
+
let(:breakpoint) { stub }
|
12
|
+
let(:context) { stub(thread: nil, stop_reason: nil, thnum: 1, stack_size: 2) }
|
13
|
+
let(:file) { fullpath('jump') }
|
14
|
+
subject { klass.new(interface) }
|
15
|
+
|
16
|
+
describe "#at_breakpoint" do
|
17
|
+
it "must assign breakpoint to instance variable" do
|
18
|
+
subject.at_breakpoint(context, breakpoint)
|
19
|
+
subject.instance_variable_get("@last_breakpoint").must_equal breakpoint
|
20
|
+
end
|
21
|
+
|
22
|
+
it "must raise error if @last_breakpoint is already assigned" do
|
23
|
+
subject.instance_variable_set("@last_breakpoint", breakpoint)
|
24
|
+
subject.at_breakpoint(context, breakpoint)
|
25
|
+
check_output_includes /INTERNAL ERROR!!!/
|
26
|
+
end
|
27
|
+
|
28
|
+
it "must not print anything" do
|
29
|
+
subject.at_breakpoint(context, breakpoint)
|
30
|
+
interface.must_be_empty
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
describe "#at_line" do
|
35
|
+
describe "print current position" do
|
36
|
+
it "must print if context is nil" do
|
37
|
+
subject.at_line(nil, file, 30)
|
38
|
+
check_output_includes "#{file}:30"
|
39
|
+
end
|
40
|
+
|
41
|
+
it "must print in xml" do
|
42
|
+
temporary_change_method_value(Debugger, :printer, Printers::Xml.new) do
|
43
|
+
subject.at_line(nil, file, 30)
|
44
|
+
check_output_includes %{<suspended file="#{file}" line="30" threadId="" frames=""/>}
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
it "must print if stop reason is :step" do
|
49
|
+
context.stubs(:stop_reason).returns(:step)
|
50
|
+
subject.at_line(context, file, 30)
|
51
|
+
check_output_includes "#{file}:30"
|
52
|
+
end
|
53
|
+
|
54
|
+
it "must clear instance variables after resuming thread" do
|
55
|
+
subject.instance_variable_set("@line", 10)
|
56
|
+
subject.at_line(context, file, 30)
|
57
|
+
subject.instance_variable_get("@line").must_be_nil
|
58
|
+
end
|
59
|
+
|
60
|
+
describe "print breakpoint after at_breakpoint" do
|
61
|
+
before do
|
62
|
+
Debugger.stubs(:breakpoints).returns([breakpoint])
|
63
|
+
Debugger.stubs(:current_context).returns(stub(thnum: 1))
|
64
|
+
subject.instance_variable_set("@last_breakpoint", breakpoint)
|
65
|
+
end
|
66
|
+
|
67
|
+
it "must print in plain text" do
|
68
|
+
subject.at_line(context, file, 30)
|
69
|
+
check_output_includes "Breakpoint 1 at #{file}:30"
|
70
|
+
end
|
71
|
+
|
72
|
+
it "must print in xml" do
|
73
|
+
temporary_change_method_value(Debugger, :printer, Printers::Xml.new) do
|
74
|
+
subject.at_line(context, file, 30)
|
75
|
+
check_output_includes %{<breakpoint file="#{file}" line="30" threadId="1"/>}
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
it "must show error if current thread is DebugThread" do
|
81
|
+
context.stubs(:thread).returns(Debugger::DebugThread.new {})
|
82
|
+
subject.at_line(context, file, 30)
|
83
|
+
check_output_includes /DebuggerThread are not supposed to be traced/
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
87
|
+
|
88
|
+
describe "#at_line?" do
|
89
|
+
it "returns false if #at_line was not called yet" do
|
90
|
+
subject.at_line?.must_equal false
|
91
|
+
end
|
92
|
+
|
93
|
+
it "returns true if #at_line was called already" do
|
94
|
+
subject.instance_variable_set("@line", 10)
|
95
|
+
subject.at_line?.must_equal true
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
describe "#at_return?" do
|
100
|
+
before { context.stubs(:stop_frame=).with(-1) }
|
101
|
+
|
102
|
+
it "sets stop_frame to -1" do
|
103
|
+
context.expects(:stop_frame=).with(-1)
|
104
|
+
subject.at_return(context, file, 30)
|
105
|
+
end
|
106
|
+
|
107
|
+
it "prints current file and line" do
|
108
|
+
subject.at_return(context, file, 30)
|
109
|
+
check_output_includes "#{file}:30"
|
110
|
+
end
|
111
|
+
|
112
|
+
it "stops the thread" do
|
113
|
+
Thread.expects(:stop)
|
114
|
+
subject.at_return(context, file, 30)
|
115
|
+
end
|
116
|
+
end
|
117
|
+
|
118
|
+
end
|
data/test/info_test.rb
ADDED
@@ -0,0 +1,12 @@
|
|
1
|
+
require_relative 'test_helper'
|
2
|
+
|
3
|
+
describe "Info Command" do
|
4
|
+
include TestDsl
|
5
|
+
temporary_change_method_value(Debugger, :printer, Printers::Xml.new)
|
6
|
+
|
7
|
+
it "must be unsupported for XML printer" do
|
8
|
+
enter 'info line'
|
9
|
+
debug_file 'info'
|
10
|
+
check_output_includes "<error>Unsupported command 'info'</error>", interface.error_queue
|
11
|
+
end
|
12
|
+
end
|
data/test/irb_test.rb
ADDED
@@ -0,0 +1,12 @@
|
|
1
|
+
require_relative 'test_helper'
|
2
|
+
|
3
|
+
describe "Irb Command" do
|
4
|
+
include TestDsl
|
5
|
+
temporary_change_method_value(Debugger, :printer, Printers::Xml.new)
|
6
|
+
|
7
|
+
it "must be unsupported for XML printer" do
|
8
|
+
enter 'irb'
|
9
|
+
debug_file 'irb'
|
10
|
+
check_output_includes "<error>Unsupported command 'irb'</error>", interface.error_queue
|
11
|
+
end
|
12
|
+
end
|
data/test/jump_test.rb
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
require_relative 'test_helper'
|
2
|
+
|
3
|
+
describe "Jump Command" do
|
4
|
+
include TestDsl
|
5
|
+
temporary_change_method_value(Debugger, :printer, Printers::Xml.new)
|
6
|
+
|
7
|
+
describe "successful" do
|
8
|
+
describe "jumping to the same line" do
|
9
|
+
it "must show show the same position" do
|
10
|
+
enter 'break 6', 'cont', "jump 6 #{fullpath('jump')}"
|
11
|
+
debug_file('jump')
|
12
|
+
check_output_includes /<suspended file="#{fullpath('jump')}" line="6" threadId="\d+" frames="\d+"\/>/
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
it "must show message after jump" do
|
17
|
+
enter 'break 6', 'cont', "jump 8 #{fullpath('jump')}"
|
18
|
+
debug_file('jump')
|
19
|
+
check_output_includes /<suspended file="#{fullpath('jump')}" line="8" threadId="\d+" frames="\d+"\/>/
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
data/test/kill_test.rb
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
require_relative 'test_helper'
|
2
|
+
|
3
|
+
describe "Kill Command" do
|
4
|
+
include TestDsl
|
5
|
+
temporary_change_method_value(Debugger, :printer, Printers::Xml.new)
|
6
|
+
|
7
|
+
it "must be unsupported for XML printer" do
|
8
|
+
enter 'kill'
|
9
|
+
debug_file 'kill'
|
10
|
+
check_output_includes "<error>Unsupported command 'kill'</error>", interface.error_queue
|
11
|
+
end
|
12
|
+
|
13
|
+
end
|
data/test/method_test.rb
ADDED
@@ -0,0 +1,36 @@
|
|
1
|
+
require_relative 'test_helper'
|
2
|
+
|
3
|
+
describe "Method Command" do
|
4
|
+
include TestDsl
|
5
|
+
temporary_change_method_value(Debugger, :printer, Printers::Xml.new)
|
6
|
+
|
7
|
+
describe "show instance method of a class" do
|
8
|
+
it "must show using full command name" do
|
9
|
+
enter 'break 15', 'cont', 'm MethodEx'
|
10
|
+
debug_file 'method'
|
11
|
+
check_output_includes '<methods><method name="bla"/></methods>'
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
describe "show methods of an object" do
|
16
|
+
it "must show using full command name" do
|
17
|
+
enter 'break 15', 'cont', 'method instance a'
|
18
|
+
debug_file 'method'
|
19
|
+
check_output_includes /<methods>.*<method name="bla"\/>.*<\/methods>/
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
describe "show instance variables of an object" do
|
24
|
+
it "must show using full name command" do
|
25
|
+
enter 'break 15', 'cont', 'method iv a'
|
26
|
+
debug_file 'method'
|
27
|
+
check_output_includes(Regexp.new(
|
28
|
+
%{<variables>} +
|
29
|
+
%{<variable name="@a" kind="instance" value="b" type="String" hasChildren="false" objectId=".*?"/>} +
|
30
|
+
%{<variable name="@c" kind="instance" value="d" type="String" hasChildren="false" objectId=".*?"/>} +
|
31
|
+
%{</variables>}
|
32
|
+
))
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
end
|
@@ -0,0 +1,193 @@
|
|
1
|
+
require_relative '../test_helper'
|
2
|
+
|
3
|
+
describe "Printers::Xml" do
|
4
|
+
include PrinterHelpers
|
5
|
+
|
6
|
+
let(:klass) { Printers::Xml }
|
7
|
+
let(:printer) { klass.new }
|
8
|
+
let(:yaml_xml) do
|
9
|
+
{
|
10
|
+
"foo" => {
|
11
|
+
"errors" => {
|
12
|
+
"bad" => "bad behavior"
|
13
|
+
},
|
14
|
+
"confirmations" => {
|
15
|
+
"okay" => "Okay?"
|
16
|
+
},
|
17
|
+
"debug" => {
|
18
|
+
"dbg" => "Debug message"
|
19
|
+
},
|
20
|
+
"bar" => {
|
21
|
+
"tag" => "xmltag",
|
22
|
+
"attributes" => {
|
23
|
+
"boo" => "{zee} > {uga}",
|
24
|
+
"agu" => "bew"
|
25
|
+
}
|
26
|
+
}
|
27
|
+
},
|
28
|
+
"variable" => {
|
29
|
+
"variable" => {
|
30
|
+
"tag" => "variable",
|
31
|
+
"attributes" => {
|
32
|
+
"name" => "{name}",
|
33
|
+
"kind" => "{kind}",
|
34
|
+
"value" => "{value}",
|
35
|
+
"type" => "{type}",
|
36
|
+
"hasChildren" => "{has_children}",
|
37
|
+
"objectId" => "{id}"
|
38
|
+
}
|
39
|
+
}
|
40
|
+
}
|
41
|
+
}
|
42
|
+
end
|
43
|
+
|
44
|
+
before do
|
45
|
+
YAML.stubs(:load_file).with(yaml_file_path('xml')).returns(yaml_xml)
|
46
|
+
YAML.stubs(:load_file).with(yaml_file_path('base')).returns({})
|
47
|
+
end
|
48
|
+
|
49
|
+
describe "#print" do
|
50
|
+
it "must return correctly translated string" do
|
51
|
+
xml = ::Builder::XmlMarkup.new.xmltag(boo: "zuu > aga", agu: "bew")
|
52
|
+
printer.print("foo.bar", zee: "zuu", uga: "aga").must_equal xml
|
53
|
+
end
|
54
|
+
|
55
|
+
it "must return error string" do
|
56
|
+
printer.print("foo.errors.bad").must_equal "<error>bad behavior</error>"
|
57
|
+
end
|
58
|
+
|
59
|
+
it "must return confirmation string" do
|
60
|
+
printer.print("foo.confirmations.okay").must_equal "<confirmation>Okay?</confirmation>"
|
61
|
+
end
|
62
|
+
|
63
|
+
it "must return debug string" do
|
64
|
+
printer.print("foo.debug.dbg").must_equal "Debug message"
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
describe "#print_collection" do
|
69
|
+
it "must print collection" do
|
70
|
+
expected = ::Builder::XmlMarkup.new.xmltags do |x|
|
71
|
+
x.xmltag(boo: "0 > a", agu: "bew") + x.xmltag(boo: "1 > b", agu: "bew")
|
72
|
+
end
|
73
|
+
result = printer.print_collection("foo.bar", [{uga: 'a'}, {uga: 'b'}]) do |item, index|
|
74
|
+
item.merge(zee: index)
|
75
|
+
end
|
76
|
+
result.must_equal expected
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
describe "#print_variables" do
|
81
|
+
it "must print variables" do
|
82
|
+
vars = [["a", "b"], ["c", "d"]]
|
83
|
+
expected = ::Builder::XmlMarkup.new.variables do |x|
|
84
|
+
vars.map do |key, value|
|
85
|
+
x.variable(name: key, kind: "instance", value: value, type: "String", hasChildren: "false", objectId: "%#+x" % value.object_id)
|
86
|
+
end.join("")
|
87
|
+
end
|
88
|
+
result = printer.print_variables(vars, 'instance')
|
89
|
+
result.must_equal expected
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
describe "Printers::Xml::Variable" do
|
94
|
+
let(:klass) { Printers::Xml::Variable }
|
95
|
+
|
96
|
+
describe "#has_children?" do
|
97
|
+
describe "value is Array" do
|
98
|
+
it("must be true for non-empty") { klass.new('bla', ['a']).has_children?.must_equal(true) }
|
99
|
+
it("must be false for empty") { klass.new('bla', []).has_children?.must_equal(false) }
|
100
|
+
end
|
101
|
+
|
102
|
+
describe "value is Hash" do
|
103
|
+
it("must be true for non-empty") { klass.new('bla', {a: 'b'}).has_children?.must_equal(true) }
|
104
|
+
it("must be false for empty") { klass.new('bla', {}).has_children?.must_equal(false) }
|
105
|
+
end
|
106
|
+
|
107
|
+
describe "value is some random class" do
|
108
|
+
unless const_defined?("VariableExampleWithInstanceVars")
|
109
|
+
class VariableExampleWithInstanceVars; def initialize; @a = '1'; end; end
|
110
|
+
end
|
111
|
+
unless const_defined?("VariableExampleWithClassVars")
|
112
|
+
class VariableExampleWithClassVars; def initialize; @@a = '1'; end; end
|
113
|
+
end
|
114
|
+
unless const_defined?("VariableExampleWithoutVars")
|
115
|
+
class VariableExampleWithoutVars; end
|
116
|
+
end
|
117
|
+
it("must be true if has instance variables") { klass.new('bla', VariableExampleWithInstanceVars.new).has_children?.must_equal(true) }
|
118
|
+
it("must be true if has class variables") { klass.new('bla', VariableExampleWithClassVars.new).has_children?.must_equal(true) }
|
119
|
+
it("must be false if has no any variables") { klass.new('bla', VariableExampleWithoutVars.new).has_children?.must_equal(false) }
|
120
|
+
it("must be false as a fallback") { klass.new('bla', BasicObject.new).has_children?.must_equal(false) }
|
121
|
+
end
|
122
|
+
end
|
123
|
+
|
124
|
+
describe "#value" do
|
125
|
+
describe "value is a Array" do
|
126
|
+
it("must return string for empty") { klass.new('bla', []).value.must_equal("Empty Array") }
|
127
|
+
it("must return result for non-empty") { klass.new('bla', [1, 2]).value.must_equal("Array (2 element(s))") }
|
128
|
+
end
|
129
|
+
|
130
|
+
describe "value is a Hash" do
|
131
|
+
it("must return string for empty") { klass.new('bla', {}).value.must_equal("Empty Hash") }
|
132
|
+
it("must return result for non-empty") { klass.new('bla', {a: 'b', c: 'd'}).value.must_equal("Hash (2 element(s))") }
|
133
|
+
end
|
134
|
+
|
135
|
+
describe "value is some random class" do
|
136
|
+
unless const_defined?("ToSReturnNotAString")
|
137
|
+
class ToSReturnNotAString; def to_s; {}; end; end
|
138
|
+
end
|
139
|
+
it("must return nil for nil") { klass.new('bla', nil).value.must_equal("nil") }
|
140
|
+
it("must return #to_s for any other class") do
|
141
|
+
klass.new('bla', OpenStruct.new(a: 'b')).value.must_equal '#<OpenStruct a="b">'
|
142
|
+
end
|
143
|
+
it("must be able to show error") do
|
144
|
+
klass.new('bla', BasicObject.new).value.must_match /<raised exception: undefined method/
|
145
|
+
end
|
146
|
+
it("must get rid of quotes") { klass.new('bla', '"foo"').value.must_equal 'foo' }
|
147
|
+
it("must return special message for binary") { klass.new('bla', "\xFF\x12").value.must_equal '[Binary Data]' }
|
148
|
+
it("must show error if returned value is not a string") do
|
149
|
+
klass.new('bla', ToSReturnNotAString.new).value.must_equal(
|
150
|
+
'ERROR: ToSReturnNotAString.to_s method returns Hash. Should return String.'
|
151
|
+
)
|
152
|
+
end
|
153
|
+
end
|
154
|
+
end
|
155
|
+
|
156
|
+
describe "#id" do
|
157
|
+
it "must show object_id" do
|
158
|
+
object = Object.new
|
159
|
+
klass.new('bla', object).id.must_equal("%#+x" % object.object_id)
|
160
|
+
end
|
161
|
+
|
162
|
+
it "must return nil as a fallback" do
|
163
|
+
klass.new('bla', BasicObject.new).id.must_be_nil
|
164
|
+
end
|
165
|
+
end
|
166
|
+
|
167
|
+
describe "#type" do
|
168
|
+
it "must return class" do
|
169
|
+
klass.new('bla', Object.new).type.must_equal(Object.new.class)
|
170
|
+
end
|
171
|
+
|
172
|
+
it "must return 'Undefined' as a callback" do
|
173
|
+
klass.new('bla', BasicObject.new).type.must_equal "Undefined"
|
174
|
+
end
|
175
|
+
end
|
176
|
+
|
177
|
+
describe "#name" do
|
178
|
+
it "must return name as a string" do
|
179
|
+
klass.new(:bla, "value").name.must_equal "bla"
|
180
|
+
end
|
181
|
+
end
|
182
|
+
|
183
|
+
describe "#to_hash" do
|
184
|
+
it "must return a hash with values" do
|
185
|
+
var = "foo"
|
186
|
+
klass.new(:bla, var).to_hash.must_equal(
|
187
|
+
{name: "bla", kind: nil, value: var, type: String, has_children: false, id: "%#+x" % var.object_id}
|
188
|
+
)
|
189
|
+
end
|
190
|
+
end
|
191
|
+
|
192
|
+
end
|
193
|
+
end
|