1

I invoke ReleaseSchedule.next_release in other controller

and got the following error

NoMethodError (undefined method `to_criteria' for #<ReleaseSchedule:0x007f9cfafbfe70>):
  app/controllers/weekly_query_controller.rb:15:in `next_release'

releae_schedule.rb

class ReleaseSchedule
  scope :next_release, ->(){ ReleaseSchedule.where(:release_date.gte => Time.now).without(:_id, :created_at, :updated_at).first }
end
newBike
  • 14,385
  • 29
  • 109
  • 192

1 Answers1

5

That's not really a scope at all, that's just a class method wrapped up to look like a scope. There are two problems:

  1. You're saying ReleaseSchedule.where(...) so you can't chain the "scope" (i.e. ReleaseSchedule.where(...).next_release won't do what it is supposed to do).
  2. Your "scope" ends in first so it won't return a query, it just returns a single instance.

2 is probably where your NoMethodError comes from.

If you really want it to be a scope for some reason then you'd say:

# No `first` or explicit class reference in here.
scope :next_release, -> { where(:release_date.gte => Time.now).without(:_id, :created_at, :updated_at) }

and use it as:

# The `first` goes here instead.
r = ReleaseSchedule.next_release.first

But really, you just want a class method:

def self.next_release
  where(:release_date.gte => Time.now).without(:_id, :created_at, :updated_at).first
end

The scope macro is, after all, just a fancy way to build class methods. The only reason we have scope is to express an intent (i.e. to build queries piece by piece) and what you're doing doesn't match that intent.

mu is too short
  • 426,620
  • 70
  • 833
  • 800