private_please 0.0.3 → 0.0.4

Sign up to get free protection for your applications and to get access to all the features.
Files changed (49) hide show
  1. data/.gitignore +0 -1
  2. data/.travis.yml +10 -0
  3. data/CHANGELOG +8 -0
  4. data/README.md +92 -42
  5. data/bin/pp_ruby +62 -0
  6. data/bin/ruby_pp +62 -0
  7. data/doc/dev_notes.txt +32 -0
  8. data/doc/fixtures/complex.rb +103 -0
  9. data/doc/fixtures/empty_class.rb +7 -0
  10. data/doc/fixtures/fixture_helper.rb +8 -0
  11. data/doc/fixtures/sample.rb +57 -0
  12. data/lib/private_please/candidate.rb +10 -2
  13. data/lib/private_please/report/table.rb +44 -0
  14. data/lib/private_please/report.rb +6 -0
  15. data/lib/private_please/reporter/base.rb +28 -0
  16. data/lib/private_please/reporter/helpers/options_helpers.rb +12 -0
  17. data/lib/private_please/reporter/helpers/text_table_helpers.rb +9 -0
  18. data/lib/private_please/{report/reporter.rb → reporter/simple_text.rb} +12 -18
  19. data/lib/private_please/reporter/templates/simple.txt.erb +77 -0
  20. data/lib/private_please/reporter.rb +8 -0
  21. data/lib/private_please/storage/methods_names.rb +1 -0
  22. data/lib/private_please/storage.rb +8 -0
  23. data/lib/private_please/tracking/extension.rb +3 -10
  24. data/lib/private_please/tracking/instrumentor.rb +13 -35
  25. data/lib/private_please/tracking/instruments_all_methods_below.rb +28 -0
  26. data/lib/private_please/tracking/instruments_automatically_all_methods_in_all_classes.rb +52 -0
  27. data/lib/private_please/tracking/line_change_tracker.rb +8 -18
  28. data/lib/private_please/tracking/utils.rb +34 -0
  29. data/lib/private_please/tracking.rb +48 -0
  30. data/lib/private_please/version.rb +1 -1
  31. data/lib/private_please.rb +27 -44
  32. data/private_please.gemspec +7 -1
  33. data/spec/{01_marking_candidate_methods_to_observe_spec.rb → 01_tracking_candidate_methods/explicitely_with_the_private_please_command_spec.rb} +35 -70
  34. data/spec/01_tracking_candidate_methods/systematically_in_auto_mode_spec.rb +187 -0
  35. data/spec/{02_logging_calls_on_candidate_methods_spec.rb → 03_logging_calls_on_candidate_methods_spec.rb} +2 -4
  36. data/spec/04_instrumented_program_activity_observation_result_spec.rb +2 -5
  37. data/spec/05_reporting/report_table_spec.rb +51 -0
  38. data/spec/06_at_exit_spec.rb +18 -0
  39. data/spec/fixtures/bug_22.rb +17 -0
  40. data/spec/fixtures/sample_class_for_report.rb +2 -0
  41. data/spec/sandbox/Gemfile +4 -0
  42. data/spec/sandbox/Gemfile.lock +14 -0
  43. data/spec/sandbox/README.txt +26 -0
  44. data/spec/sandbox/normal.rb +7 -0
  45. data/spec/sandbox/normal_prepended_with_require.rb +8 -0
  46. data/spec/spec_helper.rb +6 -2
  47. metadata +50 -13
  48. data/lib/private_please/report/templates/simple.txt.erb +0 -61
  49. data/lib/private_please/tracking/instruments_all_below.rb +0 -41
data/.gitignore CHANGED
@@ -7,7 +7,6 @@ Gemfile.lock
7
7
  InstalledFiles
8
8
  _yardoc
9
9
  coverage
10
- doc/
11
10
  lib/bundler/man
12
11
  pkg
13
12
  rdoc
data/.travis.yml ADDED
@@ -0,0 +1,10 @@
1
+ language: ruby
2
+ rvm:
3
+ - "1.8.7"
4
+ - "1.9.3"
5
+ - "2.0.0"
6
+ - jruby-18mode # JRuby in 1.8 mode
7
+ - jruby-19mode # JRuby in 1.9 mode
8
+
9
+ # uncomment this line if your project needs to run something other than `rake`:
10
+ script: bundle exec rspec
data/CHANGELOG CHANGED
@@ -1,3 +1,11 @@
1
+ v0.0.4
2
+ - `private_please :foo, :bar` syntax is removed.
3
+ - auto-mode via `$ pp_ruby`
4
+ - improved report format (2 columns, empty sections are hidden, ..)
5
+ - report can be customized with PP_OPTIONS
6
+ - tested with 3 Ruby and 2 JRuby versions (Travis CI)
7
+ - big code cleanup (development)
8
+
1
9
  v0.0.3
