detective 0.2.0 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
data/README.rdoc CHANGED
@@ -1,6 +1,6 @@
1
1
  = detective
2
2
 
3
- Detective is a gem build by BadrIT (http://www.badrit.com/) to investigate the ruby source code.
3
+ Detective is a gem built by BadrIT (http://www.badrit.com/) to investigate the ruby source code.
4
4
  Check the examples below.
5
5
 
6
6
  == Motivation
@@ -9,6 +9,9 @@ Not able to know who and where that function has been overrided?
9
9
  It's time to get help from a private Detective.
10
10
  Detective allows you show the source and find the location of some ruby method.
11
11
 
12
+ == Installation
13
+ gem install detective
14
+
12
15
  == Examples
13
16
  View the source of a class method ...
14
17
  require 'detective'
@@ -67,12 +70,49 @@ Result
67
70
  (new) You have an alternative output ...
68
71
  Detective.view_source('AuthenticatedSystem#current_user', :rdoc)
69
72
 
70
- Result
73
+ Result
71
74
  /home/aseldawy/aptana_studio/archiving_system/lib/authenticated_system.rb, line 11
72
75
  11: def current_user
73
76
  12: @current_user ||= (login_from_session || login_from_basic_auth || login_from_cookie) unless @current_user == false
74
77
  13: end
75
78
 
79
+ (new) Detective is now also working with method_missing ...
80
+ Detective.view_source('ActiveRecord::Base#find_by_id')
81
+
82
+ Result
83
+ def method_missing(method_id, *args, &block)
84
+ method_name = method_id.to_s
85
+
86
+ if self.class.private_method_defined?(method_name)
87
+ raise NoMethodError.new("Attempt to call private method", method_name, args)
88
+ end
89
+
90
+ # If we haven't generated any methods yet, generate them, then
91
+ # see if we've created the method we're looking for.
92
+ if !self.class.generated_methods?
93
+ self.class.define_attribute_methods
94
+ if self.class.generated_methods.include?(method_name)
95
+ return self.send(method_id, *args, &block)
96
+ end
97
+ end
98
+
99
+ if self.class.primary_key.to_s == method_name
100
+ id
101
+ elsif md = self.class.match_attribute_method?(method_name)
102
+ attribute_name, method_type = md.pre_match, md.to_s
103
+ if @attributes.include?(attribute_name)
104
+ __send__("attribute#{method_type}", attribute_name, *args, &block)
105
+ else
106
+ super
107
+ end
108
+ elsif @attributes.include?(method_name)
109
+ read_attribute(method_name)
110
+ else
111
+ super
112
+ end
113
+ end
114
+
115
+
76
116
  No luck with native methods ...
77
117
  Detective.view_source('String#length')
78
118
 
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.2.0
1
+ 0.3.0
data/detective.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{detective}
8
- s.version = "0.2.0"
8
+ s.version = "0.3.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Ahmed ElDawy"]
12
- s.date = %q{2009-11-21}
12
+ s.date = %q{2009-11-22}
13
13
  s.description = %q{A ruby gem built by BadrIT (http://www.badrit.com/) that allows you to view the source code of a method}
14
14
  s.email = %q{ahmed.eldawy@badrit.com}
15
15
  s.extra_rdoc_files = [
data/lib/detective.rb CHANGED
@@ -70,11 +70,6 @@ module Detective
70
70
  private
71
71
 
72
72
  def self.get_location_thread(the_klass, method_name, class_method)
73
- if class_method
74
- raise "Invalid class method name #{method_name} for class #{the_klass}" unless the_klass.respond_to? method_name
75
- else
76
- raise "Invalid instance method name #{method_name} for class #{the_klass}" unless the_klass.instance_methods.include? method_name
77
- end
78
73
  result = ""
79
74
  t = Thread.new do
80
75
  begin
@@ -144,9 +139,14 @@ private
144
139
  the_method.call *args
145
140
  # If the next line executed, this indicates an error because the method should be cancelled before called
146
141
  puts "method called!"
147
- rescue => e
142
+ rescue NoMethodError => e
143
+ puts "No method found #{method_name}"
144
+ puts e.inspect
145
+ puts e.backtrace.join("\n")
146
+ rescue Exception => e
148
147
  puts "error"
149
148
  puts e.inspect
149
+ puts e.backtrace.join("\n")
150
150
  ensure
151
151
  exit!
152
152
  end
@@ -175,7 +175,7 @@ private
175
175
  the_method = the_klass.new.method(method_name)
176
176
  # Revert initialize method
177
177
  the_klass.class_eval do
178
- # under causes a warning
178
+ # undef causes a warning with :initialize
179
179
  # undef initialize
180
180
  alias initialize old_initialize
181
181
  end
@@ -191,6 +191,17 @@ private
191
191
 
192
192
  # Return the method and its parameters
193
193
  [the_method, Array.new(required_args)]
194
+ rescue NameError => e
195
+ if method_name != 'method_missing' &&
196
+ (
197
+ class_method && the_klass.respond_to?(:method_missing) ||
198
+ !class_method && the_klass.instance_methods.include?('method_missing')
199
+ )
200
+ method_name = 'method_missing'
201
+ retry
202
+ else
203
+ raise
204
+ end
194
205
  end
195
206
 
196
207
  end
@@ -4,9 +4,21 @@ class BadrIT
4
4
  def self.hello
5
5
  puts "hello BadrIT"
6
6
  end
7
- end
8
- module IPhone; end
9
7
 
8
+ def hi
9
+ puts "hi BadrIT"
10
+ end
11
+ end
12
+
13
+ module IPhone
14
+ end
15
+
16
+ class SomeClass
17
+ def method_missing(args)
18
+ puts "no method called #{args}"
19
+ end
20
+ end
21
+
10
22
 
11
23
  class TestDetective < Test::Unit::TestCase
12
24
  def test_simple_method
@@ -31,14 +43,8 @@ class TestDetective < Test::Unit::TestCase
31
43
  end
32
44
 
33
45
  def test_instance_method
34
- BadrIT.class_eval do
35
- def test
36
- puts "testing"
37
- end
38
- end
39
-
40
- source = Detective.view_source('BadrIT#test')
41
- assert_equal 'def test puts "testing" end', source.gsub(/\s+/, ' ').strip
46
+ source = Detective.view_source('BadrIT#hi')
47
+ assert_equal 'def hi puts "hi BadrIT" end', source.gsub(/\s+/, ' ').strip
42
48
  end
43
49
 
44
50
  def test_method_with_args
@@ -93,14 +99,9 @@ class TestDetective < Test::Unit::TestCase
93
99
  def test_using_threads
94
100
  fork_supported = Detective.const_get(:ForkSupported)
95
101
  Detective.const_set(:ForkSupported, false)
96
- BadrIT.class_eval do
97
- def self.noway
98
- puts "Go away"
99
- end
100
- end
101
102
 
102
- source = Detective.view_source('BadrIT.noway')
103
- assert_equal 'def self.noway puts "Go away" end', source.gsub(/\s+/, ' ').strip
103
+ source = Detective.view_source('BadrIT.hello')
104
+ assert_equal 'def self.hello puts "hello BadrIT" end', source.gsub(/\s+/, ' ').strip
104
105
 
105
106
  Detective.const_set(:ForkSupported, fork_supported)
106
107
  end
@@ -109,14 +110,10 @@ class TestDetective < Test::Unit::TestCase
109
110
  BadrIT.class_eval do
110
111
  def initialize(arg0, arg1, arg2)
111
112
  end
112
-
113
- def some_method
114
- puts "me myself"
115
- end
116
113
  end
117
114
 
118
- source = Detective.view_source('BadrIT#some_method')
119
- assert_equal 'def some_method puts "me myself" end', source.gsub(/\s+/, ' ').strip
115
+ source = Detective.view_source('BadrIT#hi')
116
+ assert_equal 'def hi puts "hi BadrIT" end', source.gsub(/\s+/, ' ').strip
120
117
  end
121
118
 
122
119
  def test_method_with_eval
@@ -153,4 +150,34 @@ class TestDetective < Test::Unit::TestCase
153
150
  source = Detective.view_source('BadrIT.hello', :rdoc)
154
151
  assert_equal "#{__FILE__}, line 4 4: def self.hello 5: puts \"hello BadrIT\" 6: end", source.gsub(/\s+/, ' ').strip
155
152
  end
153
+
154
+ def test_should_find_private_methods
155
+ BadrIT.class_eval do
156
+ private
157
+ def hidden_method
158
+ puts "secret"
159
+ end
160
+ end
161
+ source = Detective.view_source('BadrIT#hidden_method')
162
+ assert_equal 'def hidden_method puts "secret" end', source.gsub(/\s+/, ' ').strip
163
+ end
164
+
165
+ def test_should_find_private_class_methods
166
+ BadrIT.class_eval do
167
+ class << self
168
+ def hidden_method
169
+ puts "secret"
170
+ end
171
+
172
+ private :hidden_method
173
+ end
174
+ end
175
+ source = Detective.view_source('BadrIT.hidden_method')
176
+ assert_equal 'def hidden_method puts "secret" end', source.gsub(/\s+/, ' ').strip
177
+ end
178
+
179
+ def test_method_missing
180
+ source = Detective.view_source('SomeClass#habal')
181
+ assert_equal 'def method_missing(args) puts "no method called #{args}" end', source.gsub(/\s+/, ' ').strip
182
+ end
156
183
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: detective
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 0.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ahmed ElDawy
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2009-11-21 00:00:00 +02:00
12
+ date: 2009-11-22 00:00:00 +02:00
13
13
  default_executable:
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency