Почему люди не переносят блоки начала / восстановления вокруг ActiveRecord.find в Rails? - PullRequest
0 голосов
/ 30 июля 2010

Если пользователь пытается отправить форму или получить доступ к службе, которая использует что-то под капотом, например:

Model.find(params[:id]) # if model does not exist, throw ActiveRecord::RecordNotFound

Если экземпляр не может быть найден, возникает исключение.Тем не менее, я редко вижу, как люди переносят это утверждение в блоке begin / rescue, даже если вы создаете эшафот, генератор rails не переносит вызов find в блоки begin / rescue.

Есть ли причина для этого

Ответы [ 5 ]

4 голосов
/ 30 июля 2010

Я думаю, это потому, что наиболее распространенным случаем является то, что если вы идете за объектом по идентификатору, а он не существует, то это исключительный случай. Исключение будет пузыриться, и рельсы будут обрабатывать его как 404 для вас, что обычно подходит.

Если это ситуация, когда объект может существовать или не существовать, то либо перехват исключения, либо использование Model.find_by_id(params[:id]) и проверка на нулевой объект работают отлично.

2 голосов
/ 30 июля 2010

Одной из причин может быть то, что логика обработки ошибок передается обработчикам спасения в приложении.

ваш контроллер:

def some_action
  @foo = Foo.find!(params[:id])
  # Exception will raise here ...
  # ...
end

, а затем укажите

rescue_from ActiveRecord::RecordNotFound, :some_method_that_will_render_a_404

(См. this для объяснения)

Строительные леса - это просто ярлыки для быстрого запуска и запуска чего-либо, но, как правило, строительные леса не предназначены длядожить до производства .

Лично я не видел слишком много кода, который не выполняет хотя бы базовую проверку.Я бы сказал, что это нечто культурное: если вы не создадите маршрут, который приведет к ошибке, вы не обязаны ее обрабатывать.Очевидно, что это далеко от идеала, но я думаю, что это не является приоритетом для многих разработчиков.Это в основном зависит от бизнес-логики: она обычно положительно ориентирована, то есть предполагает только реагирование на действия пользователя действительные .

0 голосов
/ 30 июля 2010

Я видел такой код:

def add_to_cart
  begin
    product = Product.find(params[:id])
  rescue ActiveRecord::RecordNotFound
    logger.error("Attempt to access invalid product #{params[:id]}")     
    redirect_to_index("Invalid product")
  else
    @cart = find_cart
    @cart.add_product(product)      
  end
end
0 голосов
/ 30 июля 2010

Поскольку вы хотите, чтобы потерпел неудачу рано . Чем раньше вы обнаружите, что что-то не так, тем быстрее вы сможете это исправить.

0 голосов
/ 30 июля 2010

потому что звонить проще:

Model.find_by_id(params[:id])

, который возвращает ноль, если запись не найдена

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...