Ответ 1
Я бы посоветовал использовать интерполяцию строк для этого, есть много острых краев, и у вас, вероятно, будет больше удовольствия подпрыгивать для яблок в ведре рыболовных крючков. Вы должны сделать это следующим образом:
Model.where(
'created_at >= :five_days_ago or updated_at >= :three_days_ago',
:five_days_ago => Time.now - 5.days,
:three_days_ago => Time.now - 3.days
)
Использование (ну) названных заполнителей дает вам читабельность и независимость позиции, которые, по вашему мнению, предлагают интерполяция строк, но прекрасно обойти проблемы цитирования, часового пояса и формата, которые накладывают на вас интерполяцию строк.
Но как вы безопасно используете интерполяцию строк? Есть несколько вещей, которые вы должны решить сами:
- Цитирование и экранирование.
- Формат временной отметки.
- Может быть, и часовые пояса.
ActiveRecord позаботится обо всем этом ерунде для вас.
Не пытайтесь делать цитаты самостоятельно, используйте методы цитирования драйверов. У вас будет доступ к connection.quote
для правильного цитирования строк.
Любая база данных будет знать, что делать с временными метками ISO 8601, и для этого существует удобный метод iso8601
. ISO 8601 также удобно включает часовой пояс, и база данных должна быть способна анализировать это (но если это не возможно, вам придется конвертировать свое время в UTC вручную с помощью .utc
).
Итак, чтобы быть в безопасности:
Model.where("created_at >= #{connection.quote((Time.now - 5.days).utc.iso8601)} " + \
"OR updated_at >= #{connection.quote((Time.now - 3.days).utc.iso8601)}")
Не так красиво это сейчас? С отметками времени ISO 8601 вы должны безопасно заменить вызовы connection.quote
на простые одинарные кавычки:
Model.where("created_at >= '#{(Time.now - 5.days).utc.iso8601}' " + \
"OR updated_at >= '#{(Time.now - 3.days).utc.iso8601}'")
но у вас все еще много шума и уродства, и вы будете развивать плохие привычки.
Мы не участвуем в вечеринках, как программисты PHP в 1999 году, поэтому не поддавайтесь ложной лени, используя строчную интерполяцию в вашем SQL, используйте именованные заполнители.