ruby-prof 0.15.8 → 0.15.9
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGES +5 -0
- data/README.rdoc +187 -185
- data/doc/LICENSE.html +114 -0
- data/doc/README_rdoc.html +544 -0
- data/doc/Rack.html +95 -0
- data/doc/Rack/RubyProf.html +223 -0
- data/doc/RubyProf.html +961 -0
- data/doc/RubyProf/AbstractPrinter.html +546 -0
- data/doc/RubyProf/AggregateCallInfo.html +551 -0
- data/doc/RubyProf/CallInfo.html +639 -0
- data/doc/RubyProf/CallInfoPrinter.html +120 -0
- data/doc/RubyProf/CallInfoVisitor.html +198 -0
- data/doc/RubyProf/CallStackPrinter.html +1121 -0
- data/doc/RubyProf/CallTreePrinter.html +359 -0
- data/doc/RubyProf/Cmd.html +631 -0
- data/doc/RubyProf/DotPrinter.html +257 -0
- data/doc/RubyProf/FlatPrinter.html +163 -0
- data/doc/RubyProf/FlatPrinterWithLineNumbers.html +208 -0
- data/doc/RubyProf/GraphHtmlPrinter.html +552 -0
- data/doc/RubyProf/GraphPrinter.html +139 -0
- data/doc/RubyProf/MethodInfo.html +745 -0
- data/doc/RubyProf/MultiPrinter.html +358 -0
- data/doc/RubyProf/Profile.html +713 -0
- data/doc/RubyProf/ProfileTask.html +490 -0
- data/doc/RubyProf/Thread.html +268 -0
- data/doc/created.rid +13 -13
- data/doc/examples/flat_txt.html +138 -0
- data/doc/examples/graph_html.html +909 -0
- data/doc/examples/graph_txt.html +247 -0
- data/doc/images/add.png +0 -0
- data/doc/images/arrow_up.png +0 -0
- data/doc/images/brick.png +0 -0
- data/doc/images/brick_link.png +0 -0
- data/doc/images/bug.png +0 -0
- data/doc/images/bullet_black.png +0 -0
- data/doc/images/bullet_toggle_minus.png +0 -0
- data/doc/images/bullet_toggle_plus.png +0 -0
- data/doc/images/date.png +0 -0
- data/doc/images/delete.png +0 -0
- data/doc/images/find.png +0 -0
- data/doc/images/macFFBgHack.png +0 -0
- data/doc/images/package.png +0 -0
- data/doc/images/page_green.png +0 -0
- data/doc/images/page_white_text.png +0 -0
- data/doc/images/page_white_width.png +0 -0
- data/doc/images/plugin.png +0 -0
- data/doc/images/ruby.png +0 -0
- data/doc/images/tag_blue.png +0 -0
- data/doc/images/tag_green.png +0 -0
- data/doc/images/transparent.png +0 -0
- data/doc/images/wrench.png +0 -0
- data/doc/images/wrench_orange.png +0 -0
- data/doc/images/zoom.png +0 -0
- data/doc/index.html +571 -0
- data/doc/js/navigation.js.gz +0 -0
- data/doc/js/search_index.js +1 -1
- data/doc/js/search_index.js.gz +0 -0
- data/doc/js/searcher.js.gz +0 -0
- data/doc/table_of_contents.html +893 -0
- data/examples/flat.txt +50 -55
- data/examples/graph.html +823 -823
- data/examples/graph.txt +139 -170
- data/ext/ruby_prof/extconf.rb +6 -1
- data/lib/ruby-prof/aggregate_call_info.rb +17 -11
- data/lib/ruby-prof/call_info.rb +2 -17
- data/lib/ruby-prof/method_info.rb +6 -22
- data/lib/ruby-prof/printers/graph_html_printer.rb +0 -2
- data/lib/ruby-prof/printers/graph_printer.rb +4 -6
- data/lib/ruby-prof/rack.rb +7 -0
- data/lib/ruby-prof/thread.rb +0 -4
- data/lib/ruby-prof/version.rb +1 -1
- data/ruby-prof.gemspec +1 -1
- data/test/basic_test.rb +26 -26
- data/test/issue137_test.rb +63 -0
- data/test/measure_allocations_test.rb +4 -3
- data/test/measure_cpu_time_test.rb +6 -6
- data/test/measure_process_time_test.rb +8 -8
- data/test/pause_resume_test.rb +9 -9
- data/test/printers_test.rb +1 -1
- data/test/printing_recursive_graph_test.rb +127 -0
- data/test/rack_test.rb +49 -1
- data/test/recursive_test.rb +41 -37
- data/test/test_helper.rb +93 -0
- metadata +59 -5
@@ -210,7 +210,6 @@ module RubyProf
|
|
210
210
|
</tr>
|
211
211
|
<!-- Children -->
|
212
212
|
<%
|
213
|
-
method.recalc_recursion unless method.non_recursive?
|
214
213
|
for callee in method.aggregate_children.sort_by(&:total_time).reverse
|
215
214
|
next if min_time && callee.total_time < min_time
|
216
215
|
%>
|
@@ -228,7 +227,6 @@ module RubyProf
|
|
228
227
|
<% end %>
|
229
228
|
<!-- Create divider row -->
|
230
229
|
<tr class="break"><td colspan="9"></td></tr>
|
231
|
-
<% thread.recalc_recursion unless method.non_recursive? %>
|
232
230
|
<% end %>
|
233
231
|
</tbody>
|
234
232
|
<tfoot>
|
@@ -36,7 +36,7 @@ module RubyProf
|
|
36
36
|
@output << sprintf("%#{TIME_WIDTH}s", "wait")
|
37
37
|
@output << sprintf("%#{TIME_WIDTH}s", "child")
|
38
38
|
@output << sprintf("%#{CALL_WIDTH}s", "calls")
|
39
|
-
@output << "
|
39
|
+
@output << " name"
|
40
40
|
@output << "\n"
|
41
41
|
end
|
42
42
|
|
@@ -63,16 +63,14 @@ module RubyProf
|
|
63
63
|
@output << sprintf("%#{TIME_WIDTH}.3f", method.wait_time)
|
64
64
|
@output << sprintf("%#{TIME_WIDTH}.3f", method.children_time)
|
65
65
|
@output << sprintf("%#{CALL_WIDTH}i", method.called)
|
66
|
-
@output << sprintf("
|
66
|
+
@output << sprintf(" %s", method.recursive? ? "*" : " ")
|
67
67
|
@output << sprintf("%s", method_name(method))
|
68
68
|
if print_file
|
69
69
|
@output << sprintf(" %s:%s", method.source_file, method.line)
|
70
70
|
end
|
71
71
|
@output << "\n"
|
72
72
|
|
73
|
-
method.recalc_recursion unless method.non_recursive?
|
74
73
|
print_children(method)
|
75
|
-
thread.recalc_recursion unless method.non_recursive?
|
76
74
|
end
|
77
75
|
end
|
78
76
|
|
@@ -87,7 +85,7 @@ module RubyProf
|
|
87
85
|
|
88
86
|
call_called = "#{caller.called}/#{method.called}"
|
89
87
|
@output << sprintf("%#{CALL_WIDTH}s", call_called)
|
90
|
-
@output << sprintf("
|
88
|
+
@output << sprintf(" %s", caller.parent.target.full_name)
|
91
89
|
@output << "\n"
|
92
90
|
end
|
93
91
|
end
|
@@ -105,7 +103,7 @@ module RubyProf
|
|
105
103
|
|
106
104
|
call_called = "#{child.called}/#{child.target.called}"
|
107
105
|
@output << sprintf("%#{CALL_WIDTH}s", call_called)
|
108
|
-
@output << sprintf("
|
106
|
+
@output << sprintf(" %s", child.target.full_name)
|
109
107
|
@output << "\n"
|
110
108
|
end
|
111
109
|
end
|
data/lib/ruby-prof/rack.rb
CHANGED
@@ -38,9 +38,16 @@ module Rack
|
|
38
38
|
end
|
39
39
|
end
|
40
40
|
|
41
|
+
private
|
42
|
+
|
41
43
|
def print(data, path)
|
42
44
|
@printer_klasses.each do |printer_klass, base_name|
|
43
45
|
printer = printer_klass.new(data)
|
46
|
+
|
47
|
+
if base_name.respond_to?(:call)
|
48
|
+
base_name = base_name.call
|
49
|
+
end
|
50
|
+
|
44
51
|
file_name = ::File.join(@tmpdir, "#{path}-#{base_name}")
|
45
52
|
::File.open(file_name, 'wb') do |file|
|
46
53
|
printer.print(file, @options)
|
data/lib/ruby-prof/thread.rb
CHANGED
@@ -16,10 +16,6 @@ module RubyProf
|
|
16
16
|
top_call_infos.each(&:detect_recursion)
|
17
17
|
end
|
18
18
|
|
19
|
-
def recalc_recursion
|
20
|
-
top_call_infos.each(&:recalc_recursion)
|
21
|
-
end
|
22
|
-
|
23
19
|
def total_time
|
24
20
|
self.top_methods.inject(0) do |sum, method_info|
|
25
21
|
method_info.call_infos.each do |call_info|
|
data/lib/ruby-prof/version.rb
CHANGED
data/ruby-prof.gemspec
CHANGED
@@ -51,7 +51,7 @@ EOF
|
|
51
51
|
spec.required_ruby_version = '>= 1.9.3'
|
52
52
|
spec.date = Time.now.strftime('%Y-%m-%d')
|
53
53
|
spec.homepage = 'https://github.com/ruby-prof/ruby-prof'
|
54
|
-
spec.add_development_dependency('minitest', '~> 5.
|
54
|
+
spec.add_development_dependency('minitest', '~> 5.8.3')
|
55
55
|
spec.add_development_dependency('rake-compiler')
|
56
56
|
spec.add_development_dependency('rdoc')
|
57
57
|
end
|
data/test/basic_test.rb
CHANGED
@@ -53,7 +53,7 @@ class BasicTest < TestCase
|
|
53
53
|
assert_equal(1, profile.threads.count)
|
54
54
|
|
55
55
|
thread = profile.threads.first
|
56
|
-
assert_in_delta(0.25, thread.total_time, 0.
|
56
|
+
assert_in_delta(0.25, thread.total_time, 0.015)
|
57
57
|
|
58
58
|
top_methods = thread.top_methods.sort
|
59
59
|
assert_equal(2, top_methods.count)
|
@@ -65,24 +65,24 @@ class BasicTest < TestCase
|
|
65
65
|
|
66
66
|
# Check times
|
67
67
|
assert_equal("<Class::RubyProf::C1>#hello", methods[0].full_name)
|
68
|
-
assert_in_delta(0.1, methods[0].total_time, 0.
|
69
|
-
assert_in_delta(0.0, methods[0].wait_time, 0.
|
70
|
-
assert_in_delta(0.0, methods[0].self_time, 0.
|
68
|
+
assert_in_delta(0.1, methods[0].total_time, 0.015)
|
69
|
+
assert_in_delta(0.0, methods[0].wait_time, 0.015)
|
70
|
+
assert_in_delta(0.0, methods[0].self_time, 0.015)
|
71
71
|
|
72
72
|
assert_equal("BasicTest#start", methods[1].full_name)
|
73
|
-
assert_in_delta(0.1, methods[1].total_time, 0.
|
74
|
-
assert_in_delta(0.0, methods[1].wait_time, 0.
|
75
|
-
assert_in_delta(0.0, methods[1].self_time, 0.
|
73
|
+
assert_in_delta(0.1, methods[1].total_time, 0.015)
|
74
|
+
assert_in_delta(0.0, methods[1].wait_time, 0.015)
|
75
|
+
assert_in_delta(0.0, methods[1].self_time, 0.015)
|
76
76
|
|
77
77
|
assert_equal("BasicTest#test_leave_method", methods[2].full_name)
|
78
|
-
assert_in_delta(0.15, methods[2].total_time, 0.
|
79
|
-
assert_in_delta(0.0, methods[2].wait_time, 0.
|
80
|
-
assert_in_delta(0.0, methods[2].self_time, 0.
|
78
|
+
assert_in_delta(0.15, methods[2].total_time, 0.015)
|
79
|
+
assert_in_delta(0.0, methods[2].wait_time, 0.015)
|
80
|
+
assert_in_delta(0.0, methods[2].self_time, 0.015)
|
81
81
|
|
82
82
|
assert_equal("Kernel#sleep", methods[3].full_name)
|
83
|
-
assert_in_delta(0.25, methods[3].total_time, 0.
|
84
|
-
assert_in_delta(0.0, methods[3].wait_time, 0.
|
85
|
-
assert_in_delta(0.25, methods[3].self_time, 0.
|
83
|
+
assert_in_delta(0.25, methods[3].total_time, 0.015)
|
84
|
+
assert_in_delta(0.0, methods[3].wait_time, 0.015)
|
85
|
+
assert_in_delta(0.25, methods[3].self_time, 0.015)
|
86
86
|
end
|
87
87
|
|
88
88
|
def test_leave_method_2
|
@@ -94,7 +94,7 @@ class BasicTest < TestCase
|
|
94
94
|
assert_equal(1, profile.threads.count)
|
95
95
|
|
96
96
|
thread = profile.threads.first
|
97
|
-
assert_in_delta(0.3, thread.total_time, 0.
|
97
|
+
assert_in_delta(0.3, thread.total_time, 0.015)
|
98
98
|
|
99
99
|
top_methods = thread.top_methods.sort
|
100
100
|
assert_equal(2, top_methods.count)
|
@@ -106,23 +106,23 @@ class BasicTest < TestCase
|
|
106
106
|
|
107
107
|
# Check times
|
108
108
|
assert_equal("BasicTest#start", methods[0].full_name)
|
109
|
-
assert_in_delta(0.1, methods[0].total_time, 0.
|
110
|
-
assert_in_delta(0.0, methods[0].wait_time, 0.
|
111
|
-
assert_in_delta(0.0, methods[0].self_time, 0.
|
109
|
+
assert_in_delta(0.1, methods[0].total_time, 0.015)
|
110
|
+
assert_in_delta(0.0, methods[0].wait_time, 0.015)
|
111
|
+
assert_in_delta(0.0, methods[0].self_time, 0.015)
|
112
112
|
|
113
113
|
assert_equal("BasicTest#test_leave_method_2", methods[1].full_name)
|
114
|
-
assert_in_delta(0.2, methods[1].total_time, 0.
|
115
|
-
assert_in_delta(0.0, methods[1].wait_time, 0.
|
116
|
-
assert_in_delta(0.0, methods[1].self_time, 0.
|
114
|
+
assert_in_delta(0.2, methods[1].total_time, 0.015)
|
115
|
+
assert_in_delta(0.0, methods[1].wait_time, 0.015)
|
116
|
+
assert_in_delta(0.0, methods[1].self_time, 0.015)
|
117
117
|
|
118
118
|
assert_equal("Kernel#sleep", methods[2].full_name)
|
119
|
-
assert_in_delta(0.3, methods[2].total_time, 0.
|
120
|
-
assert_in_delta(0.0, methods[2].wait_time, 0.
|
121
|
-
assert_in_delta(0.3, methods[2].self_time, 0.
|
119
|
+
assert_in_delta(0.3, methods[2].total_time, 0.015)
|
120
|
+
assert_in_delta(0.0, methods[2].wait_time, 0.015)
|
121
|
+
assert_in_delta(0.3, methods[2].self_time, 0.015)
|
122
122
|
|
123
123
|
assert_equal("<Class::RubyProf::C1>#hello", methods[3].full_name)
|
124
|
-
assert_in_delta(0.3, methods[3].total_time, 0.
|
125
|
-
assert_in_delta(0.0, methods[3].wait_time, 0.
|
126
|
-
assert_in_delta(0.0, methods[3].self_time, 0.
|
124
|
+
assert_in_delta(0.3, methods[3].total_time, 0.015)
|
125
|
+
assert_in_delta(0.0, methods[3].wait_time, 0.015)
|
126
|
+
assert_in_delta(0.0, methods[3].self_time, 0.015)
|
127
127
|
end
|
128
128
|
end
|
@@ -0,0 +1,63 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
# encoding: UTF-8
|
3
|
+
|
4
|
+
require File.expand_path('../test_helper', __FILE__)
|
5
|
+
|
6
|
+
# issue 137 is about correctly attributing time of recursive children
|
7
|
+
|
8
|
+
class RecursiveChildrenTest < TestCase
|
9
|
+
class SlowClass
|
10
|
+
def time_sink
|
11
|
+
1234567890 ** 100 == 0
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
class SlowSearcher
|
16
|
+
def do_find(slow_objects)
|
17
|
+
slow_objects.find(&:time_sink)
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
class MainClass
|
22
|
+
def self.main_method
|
23
|
+
slow_objects = [SlowClass.new] * 100_000
|
24
|
+
slow_searcher = SlowSearcher.new
|
25
|
+
slow_searcher.do_find(slow_objects)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
include PrinterTestHelper
|
30
|
+
|
31
|
+
def setup
|
32
|
+
# Need to use wall time for this test due to the sleep calls
|
33
|
+
RubyProf::measure_mode = RubyProf::WALL_TIME
|
34
|
+
end
|
35
|
+
|
36
|
+
def test_simple
|
37
|
+
result = RubyProf.profile do
|
38
|
+
# make array each recursive
|
39
|
+
[1].each do
|
40
|
+
MainClass.main_method
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
# methods = result.threads.first.methods.sort.reverse
|
45
|
+
|
46
|
+
printer = RubyProf::GraphPrinter.new(result)
|
47
|
+
|
48
|
+
buffer = ''
|
49
|
+
printer.print(StringIO.new(buffer))
|
50
|
+
|
51
|
+
puts buffer if ENV['SHOW_RUBY_PROF_PRINTER_OUTPUT'] == "1"
|
52
|
+
|
53
|
+
parsed_output = MetricsArray.parse(buffer)
|
54
|
+
|
55
|
+
assert( enum_find = parsed_output.metrics_for("Enumerable#find") )
|
56
|
+
assert( array_each = enum_find.child("Array#each") )
|
57
|
+
|
58
|
+
assert_operator enum_find.metrics.total, :>=, array_each.total
|
59
|
+
assert_operator enum_find.metrics.total, :>, 0
|
60
|
+
assert_in_delta enum_find.metrics.total, array_each.total, 0.02
|
61
|
+
end
|
62
|
+
|
63
|
+
end
|
@@ -16,10 +16,11 @@ class MeasureAllocationsTest < TestCase
|
|
16
16
|
if RubyProf::ALLOCATIONS_ENABLED
|
17
17
|
def test_allocations
|
18
18
|
t = RubyProf.measure_allocations
|
19
|
-
|
20
|
-
|
19
|
+
refute_empty("a" + "b")
|
21
20
|
u = RubyProf.measure_allocations
|
22
|
-
|
21
|
+
assert_kind_of Integer, t
|
22
|
+
assert_kind_of Integer, u
|
23
|
+
assert_operator t, :<, u
|
23
24
|
end
|
24
25
|
end
|
25
26
|
end
|
@@ -35,13 +35,13 @@ class MeasureCpuTimeTest < TestCase
|
|
35
35
|
assert_equal('<Class::RubyProf::C7>#hello', methods[1].full_name)
|
36
36
|
|
37
37
|
# Check times
|
38
|
-
assert_in_delta(0.1, methods[0].total_time, 0.
|
39
|
-
assert_in_delta(0, methods[0].wait_time, 0.
|
40
|
-
assert_in_delta(0, methods[0].self_time, 0.
|
38
|
+
assert_in_delta(0.1, methods[0].total_time, 0.03)
|
39
|
+
assert_in_delta(0, methods[0].wait_time, 0.03)
|
40
|
+
assert_in_delta(0, methods[0].self_time, 0.03)
|
41
41
|
|
42
|
-
assert_in_delta(0.1, methods[1].total_time, 0.
|
43
|
-
assert_in_delta(0, methods[1].wait_time, 0.
|
44
|
-
assert_in_delta(0, methods[1].self_time, 0.
|
42
|
+
assert_in_delta(0.1, methods[1].total_time, 0.03)
|
43
|
+
assert_in_delta(0, methods[1].wait_time, 0.03)
|
44
|
+
assert_in_delta(0, methods[1].self_time, 0.03)
|
45
45
|
end
|
46
46
|
|
47
47
|
def test_instance_methods
|
@@ -31,15 +31,15 @@ class MeasureProcessTimeTest < TestCase
|
|
31
31
|
|
32
32
|
methods = result.threads.first.methods.sort.reverse
|
33
33
|
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
end
|
34
|
+
expected_number_of_methods =
|
35
|
+
case RUBY_VERSION
|
36
|
+
when /^1\.9\.3/ then 16
|
37
|
+
when /^2\.0/ then 15
|
38
|
+
when /^2\.(1|2)/ then 14
|
39
|
+
else 13
|
40
|
+
end
|
42
41
|
# puts methods.map(&:full_name).inspect
|
42
|
+
assert_equal expected_number_of_methods, methods.length
|
43
43
|
|
44
44
|
# Check times
|
45
45
|
assert_equal("MeasureProcessTimeTest#test_primes", methods[0].full_name)
|
data/test/pause_resume_test.rb
CHANGED
@@ -43,17 +43,17 @@ class PauseResumeTest < TestCase
|
|
43
43
|
assert_equal('PauseResumeTest#test_pause_resume', methods[2].full_name)
|
44
44
|
|
45
45
|
# Check times
|
46
|
-
assert_in_delta(0.2, methods[0].total_time, 0.
|
47
|
-
assert_in_delta(0, methods[0].wait_time, 0.
|
48
|
-
assert_in_delta(0, methods[0].self_time, 0.
|
46
|
+
assert_in_delta(0.2, methods[0].total_time, 0.02)
|
47
|
+
assert_in_delta(0, methods[0].wait_time, 0.02)
|
48
|
+
assert_in_delta(0, methods[0].self_time, 0.02)
|
49
49
|
|
50
|
-
assert_in_delta(0.2, methods[1].total_time, 0.
|
51
|
-
assert_in_delta(0, methods[1].wait_time, 0.
|
52
|
-
assert_in_delta(0.2, methods[1].self_time, 0.
|
50
|
+
assert_in_delta(0.2, methods[1].total_time, 0.02)
|
51
|
+
assert_in_delta(0, methods[1].wait_time, 0.02)
|
52
|
+
assert_in_delta(0.2, methods[1].self_time, 0.02)
|
53
53
|
|
54
|
-
assert_in_delta(0.2, methods[2].total_time, 0.
|
55
|
-
assert_in_delta(0, methods[2].wait_time, 0.
|
56
|
-
assert_in_delta(0, methods[2].self_time, 0.
|
54
|
+
assert_in_delta(0.2, methods[2].total_time, 0.02)
|
55
|
+
assert_in_delta(0, methods[2].wait_time, 0.02)
|
56
|
+
assert_in_delta(0, methods[2].self_time, 0.02)
|
57
57
|
end
|
58
58
|
|
59
59
|
# pause/resume in the same frame
|
data/test/printers_test.rb
CHANGED
@@ -11,7 +11,7 @@ class PrintersTest < TestCase
|
|
11
11
|
# WALL_TIME so we can use sleep in our test and get same measurements on linux and windows
|
12
12
|
RubyProf::measure_mode = RubyProf::WALL_TIME
|
13
13
|
@result = RubyProf.profile do
|
14
|
-
run_primes(
|
14
|
+
run_primes(1000, 5000)
|
15
15
|
end
|
16
16
|
end
|
17
17
|
|
@@ -0,0 +1,127 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
# encoding: UTF-8
|
3
|
+
|
4
|
+
require File.expand_path('../test_helper', __FILE__)
|
5
|
+
require 'stringio'
|
6
|
+
require 'fileutils'
|
7
|
+
|
8
|
+
# --- code to be tested ---
|
9
|
+
module PRGT
|
10
|
+
extend self
|
11
|
+
|
12
|
+
def f(n)
|
13
|
+
n.times { sleep 0.1 }
|
14
|
+
end
|
15
|
+
|
16
|
+
def g(n)
|
17
|
+
n.times { sleep 0.2 }
|
18
|
+
end
|
19
|
+
|
20
|
+
def run
|
21
|
+
2.times { f(2); g(4) }
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
# --- expected test output ---
|
26
|
+
=begin
|
27
|
+
Measure Mode: wall_time
|
28
|
+
Thread ID: 70238775664960
|
29
|
+
Fiber ID: 70238784046840
|
30
|
+
Total Time: 2.040249824523926
|
31
|
+
Sort by: total_time
|
32
|
+
|
33
|
+
%total %self total self wait child calls Name
|
34
|
+
--------------------------------------------------------------------------------
|
35
|
+
100.00% 0.00% 2.040 0.000 0.000 2.040 1 PrintingRecursiveGraphTest#setup
|
36
|
+
2.040 0.000 0.000 2.040 1/1 PRGT#run
|
37
|
+
--------------------------------------------------------------------------------
|
38
|
+
2.040 0.000 0.000 2.040 1/1 PrintingRecursiveGraphTest#setup
|
39
|
+
100.00% 0.00% 2.040 0.000 0.000 2.040 1 PRGT#run
|
40
|
+
2.040 0.000 0.000 2.040 1/5 Integer#times
|
41
|
+
--------------------------------------------------------------------------------
|
42
|
+
0.409 0.000 0.000 0.409 2/5 Prgt#f
|
43
|
+
1.631 0.000 0.000 1.631 2/5 PRGT#g
|
44
|
+
2.040 0.000 0.000 2.040 1/5 PRGT#run
|
45
|
+
100.00% 0.00% 2.040 0.000 0.000 2.040 5 *Integer#times
|
46
|
+
2.040 2.040 0.000 0.000 12/12 Kernel#sleep
|
47
|
+
1.631 0.000 0.000 1.631 2/2 PRGT#g
|
48
|
+
0.409 0.000 0.000 0.409 2/2 PRGT#f
|
49
|
+
--------------------------------------------------------------------------------
|
50
|
+
2.040 2.040 0.000 0.000 12/12 Integer#times
|
51
|
+
99.99% 99.99% 2.040 2.040 0.000 0.000 12 Kernel#sleep
|
52
|
+
--------------------------------------------------------------------------------
|
53
|
+
1.631 0.000 0.000 1.631 2/2 Integer#times
|
54
|
+
79.94% 0.00% 1.631 0.000 0.000 1.631 2 PRGT#g
|
55
|
+
1.631 0.000 0.000 1.631 2/5 Integer#times
|
56
|
+
--------------------------------------------------------------------------------
|
57
|
+
0.409 0.000 0.000 0.409 2/2 Integer#times
|
58
|
+
20.05% 0.00% 0.409 0.000 0.000 0.409 2 PRGT#f
|
59
|
+
0.409 0.000 0.000 0.409 2/5 Integer#times
|
60
|
+
|
61
|
+
* indicates recursively called methods
|
62
|
+
=end
|
63
|
+
|
64
|
+
class PrintingRecursiveGraphTest < TestCase
|
65
|
+
include PrinterTestHelper
|
66
|
+
|
67
|
+
def setup
|
68
|
+
# WALL_TIME so we can use sleep in our test and get same measurements on linux and windows
|
69
|
+
RubyProf::measure_mode = RubyProf::WALL_TIME
|
70
|
+
@result = RubyProf.profile do
|
71
|
+
PRGT.run
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
def test_printing_rescursive_graph
|
76
|
+
printer = RubyProf::GraphPrinter.new(@result)
|
77
|
+
|
78
|
+
buffer = ''
|
79
|
+
printer.print(StringIO.new(buffer))
|
80
|
+
|
81
|
+
puts buffer if ENV['SHOW_RUBY_PROF_PRINTER_OUTPUT'] == "1"
|
82
|
+
|
83
|
+
parsed_output = MetricsArray.parse(buffer)
|
84
|
+
|
85
|
+
assert( integer_times = parsed_output.metrics_for("*Integer#times") )
|
86
|
+
|
87
|
+
actual_parents = integer_times.parents.map(&:name)
|
88
|
+
expected_parents = %w(PRGT#f PRGT#g PRGT#run)
|
89
|
+
assert_equal expected_parents, actual_parents
|
90
|
+
|
91
|
+
actual_children = integer_times.children.map(&:name)
|
92
|
+
expected_children = %w(Kernel#sleep PRGT#g PRGT#f)
|
93
|
+
assert_equal expected_children, actual_children
|
94
|
+
|
95
|
+
assert( fp = integer_times.parent("PRGT#f") )
|
96
|
+
assert_in_delta(fp.total, fp.child, 0.01)
|
97
|
+
assert_equal("2/5", fp.calls)
|
98
|
+
|
99
|
+
assert( gp = integer_times.parent("PRGT#g") )
|
100
|
+
assert_in_delta(gp.total, gp.child, 0.01)
|
101
|
+
assert_equal("2/5", gp.calls)
|
102
|
+
|
103
|
+
assert( rp = integer_times.parent("PRGT#run") )
|
104
|
+
assert_in_delta(rp.total, rp.child, 0.01)
|
105
|
+
assert_equal("1/5", rp.calls)
|
106
|
+
|
107
|
+
assert_in_delta(4*fp.total, gp.total, 0.05)
|
108
|
+
assert_in_delta(fp.total + gp.total, rp.total, 0.05)
|
109
|
+
assert_in_delta(integer_times.metrics.total, rp.total, 0.05)
|
110
|
+
|
111
|
+
assert( fc = integer_times.child("PRGT#f") )
|
112
|
+
assert_in_delta(fc.total, fc.child, 0.01)
|
113
|
+
assert_equal("2/2", fc.calls)
|
114
|
+
|
115
|
+
assert( gc = integer_times.child("PRGT#g") )
|
116
|
+
assert_in_delta(gc.total, gc.child, 0.01)
|
117
|
+
assert_equal("2/2", gc.calls)
|
118
|
+
|
119
|
+
assert( ks = integer_times.child("Kernel#sleep") )
|
120
|
+
assert_in_delta(ks.total, ks.self_t, 0.01)
|
121
|
+
assert_equal("12/12", ks.calls)
|
122
|
+
|
123
|
+
assert_in_delta(4*fc.total, gc.total, 0.05)
|
124
|
+
assert_in_delta(fp.total + gc.total, ks.total, 0.05)
|
125
|
+
assert_in_delta(integer_times.metrics.total, ks.total, 0.05)
|
126
|
+
end
|
127
|
+
end
|