私は、Ruby のメッセージ パッシング インフラストラクチャが、これに対する巧妙なトリックがあることを意味することを願っています。
呼び出し元のオブジェクト (現在使用しているメソッドを呼び出したオブジェクト) を特定するにはどうすればよいですか?
私は、Ruby のメッセージ パッシング インフラストラクチャが、これに対する巧妙なトリックがあることを意味することを願っています。
呼び出し元のオブジェクト (現在使用しているメソッドを呼び出したオブジェクト) を特定するにはどうすればよいですか?
目的の関数を呼び出したコード行を簡単に確認できます。
caller.first
関連する関数を呼び出したファイル名と行番号がわかります。次に、それがどのオブジェクトであったかを逆算できます。
ただし、おそらくインスタンスメソッド内で、特定の関数を呼び出したオブジェクトを求めているようです。これを理解する方法はわかりませんが、カプセル化にひどく違反しているように見えるので、とにかく使用しません。
最高の技術:
1 # phone.rb
2 class Phone
3 def caller_id
4 caller
5 end
6 end
7
8 class RecklessDriver
9 def initialize
10 @phone = Phone.new
11 end
12 def dial
13 @phone.caller_id
14 end
15 end
16
17 p = Phone.new
18 p.caller_id.inspect # => ["phone.rb:18:in `<main>'"]
19
20 macek = RecklessDriver.new
22 macek.dial.inspect # => ["phone.rb:13:in `dial'", "phone.rb:22:in `<main>'"]
注: 行番号はデモ用です。 スクリプトのphone.rb:X
行を指します。X
見てphone.rb:13
!このdial
メソッドが呼び出しを送信しました。と、その手法phone.rb:22
を用いた暴走ドライバーを指すdial
!
本番コードの例で使用されるピーターの答え
私の会社では、 Paranoia gemコラムdeleted
のフレーバーで flagを非推奨にしていました。次のコードは、列を削除する前にすべてがうまくいくことを確認する方法です (このコードを展開し、ライブになってから 2 ~ 3 日後に移行を展開します)。 deleted_at
remoove_column :lessons, :deleted
class Lesson < ActiveRecord::Base
def deleted
if caller.select { |c| c.match /serialization\.rb/ }.any?
# this is Rails object mapping
!!deleted_at
else
raise 'deplicated - deleted was replaced by deleted_at'
end
end
end
みたいなself
?
irb> class Object
.. def test
.. self
.. end
.. end
=> nil
irb> o = Object.new
=> #<Object:0xb76c5b6c>
irb> o.test
=> #<Object:0xb76c5b6c>