Hatena::ブログ(Diary)

わからん

2012.04.05

[][] let での(変数)定義で既に別の let で定義した内容を代入するには

 問題

RSpec の let での変数定義で、すでに別の let で設定した結果の変数を代入したい。a = foo; b = a みたいの、どうやるの。


 答案

まず「変数」定義というのが間違いです。let が実行されることで「メソッド」が定義されます。RSpec で、let 自身は以下のように定義されています。かっこいいです。

module Let
  module ExampleGroupMethods

    def let(name, &block)
      define_method(name) do
        __memoized.fetch(name) {|k| __memoized[k] = instance_eval(&block) }
      end
    end

  end

  module ExampleMethods
    def __memoized
      @__memoized ||= {}
    end
  end

  def self.included(mod)
    mod.extend ExampleGroupMethods
    mod.__send__ :include, ExampleMethods
  end
end

let のブロックで渡した内容を実行する、let の引数と同名のメソッドを定義しています。だから、a = foo; b = a 的なことがしたければ、こんなふうに

let(:valid_params_for_foo) do
  # ...
  # ...
  # ...
end

let(:valid_params_for_bar) { valid_params_for_foo }

メソッド b を定義する let のブロックの中で、メソッド a を実行すればよい。ハッ、そういえば、まれにブロックが長ーくなる let で、こういうのなんとなく使っていた気がします。つまんない記事、書いちゃいました ><

Google