0

Rails モデルでやりたいことをよく反映した、いくつかの異なる方法で実装された 2 つのサンプル クラスをまとめました。私の懸念は、どちらの方法を使用する場合の懸念事項があるとしても、何がわからないということです。そして、それらを実装する方法を説明する投稿、またはそれらを使用するときに避ける/注意するための一般的な警告のみを見つけました。私が見つけられなかったのは、これを安全に達成する方法、および私が注意していること、またはこのパターンを避けるべき理由の明確な説明です.

class X
  attr_accessor :yn_sc, :um_sc
  def initialize
    @yn_sc = 0
    @um_sc = 0
  end
  types = %w(yn um)
  types.each do |t|
    define_method("#{t}_add") do |val|
      val = ActiveRecord::Base.send(:sanitize_sql_array, ["%s", val])
      eval("@#{t}_sc += #{val}")
    end
  end
end

class X
  attr_accessor :yn_sc, :um_sc
  def initialize
    @yn_sc = 0
    @um_sc = 0
  end
  types = %w(yn um)
  types.each do |t|
    # eval <<-EVAL also works
    self.class_eval <<-EVAL 
      def #{t}_add(val)
        @#{t}_sc += val
      end
    EVAL
  end
end


x = X.new
x.yn_add(1) #=> x.yn_sc == 1 for both
4

1 に答える 1

1

さて、あなたのコードは本当に安全に見えます。しかし、ユーザー入力に基づくコードを想像してみてください。それは何かのように見えるかもしれません

puts 'Give me an order, sir!'
order = gets.chomp
eval(order)

私たちの船長が暴れて私たちに命じたらどうなり'rm -rf ~/'ますか?確かに悲しいこと!

だから少しレッスンを受けてください。eval受け取るすべての文字列を評価するため、安全ではありません。しかし、使用しない別の理由がありますeval。場合によっては、代替よりも遅く評価されます。興味のある方はこちらをご覧ください。

于 2013-11-19T17:53:14.697 に答える