6

ここで検索中にいくつかの同様の質問を見つけましたが、見つけた解決策以外に追加しようとすると、問題が発生し始めました...

これが私が持っているものです:

コントローラ:

    @metrics = Metric.where("current_ratio > ?", @screen.current_ratio_min) unless @screen.current_ratio_min.nil?

別の .where 行 (そのうちの多くを追加する必要があります) を追加すると、

    @metrics = Metric.where("current_ratio > ?", @screen.current_ratio_min) unless @screen.current_ratio_min.nil?
    .where("current_ratio < ?", @screen.current_ratio_max) unless @screen.current_ratio_max.nil?

エラーが発生します:

undefined method `where' for false:FalseClass

これは、最初のunlessがクエリを終了しているためだと思います。個々の条件だけに not を適用するにはどうすればよいですか? それが実際に問題である場合:\

前もって感謝します!

4

5 に答える 5

8
@metrics = Metric.all
@metrics = @metrics.where('current_ratio > ?', @screen.current_ration_min) if @screen.current_ratio_min.present?
@metrics = @metrics.where('other_value > ?', @screen.other_value) if @screen.other_value.present?

これは、SQL インジェクションの危険性がある where 句の文字列をプログラムで構築することなく、私が考えることができる最良の方法です。

必要な数の条件を追加し続けます。注目すべきは、何かが存在する場合に使用しますか?あなた以外の何か.nilの代わりに?

また、Metric.all は理想的ではないかもしれませんが、最初にすべてのレコードを取得するために必要なものは何でも構いません。

于 2013-07-08T05:27:01.800 に答える
1

きれいなコードが必要な場合は、scope

metric.rb で

  scope :current_ratio_min, lambda {|current_ratio_min|
    current_ratio_min.present? ? where('current_ratio > ?', current_ration_min) : where()}
  scope :current_ratio_max, lambda {|current_ratio_max|
    current_ratio_max.present? ? where('current_ratio > ?', current_ratio_max) : where()}

あなたのクエリ:

@metrics = Metric.current_ratio_min(@screen.current_ratio_min).current_ratio_max(@screen.current_ratio_max)`
于 2013-07-08T08:44:13.673 に答える
0

Array クラスに次のメソッドを記述します。

 class Array
  def add_condition!(condition, conjunction = 'AND')
   if String === condition
     add_condition!([condition])
   elsif Hash === condition
     add_condition!([condition.keys.map { |attr| "#{attr}=?" }.join(' AND ')] + condition.values)
   elsif Array === condition
     unless condition.empty?
       self[0] = "(#{self[0]}) #{conjunction} (#{condition.shift})" unless empty?
       self.push(*condition)
     end
   else
    raise "don't know how to handle this condition type"
   end
  self
 end
end

次のように条件を使用して、ActiveRecord where または find の条件を作成できます。

 conditions = []
 conditions.add_condition!(["current_ratio > ?", @screen.current_ratio_min]) unless @screen.current_ratio_min.nil?  
 conditions.add_condition!(["current_ratio < ?", @screen.current_ratio_max]) unless @screen.current_ratio_max.nil?
 @metrics = Metric.where(conditions)

これは、AND/OR の組み合わせで複数の条件を構築するのに役立ちます。

于 2015-04-07T18:25:40.107 に答える
-1

このようなものはどうですか?

if !@screen.current_ratio_min.nil? && !@screen.current_ratio_max.nil?
  @metrics = Metric.where("current_ratio > ?", @screen.current_ratio_min).where("current_ratio < ?", @screen.current_ratio_max)
elsif @screen.current_ratio_min.nil? && !@screen.current_ratio_max.nil?
  @metrics = Metric.where("current_ratio < ?", @screen.current_ratio_max)
elsif !@screen.current_ratio_min.nil? && @screen.current_ratio_max.nil?
  @metrics = Metric.where("current_ratio > ?", @screen.current_ratio_min)
else
  @metrics = Metric.all
end
于 2013-07-08T04:23:33.480 に答える