I have such scope
scope :old, joins(:group).where("`users`.`created_at` <=
DATE_SUB(?, INTERVAL `groups`.`check_minutes` MINUTE)", Time.now)
I stub Time.now as following
Time.stub!(:now).and_return(Time.parse("1 JUL 2010"))
I want scope old to use this stubbed Time.now but it uses current time.
I suppose rails create scopes when load model first time (e.g. when load spec_helper.rb), so we stub Time.now after loading the scope. Is it true?
So I found two solutions:
- Reload User model after stubbing Time.now and before using scope
- Use regular method instead of stub like this
Do you have more elegant solutions?
Having
Time.nowin a plain scope is undesirable, as you state the scope is setup when the model class is loaded, so a long running Rails process may have a scope that is from hours or days ago. The stubbing issue is a side-effect of this undesirable situation.I would suggest you rewrite your scope using a
lambda, so thatTime.nowis always queried. This will alleviate the stubbing issue and always get the latestTime.now.I’m not a huge fan of the lambda syntax here, but it does do the job.