2
10
  - private_please without parameters observes all the methods defined afterwards
3
11
  - PP is active once you require the gem
data/README.md CHANGED
@@ -1,70 +1,120 @@
1
- # PrivatePlease
1
+ [![Build Status](https://travis-ci.org/alainravet/private_please.png?branch=master)](https://travis-ci.org/alainravet/private_please) -
2
+ [![Code Climate](https://codeclimate.com/github/alainravet/private_please.png)](https://codeclimate.com/github/alainravet/private_please)
3
+ tested with Ruby (1.8.7, 1.9.3, and 2.0.0) and JRuby(1.8 and 1.9 mode) - see [.travis.yml](.travis.yml)
2
4
 
3
- limitation : Ruby 1.8.7
5
+ ## TL;DR :
6
+ Given this code
7
+ ```ruby
8
+ # file : big_code
9
+ class BigCode
10
+ def long_method # the only method that should be public
11
+ _part_1
12
+ _part_2
13
+ end
4
14
 
5
- ## Installation
15
+ # PROBLEM : Those 2 methods were extracted and should be private
16
+ def _part_1
17
+ # ....
18
+ end
19
+ def _part_2
20
+ # ....
21
+ end
22
+ end
23
+ BigCode.new.long_method
24
+ ```
25
+ When you run this command
26
+ ```
27
+ $ pp_ruby big_code
28
+ ^^^
29
+ ```
30
+ Then the methods usage is tracked while the program runs and this findings report is output:
31
+ ```
32
+ ====================================================================================
33
+ = PrivatePlease report : =
34
+ ====================================================================================
35
+ BigCode
6
36
 
7
- Add this line to your application's Gemfile:
37
+ * Good candidates : can be made private :
38
+ ------------------------------------------
39
+ #_part_2
40
+ #_part_1
8
41
 
9
- gem 'private_please'
42
+ ====================================================================================
43
+ ```
10
44
 
11
- ## Usage
45
+ ## Installation
46
+ ```
47
+ $ gem install private_please
48
+ ```
12
49
 
13
- ```ruby
50
+ ## Usage : the 2 modes (auto and manual)
14
51
 
15
- require 'private_please' # step 1
52
+ You can use *private_please* (*PP*) in either **auto-mode** or in **manual mode**.
53
+ Optionally you can customize the report contents with the env. variable ```PP_OPTIONS```.
16
54
 
17
- class CouldBeMorePrivate
18
- def to_s # not observed -> won't appear in the report.
19
- # ...
20
- end
55
+ - in **auto-mode** (the example above in TL;DR), you simply run your program with ```pp_ruby``` (instead of ```ruby```) and all your code is inspected by *PP* while it runs.
56
+ - in **manual mode** you must manually instrument (==add code to) each file you want *PP* to track and inspect.
21
57
 
22
- private_please # step 2 : start observing
23
58
 
24
- def do_the_thing # is called by class' users => must stay public (case #1)
25
- part_1
26
- part_2
27
- end
28
- def part_1 ; end # only called by #do_the_thing => should be private (case #2)
29
- def part_2 ; end # only called by #do_the_thing => should be private (case #2)
59
+ ### Auto-mode
60
+ PP will run the program and track all the classes and methods that are defined.
30
61
 
31
- def part_3 ; end # is never used -> will be detected. (case #3)
32
- end
62
+ How to :
63
+ - step 1 : use ```pp_ruby``` instead of ```ruby```.
33
64
 
34
- c = CouldBeMorePrivate.new
35
- c.do_the_thing # step 3 : execute the code, so PP can observe and deduce.
65
+ Example :
66
+ ```
67
+ $ bundle exec pp_ruby -Ilib normal.rb
68
+ ^^^
36
69
  ```
37
- A report is automatically printed in the console when the program exits.
38
- For the code above, the report would be :
70
+ A report is automatically printed when the program exits
39
71
 
40
- ====================================================================================
41
- = PrivatePlease report : =
42
- ====================================================================================
43
72
 
44
- **********************************************************
45
- CouldBeMorePrivate
46
- **********************************************************
73
+ ### Manual mode
74
+ You tell PP which classes and which methods to track.
47
75
 
48
- * Good candidates : can be made private :
49
- ------------------------------------------
76
+ How to :
77
+ - step 1 : Instrument your Ruby code
78
+ - step 2 : launch program as usual, with ```ruby```.
79
+
80
+
81
+ Example :
82
+ #### step 1 : Instrument your code
83
+ ```ruby
84
+ # load PP
85
+ require 'private_please' <<<<<<< ADD THIS (only 1x in the whole program)
86
+ PrivatePlease.pp_automatic_mode_disable <<<<<<< " " " " " " " " "
50
87
 
51
- #part_1
52
- #part_2
88
+ class BigCode
53
89
 
54
- * Bad candidates : must stay public/protected
55
- ------------------------------------------
90
+ private_please << ~~ JUST ADD THIS in every file you want PP to inspect
91
+ <<
92
+ << Meaning : "track the code below"
56
93
 
57
- #do_the_thing
94
+ def long_method # the only method that should be public
95
+ _part_1
96
+ _part_2
97
+ end
58
98
 
59
- * Methods that were never called
60
- ------------------------------------------
99
+ def _part_1
100
+ # ....
101
+ end
102
+ def _part_2
103
+ # ....
104
+ end
105
+ end
61
106
 
62
- #part_3
107
+ BigCode.new.long_method
108
+ ```
63
109
 
64
- ====================================================================================
110
+ ####step 2 : run you code normally
111
+ ```
112
+ $ ruby big_code.rb
113
+ ```
65
114
 
66
115
 
67
116
  ## Contributing
117
+ **Please respect and reuse the current code style and formatting**
68
118
 
69
119
  1. Fork it
70
120
  2. Create your feature branch (`git checkout -b my-new-feature`)
data/bin/pp_ruby ADDED
@@ -0,0 +1,62 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ # ----------------------------------------------------------------------------------- #
4
+ # Effects : inject PrivatePlease tracking in the command #
5
+ # ----------------------------------------------------------------------------------- #
6
+ # $ pp_ruby normal.rb #
7
+ # $ bundle exec pp_ruby normal.rb #
8
+ # become #
9
+ # $ ruby -rubygems -e "require 'private_please' ; load 'normal.rb'" #
10
+ # $ bundle exec ruby -e "require 'private_please' ; load 'normal.rb'" #
11
+ # ----------------------------------------------------------------------------------- #
12
+
13
+
14
+ ########################
15
+ # Extract command parts :
16
+ ########################
17
+
18
+ switches, filename, arguments = [], nil, []
19
+ loop do
20
+ case ARGV[0]
21
+ when '-r' then switches << ARGV.shift << ARGV.shift
22
+ when '-e' then switches << ARGV.shift << ARGV.shift.inspect
23
+ when /^-\S/ then switches << ARGV.shift
24
+ else break
25
+ end
26
+ end
27
+ filename = ARGV.shift
28
+ arguments = ARGV
29
+
30
+
31
+ ######################
32
+ # Assemble new command :
33
+ ######################
34
+
35
+ # ? called with `bundle exec ruby .....`
36
+ in_bundler_mode = !!defined?(Bundler)
37
+
38
+ program = in_bundler_mode ?
39
+ 'bundle exec ruby' :
40
+ 'ruby'
41
+
42
+ command = if filename
43
+ rubygems_or_not = in_bundler_mode ? nil : " -rubygems"
44
+ [ program,
45
+ switches,
46
+ %|#{rubygems_or_not} -e "require 'private_please' ; load '#{filename}'"| ,
47
+ arguments
48
+ ]
49
+ else
50
+ [ program,
51
+ switches,
52
+ arguments
53
+ ]
54
+ end.flatten.compact.join(' ')
55
+
56
+
57
+ #############################
58
+ # Execute transformed command :
59
+ #############################
60
+
61
+ puts "Executing: #{command}"
62
+ puts `#{command}`
data/bin/ruby_pp ADDED
@@ -0,0 +1,62 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ # ----------------------------------------------------------------------------------- #
4
+ # Effects : inject PrivatePlease tracking in the command #
5
+ # ----------------------------------------------------------------------------------- #
6
+ # $ pp_ruby normal.rb #
7
+ # $ bundle exec pp_ruby normal.rb #
8
+ # become #
9
+ # $ ruby -rubygems -e "require 'private_please' ; load 'normal.rb'" #
10
+ # $ bundle exec ruby -e "require 'private_please' ; load 'normal.rb'" #
11
+ # ----------------------------------------------------------------------------------- #
12
+
13
+
14
+ ########################
15
+ # Extract command parts :
16
+ ########################
17
+
18
+ switches, filename, arguments = [], nil, []
19
+ loop do
20
+ case ARGV[0]
21
+ when '-r' then switches << ARGV.shift << ARGV.shift
22
+ when '-e' then switches << ARGV.shift << ARGV.shift.inspect
23
+ when /^-\S/ then switches << ARGV.shift
24
+ else break
25
+ end
26
+ end
27
+ filename = ARGV.shift
28
+ arguments = ARGV
29
+
30
+
31
+ ######################
32
+ # Assemble new command :
33
+ ######################
34
+
35
+ # ? called with `bundle exec ruby .....`
36
+ in_bundler_mode = !!defined?(Bundler)
37
+
38
+ program = in_bundler_mode ?
39
+ 'bundle exec ruby' :
40
+ 'ruby'
41
+
42
+ command = if filename
43
+ rubygems_or_not = in_bundler_mode ? nil : " -rubygems"
44
+ [ program,
45
+ switches,
46
+ %|#{rubygems_or_not} -e "require 'private_please' ; load '#{filename}'"| ,
47
+ arguments
48
+ ]
49
+ else
50
+ [ program,
51
+ switches,
52
+ arguments
53
+ ]
54
+ end.flatten.compact.join(' ')
55
+
56
+
57
+ #############################
58
+ # Execute transformed command :
59
+ #############################
60
+
61
+ puts "Executing: #{command}"
62
+ puts `#{command}`
data/doc/dev_notes.txt ADDED
@@ -0,0 +1,32 @@
1
+ Q: Where is the TODO list :
2
+ A: https://github.com/alainravet/private_please/issues?state=open
3
+
4
+ How to run the tests :
5
+ ========================
6
+
7
+ $ cd <project root>
8
+ $ bundle exec rspec
9
+ or
10
+ $ bundle exec guard # (see https://github.com/alainravet/private_please/issues/10)
11
+
12
+
13
+ How to test on multiple versions of Ruby :
14
+ ============================================
15
+ # install rbenv + multiple versions of Ruby
16
+ # install the rbenv-each plugin
17
+ $ rbenv each -v bundle exec ruby -Ilib rspec
18
+
19
+
20
+ How to run the latest PP code on a custom Ruby code sample :
21
+ ======================================================
22
+
23
+ $ cd <project root>
24
+ $ bundle exec ruby -Ilib doc/fixtures/complex.rb
25
+
26
+ How to display more than the list of methods that can be made private ?
27
+ ======================================================
28
+
29
+ $ export PP_OPTIONS="--show-bad-candidates --show-never-called"
30
+ $ bundle exec ruby -Ilib doc/fixtures/complex.rb
31
+ or
32
+ $ PP_OPTIONS="--show-bad-candidates --show-never-called" bundle exec ruby -Ilib doc/fixtures/complex.rb
@@ -0,0 +1,103 @@
1
+ load File.dirname(__FILE__) + '/fixture_helper.rb'
2
+
3
+ module ComplexReport
4
+
5
+ class Class1
6
+ def initialize
7
+ super
8
+ end
9
+ def sole_entry_point
10
+ instance_m_1
11
+ self.class.class_m_1
12
+ self.class.c_make_internal_method_calls
13
+ end
14
+
15
+ def instance_m_1; end
16
+ def instance_m_2; end
17
+
18
+ def self.class_m_1;
19
+ class_m_2
20
+ end
21
+ def self.class_m_2; end
22
+
23
+
24
+ def self.c_make_internal_method_calls
25
+ class_m_1
26
+ new.instance_m_2
27
+ end
28
+ end
29
+
30
+ end
31
+
32
+ #-----------------------------------------------------------------------------------------------------------------------
33
+
34
+ ComplexReport::Class1.new.sole_entry_point
35
+
36
+ module ComplexReport
37
+ ###########################################
38
+ class Simple # Internal calls : #
39
+ # -> called methods are _GOOD CANDIDATES_ #
40
+ def make_internal_calls ###########################################
41
+ instance_m_1 # i -> i
42
+ self.class.class_m_1 # i -> C
43
+ self.class.c_make_internal_method_calls # i -> C --> C
44
+ end # +-> i
45
+
46
+ def self.c_make_internal_method_calls #
47
+ class_m_1 # C -> C
48
+ new.instance_m_2 # C -> i
49
+ end #
50
+ end
51
+
52
+ #######################################################
53
+ class AnotherClass # External calls (would fail if methods were private) #
54
+ # -> called methods are _BAD CANDIDATES_ #
55
+ def make_external_calls #######################################################
56
+ Simple.new.instance_m_1 # i -> i
57
+ Simple .class_m_1 # i -> C
58
+ self.class.c_make_external_calls # i -> C -> i
59
+ end # -> C
60
+ def self.c_make_external_calls #
61
+ Simple.new.instance_m_1 # C -> i
62
+ Simple .class_m_1 # C -> C
63
+ end #
64
+ def call_the_candidate_from_inside_and_outside
65
+ make_external_calls
66
+ Simple.new.make_internal_calls
67
+ Simple.a_class_method_via_module_Extra
68
+ end
69
+ end
70
+
71
+ #-----------------------------------------------------------------------------------------------------------------------
72
+ module Extra
73
+ def self.included(base)
74
+ base.extend(ClassMethods)
75
+ end
76
+ def im_never_called ; raise; end
77
+ module ClassMethods
78
+ def a_class_method_via_module_Extra ; end
79
+ end
80
+ end
81
+
82
+
83
+ class Simple
84
+ def self.not_a_candidate_c1;
85
+ class_m_2
86
+ end
87
+
88
+ include Extra
89
+ def instance_m_1; end
90
+ def instance_m_2; end
91
+
92
+ def self.class_m_1;
93
+ class_m_2
94
+ end
95
+ def self.class_m_2; end
96
+
97
+ def never_called_1; end
98
+ def self.class_never_called_1; end
99
+ end
100
+ #-----------------------------------------------------------------------------------------------------------------------
101
+ end
102
+
103
+ ComplexReport::AnotherClass.new.call_the_candidate_from_inside_and_outside
@@ -0,0 +1,7 @@
1
+ require File.dirname(__FILE__) + '/fixture_helper.rb'
2
+ load File.dirname(__FILE__) + '/fixture_helper.rb'
3
+
4
+ module ReportSample
5
+ class EmptyClass
6
+ end
7
+ end
@@ -0,0 +1,8 @@
1
+ begin
2
+ # for $ bundle exec ruby -r private_please doc/fixtures/empty_class.r
3
+ PrivatePlease::Storage
4
+ rescue NameError
5
+ # for $ bundle exec ruby -Ilib doc/fixtures/empty_class.r
6
+ require 'private_please'
7
+ end
8
+ PrivatePlease.pp_automatic_mode_enable
@@ -0,0 +1,57 @@
1
+ load File.dirname(__FILE__) + '/fixture_helper.rb'
2
+
3
+ module ReportSample
4
+ ###########################################
5
+ class Simple # Internal calls : #
6
+ # -> called methods are _GOOD CANDIDATES_ #
7
+ def make_internal_calls ###########################################
8
+ instance_m_1 # i -> i
9
+ self.class.class_m_1 # i -> C
10
+ self.class.c_make_internal_method_calls # i -> C --> C
11
+ end # +-> i
12
+
13
+ def self.c_make_internal_method_calls #
14
+ class_m_1 # C -> C
15
+ new.instance_m_2 # C -> i
16
+ end #
17
+ end
18
+
19
+ #######################################################
20
+ class AnotherClass # External calls (would fail if methods were private) #
21
+ # -> called methods are _BAD CANDIDATES_ #
22
+ def make_external_calls #######################################################
23
+ Simple.new.instance_m_1 # i -> i
24
+ Simple .class_m_1 # i -> C
25
+ self.class.c_make_external_calls # i -> C -> i
26
+ end # -> C
27
+ def self.c_make_external_calls #
28
+ Simple.new.instance_m_1 # C -> i
29
+ Simple .class_m_1 # C -> C
30
+ end #
31
+ def call_the_candidate_from_inside_and_outside
32
+ make_external_calls
33
+ Simple.new.make_internal_calls
34
+ end
35
+ end
36
+
37
+ #-----------------------------------------------------------------------------------------------------------------------
38
+ class Simple
39
+ def self.not_a_candidate_c1;
40
+ class_m_2
41
+ end
42
+
43
+ def instance_m_1; end
44
+ def instance_m_2; end
45
+
46
+ def self.class_m_1;
47
+ class_m_2
48
+ end
49
+ def self.class_m_2; end
50
+
51
+ def never_called_1; end
52
+ def self.class_never_called_1; end
53
+ end
54
+ end
55
+ #-----------------------------------------------------------------------------------------------------------------------
56
+
57
+ ReportSample::Simple.new.make_internal_calls
@@ -28,13 +28,21 @@ module PrivatePlease
28
28
  alias_method :instance_method?, :is_instance_method
29
29
 
30
30
  def already_instrumented?
31
- candidates_store.stored?(self)
31
+ instrumented_candidates_store.stored?(self)
32
32
  end
33
33
 
34
+ #----------------------------------------------------------------------------
35
+ # SUGAR:
36
+ #----------------------------------------------------------------------------
37
+
38
+ def mark_as_instrumented
39
+ instrumented_candidates_store.store(self)
40
+ end
41
+
34
42
  #----------------------------------------------------------------------------
35
43
  private
36
44
 
37
- def candidates_store
45
+ def instrumented_candidates_store
38
46
  PrivatePlease.candidates_store
39
47
  end
40
48
  end
@@ -0,0 +1,44 @@
1
+ module PrivatePlease::Report
2
+
3
+ class Table
4
+
5
+ def initialize(col_1, col_2)
6
+ @col_1, @col_2 = col_1, col_2
7
+
8
+ prepare_data
9
+ end
10
+
11
+ #----------------------------------------------------------------------------
12
+ # QUERIES:
13
+ #----------------------------------------------------------------------------
14
+
15
+ attr_reader :col_1,
16
+ :col_2,
17
+ :rows,
18
+ :longest_value_length
19
+
20
+ def empty?
21
+ col_1.empty? && col_2.empty?
22
+ end
23
+
24
+ #----------------------------------------------------------------------------
25
+ # COMMANDS:
26
+ #----------------------------------------------------------------------------
27
+
28
+ # none (immutable)
29
+
30
+ #----------------------------------------------------------------------------
31
+ private
32
+
33
+ def prepare_data
34
+ @longest_value_length = [col_1 + col_2].flatten.map(&:length).max || 0
35
+
36
+ # pad whichever column is shorter
37
+ @col_1[@col_2.length-1] ||= nil unless @col_2.empty?
38
+ @col_2[@col_1.length-1] ||= nil unless @col_1.empty?
39
+
40
+ @rows = @col_1.zip(@col_2)
41
+ end
42
+
43
+ end
44
+ end
@@ -0,0 +1,6 @@
1
+ module PrivatePlease
2
+ module Report
3
+ end
4
+ end
5
+
6
+ require File.dirname(__FILE__) + '/report/table'
@@ -0,0 +1,28 @@
1
+ module PrivatePlease ; module Reporter
2
+
3
+ class Base
4
+
5
+ attr_reader :candidates_store, :calls_store,
6
+ :good_candidates, :bad_candidates,
7
+ :good_candidates_c, :bad_candidates_c,
8
+ :never_called_candidates, :never_called_candidates_c,
9
+ :building_time
10
+
11
+
12
+ def initialize(candidates_store, calls_store)
13
+ @candidates_store = candidates_store
14
+ @calls_store = calls_store
15
+
16
+ start_time = Time.now
17
+ prepare_report_data
18
+ @building_time = Time.now - start_time
19
+ end
20
+
21
+ private
22
+
23
+ def prepare_report_data
24
+ raise "prepare_report_data() ot implemented in the child class"
25
+ end
26
+ end
27
+
28
+ end end
@@ -0,0 +1,12 @@
1
+
2
+ def show_never_called_candidates_section?
3
+ ENV['PP_OPTIONS'] =~ /--show-never-called/
4
+ end
5
+
6
+ def show_bad_candidates_section?
7
+ ENV['PP_OPTIONS'] =~ /--show-bad-candidates/
8
+ end
9
+
10
+ def show_empty_classes?
11
+ ENV['PP_OPTIONS'] =~ /--show-empty-classes/
12
+ end
@@ -0,0 +1,9 @@
1
+
2
+ def table_for(col_1, col_2)
3
+ PrivatePlease::Report::Table.new(col_1, col_2)
4
+ end
5
+
6
+ def names_from(class_name, candidates, prefix)
7
+ candidates.get_methods_names(class_name).collect{|n|"#{prefix}#{n}"}
8
+ end
9
+