我有这个小代码
class ReadReportService
def self.get_oldest_reports(count, filter={})
reports = Report.unread.order('created_at DESC').limit(count)
reports = reports.where(category: filter[:category]) if filter[:category].present?
reports = reports.where(cost: filter[:cost]) if filter[:cost].present?
reports = reports.where(email: filter[:email]) if filter[:email].present?
reports.update_all(status: Report.statuses[:read])
reports.to_a
end
end
我能做得更好更好吗?如何改进检查哈希参数?
答案 0 :(得分:0)
它应该在Report
型号中:
class Report < ActiveRecord::Base
STATUSES = {read: 'read', pending: 'pending'}
scope :ordered_limit, ->(limit) { order('created_at DESC').limit(limit) }
scope :filter_category, ->(category) { where(category: category) if category }
scope :filter_cost, ->(cost) { where(cost: cost) if cost }
scope :filter_email, ->(email) { where(email: email) if email }
def self.get_oldest_reports(count, filter={})
reports = unread.ordered_limit(count)
.filter_category(filter[:category])
.filter_cost(cost)
.filter_email(email)
reports.update_all(status: STATUSES[:read])
reports.to_a # not sure you need it
end
end
答案 1 :(得分:0)
如果您想简化适用于过滤器的代码,您可以执行以下操作:
reports = Report.unread.order('created_at DESC').limit(count)
[:category, :cost, :email].each do |key|
reports = reports.where(key => filter[key]) if filter[key].present?
end
reports.update_all(status: Report.statuses[:read])
reports.to_a
顺便说一句,在名为update_all
的方法中调用get_xxx
并不是一个好主意。如果我得到了某些东西,我就不会期望某些东西会被改变。
P.S。如果你喜欢oneliners,你甚至可以做这样的事情:
reports.where(filter.slice(:category, :cost, :email).select { |k, v| v.present? })