-
Notifications
You must be signed in to change notification settings - Fork 21.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Can no longer rescue_from ActionController::RoutingError #671
Comments
Imported from Lighthouse. I verified this with a freshly generated rails app from the master branch. I haven't investigated too far, but at this point the best way I can see to do this in rails 3 is to subclass and swap out the |
Imported from Lighthouse. I am also hitting this problem, but my understanding of the internals of rails3 is very limited atm ... Couldn't we define the rescue handling as an option to the route ? (thus in route.rb) |
Imported from Lighthouse. Put following code in an initializer in a rails3 app. module ActionDispatch
class ShowExceptions
def render_exception(env, exception)
if exception.kind_of? ActionController::RoutingError
render(500, 'it was routing error')
else
render(500, "some other error")
end
end
end
end There might be a better way but it works in my quick test. |
Imported from Lighthouse. The best way to handle a missing route in Rails 3 is by adding the following line at the end of your router: match "*", :to => "home#routing_error" And add the routing_error action. We will be working on a better solution, but it is targeted for 3.1. |
Imported from Lighthouse. José, are you sure that your solution actually works? I think it's not working as you can't simply say match "*" to match everything in Rails 3 so far? |
Imported from Lighthouse. I mean, you have to do it like this: match '/:anything', :to => "home#routing_error", :constraints => { :anything => /.*/ } |
Imported from Lighthouse. I was giving it a bit more thought since yesterday. The solution with match "/:anything" is also not perfect for some people, as it'll override all routes from plugins/engines. I now think that best solution is to use custom rack middleware for handling 404 pages in Rails. |
Imported from Lighthouse. The approach that I have adopted to solve this (for now) is to make a call back into the application (from ActionDispatch::ShowExcpetions#render_exception), specifically to a controller that is there for the purpose of rendering an error page. This has all the benefits of using the layout and styling of the host application. However, if a second exception occurs whilst handling the exception in this way, the original method is called, and the default is rendered. It is better explained here: http://accuser.cc/posts/1-rails-3-0-exception-handling For those who would rather copy and paste than read the above... ;) |
Imported from Lighthouse. Here is a gem that may solve this issue: http://github.com/vidibus/vidibus-routing_error |
Imported from Lighthouse. The easiest way for me was to add this very last route: match ''=> lambda { |env| raise ActionController::RoutingError, env["PATH_INFO"] } |
Imported from Lighthouse. Please ignore my previous comment, it does not work that way. Seems rails had some routes cached, so it seemed to work initially. |
Imported from Lighthouse. Automatic cleanup of spam. |
Imported from Lighthouse. Automatic cleanup of spam. |
Imported from Lighthouse. Personally, I'm waiting for an Official solution from the Rails Core Team. Until then I need a simple, no side effect solution for catching rogue routes. For now, my solution is an elaboration on José Valim's recommendation: With this approach, you'll be in unison with the Rails Core Team. Moreover, I incorporate Rails 3 Route Globbing, so you get the added benefit of knowing exactly which rogue route was entered. As a result, you're free to handle routing errors as creatively as you'd like. |
Imported from Lighthouse. Issue for more than just rescuing from routing errors, CanCan::AccessDenied too: |
Imported from Lighthouse. This is a huge bug and I feel it's priority should be raised. It's not acceptable for a broken link in a production app to result in a blank screen, this is why we make 404 handlers. But once the request is dispatched to rails it seems to be rails job to render the 404 page, which it can't do because of this bug. |
Imported from Lighthouse. Just to add, Don't seem to work when the controller exists but the action doesn't. Exception log still just shows "AbstractController::ActionNotFound (The action 'rejsasdf' could not be found for HomeController):" and a blank page is rendered. |
Imported from Lighthouse. Are you using :action as the dynamic segment name? If so Rails will try to find the action in the controller. The following path works for me: match '*path', :to => 'errors#not_found' This won't catch a missing root path - but I'm guessing you're website is there. |
Imported from Lighthouse. A catch-all route at the end of your routes my seem like a simple fix, but it has a major drawback: I've published a gem that solves the routing error. It basically catches the exception on Rack-level and re-raises it on application-level: https://github.com/vidibus/vidibus-routing_error |
Imported from Lighthouse. Oops, I removed José. Sorry. |
Imported from Lighthouse. I am using non-restful routes, which is perhaps why the catch-all doesn't work for me
|
Yeah, you can no longer do that. You need to define a catch all route. |
Why has this issue been closed? As far as I can tell, Rails 3.1 RC1 still hasn't added back support rescue_from, right? Or is it going to be in the next RC / official release? |
No Exceptron did not get in Rails 3.1. :( We are going to merge it into master soon. |
Should this issue be re-opened until the actual fix is merged? |
Any word on the status of this issue? |
Can someone please provide some more info on the status of this issue? I'm still seeing it on edge. |
With how rails 3 was restructured to be a real rack app, it's not longer easy and clean to raise that error inside the context of a controller instance. |
Ok, I understand it's going to stay this way. |
great explanation On Mon, Feb 20, 2012 at 11:40 AM, Reinier de Lange <
|
Hello, I want to handle not only routing errors. I have used the code from #671 (comment) and is working fine. What I would like to do is to render a page directly instead of displaying a message. Therefore I've replaced --> render(500, 'it was routing error') for this --> render :file => "#{RAILS_ROOT}/public/500.html", :status => 500 But I get an error: wrong number of arguments (1 for 2) This is what im trying: module ActionDispatch Any help will be very welcome! Thanks in advance! |
why don't you just use rescue_from for anything other than routing errors? |
Hi, I thought rescue_from didnt work in Rails 3.0.X versions. Reading now better the post I assume that the only one that doesnt work is for the Routing errors. Sorry, my bad! |
@canma5 Correct - rescue_from doesn't work with ActionController::RoutingError in 3.2.0, but does work for everything else. |
What is the current status? 11 months ago, josé:
10 months ago, josé:
Now we're in several patch releases of rails 3.2. Is there any new official way to deal with this? Or is the only way still a catch-all route? The problem with the catch-all route, as others have mentioned, is it messes up engine-supplied routes. To deal with that, you can do it in an after_initialize block or some other initializer you hook in after engine routes are loaded... but this starts getting kind of cumbersome and confusing for the beginner. At one point José suggested Rails core team planned to implement some other fix -- is there still such a plan/desire? |
+1 looking forward to a status update. |
Any update on how to handle this? |
This issue shouldn't be closed. |
I will review this later, but from the top of my head you can fix this changing ... |
Closing, see @spastorino comment |
I do not understand how to apply @spastorino's comment. Is it possible to rescue from Routing exceptions in current Rails, and if so, how? |
For everyone waiting on a status update, I've written briefly about it here (point 3): http://blog.plataformatec.com.br/2012/01/my-five-favorite-hidden-features-in-rails-3-2/ |
Thanks. Is rescue_from discouraged/deprecated behavior, and the new middleware-based |
Regarding the blog post that josevalim posted, is that the real way to handle this? I like that method and it works well for me except for integration tests that tests for a 404 server response since the ActiveRecord::RecordNotFound exception bubbles up to the tests. I've been able to fix that by doing the 'rescue_from ActiveRecord::RecordNotFound' thing but that seems like duplication since I also have a 'match 404' in my routes. |
Here an example: https://gist.github.com/Sujimichi/2349565 |
* 404 page redesign * Fix css format * Fix link destination * Remove old 404 file * Add new controller and helper * Add new 404 template * Add new route to the 404 page * Tell rails to use tempaltes * Error pages sass * Catch errors with custom error pages yielded w/ application layout * update styling and put content inside .container * Optimize calls + raise exception for development mode * Return back static 500 page * Make rails app available to catch RoutingError (raised by ActionDispatch) Ref: rails/rails#671 * Fix not found routes spec * Fix unmactched routes catch * Fix specs
* 404 page redesign * Fix css format * Fix link destination * Remove old 404 file * Add new controller and helper * Add new 404 template * Add new route to the 404 page * Tell rails to use tempaltes * Error pages sass * Catch errors with custom error pages yielded w/ application layout * update styling and put content inside .container * Optimize calls + raise exception for development mode * Return back static 500 page * Make rails app available to catch RoutingError (raised by ActionDispatch) Ref: rails/rails#671 * Fix not found routes spec * Fix unmactched routes catch * Fix specs
Imported from Lighthouse. Original ticket at: http://rails.lighthouseapp.com/projects/8994/tickets/4444
Created by Luigi Montanez - 2011-02-14 05:42:01 UTC
In Rails 2.3.x, one is able to stick this in ApplicationController to present the user with a custom 404 screen:
Now in Rails 3, because routing is done as middleware (ActionDispatch), it seems that the ActionController::RoutingError that gets thrown by ActionDispatch no longer can be caught from ApplicationController -- the error is already thrown and ActionDispatch renders /templates/rescues/routing_error.erb before the controller can rescue_from the error.
The text was updated successfully, but these errors were encountered: