Ruby on Rails: как мне изменить поведение RecordNotFound? - PullRequest
4 голосов
/ 30 августа 2011

При переходе на страницу показа объекта с идентификатором, который не существует, возникает исключение RecordNotFonud. Есть ли способ, которым я могу перенаправить на какую-то страницу ошибки, или, может быть, другое действие, когда эта ошибка выдается?

Ответы [ 6 ]

10 голосов
/ 30 августа 2011

Вы можете использовать rescue_from , если вы используете Rails 3:

class ApplicationController < ActionController::Base
  rescue_from ActiveRecord::RecordNotFound, :with => :render_404

  def render_404
    respond_to do |format|
      format.html { render :action => "errors/404.html.erb", :status => 404 }
      # and so on..
    end
  end
end

Да, вы также можете сделать перенаправление вместо рендеринга , но это не очень хорошая идея. При любом полуавтоматическом взаимодействии с вашим сайтом считается, что передача прошла успешно (поскольку возвращенный код не был 404), но полученный ресурс был не тем, который хотел ваш клиент.

1 голос
/ 30 августа 2011

Я обычно делаю что-то подобное в моем ApplicationController

class ApplicationController < ActionController::Base
    rescue_from ActiveRecord::RecordNotFound, :with => :routing_error

    private
    def routing_error
        redirect_to(root_url, :alert => "Sorry, the page you requested could not be found.")
    end
end
1 голос
/ 30 августа 2011

См. http://api.rubyonrails.org/classes/ActiveSupport/Rescuable/ClassMethods.html. В Rails есть хорошие функции для обработки исключений.

1 голос
/ 30 августа 2011

В режиме разработки вы увидите подробности исключения, но он должен автоматически отобразить файл 404.html из вашего общего каталога, когда ваше приложение работает в производственном режиме.

0 голосов
/ 06 сентября 2011

Если вам нужно обработать более одного конкретного исключения, используйте rescue_action или rescue_action_in_public , разница в том, чтобы перехватывать локальные запросы или нет (общая разработка / производство). Я предпочитаю использовать in_public , потому что необходимо просмотреть трассировку исключения в режиме разработки.

взгляните на мой исходный код:

class ApplicationController < ActionController::Base
  include CustomExceptionsHandler
  ....

end


module CustomExceptionsHandler

  # Redirect to login/dashboard path when Exception is caught
  def rescue_action_in_public(exception)
    logger.error("\n !!! Exception !!! \n #{exception.message} \n")

    case exception.class.to_s
    when "Task::AccessDenied"
      logger.error(" !!! 403 !!!")
      notify_hoptoad(exception) //catch this kind of notification to Hoptoad
      render_403
    when "AuthenticatedSystem::PermissionDenied"
      logger.error(" !!! 403 !!!")
      render_403      
    when "Task::MissingDenied"
      logger.error(" !!! 404 !!!")
      notify_hoptoad(exception)
      render_404
    when "ActionController::RoutingError"
      logger.error(" !!! 404 !!!")
      render_404      
    else
      notify_hoptoad(exception)
      redirect_to(current_user.nil? ? login_path : dashboard_path) and return false
    end
  end


  private


  #403 Forbidden
  def render_403
    respond_to do |format|
      format.html { render :template => "common/403", :layout => false, :status => 403 }
      format.xml  { head 403 }
      format.js   { head 403 }
      format.json { head 403 }
    end
    return false
  end

  #404 Not Found
  def render_404
    respond_to do |format|
      format.html { render :template => "common/404", :layout => false, :status => 404 }
      format.xml  { head 404 }
      format.js   { head 404 }
      format.json { head 404 }
    end
    return false
  end

end
0 голосов
/ 30 августа 2011

Используйте конструкцию begin - rescue - end, чтобы перехватить исключение и сделать с ним что-нибудь полезное.

userid=2
begin
    u=User.find userid
rescue RecordNotFound
    redirect_to "/errorpage"     #Go to erropage if you didn't find the record
    exit
end

redirect_to u           # Go to the user page
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...