I need to know the current route in a filter in Rails. How can I find out what it is?
I'm doing REST resources, and see no named routes.
I need to know the current route in a filter in Rails. How can I find out what it is?
I'm doing REST resources, and see no named routes.
To find out URI:
current_uri = request.env['PATH_INFO']
# If you are browsing http://example.com/my/test/path,
# then above line will yield current_uri as "/my/test/path"
To find out the route i.e. controller, action and params:
path = ActionController::Routing::Routes.recognize_path "/your/path/here/"
# ...or newer Rails versions:
#
path = Rails.application.routes.recognize_path('/your/path/here')
controller = path[:controller]
action = path[:action]
# You will most certainly know that params are available in 'params' hash
params[:controller]
and params[:action]
. However, outside of it, if you want to recognize the route, this API is not available anymore. It has now shifted to ActionDispatch::Routing
and I haven't tried out the recognize_path
on it yet. –
Crazy request.path
for finding the current path. –
Rior request.env['ORIGINAL_FULLPATH']
to include the possible parameters in the path, see my answer below. –
Acerbic If you are trying to special case something in a view, you can use current_page?
as in:
<% if current_page?(:controller => 'users', :action => 'index') %>
...or an action and id...
<% if current_page?(:controller => 'users', :action => 'show', :id => 1) %>
...or a named route...
<% if current_page?(users_path) %>
...and
<% if current_page?(user_path(1)) %>
Because current_page?
requires both a controller and action, when I care about just the controller I make a current_controller?
method in ApplicationController:
def current_controller?(names)
names.include?(current_controller)
end
And use it like this:
<% if current_controller?('users') %>
...which also works with multiple controller names...
<% if current_controller?(['users', 'comments']) %>
controller_name
and action_name
are good for use in helpers and views for this sort of thing too. –
Vaporous current_page?
needs at least the controller and the action. If you need just the controller, you can use controller_name == 'users'
. I make a current_controller?
helper that does that check and put it in ApplicationController. –
Silicosis current_page?(@user)
or collection current_page?(@users)
. Rails uses polymorphic_path
under the hood to generate the path from the given active record object. Pretty neat! –
Bankhead @user
as the path \user\:id
. If the person is on the edit action users#edit
it will return false, however, because the actual current page is \user\:id\edit
. So it will work depending on what you are trying to do. –
Silicosis current_controller?
method would be better defined in a helper (perhaps ApplicationHelper
) instead of in a controller. –
Ruvolo To find out URI:
current_uri = request.env['PATH_INFO']
# If you are browsing http://example.com/my/test/path,
# then above line will yield current_uri as "/my/test/path"
To find out the route i.e. controller, action and params:
path = ActionController::Routing::Routes.recognize_path "/your/path/here/"
# ...or newer Rails versions:
#
path = Rails.application.routes.recognize_path('/your/path/here')
controller = path[:controller]
action = path[:action]
# You will most certainly know that params are available in 'params' hash
params[:controller]
and params[:action]
. However, outside of it, if you want to recognize the route, this API is not available anymore. It has now shifted to ActionDispatch::Routing
and I haven't tried out the recognize_path
on it yet. –
Crazy request.path
for finding the current path. –
Rior request.env['ORIGINAL_FULLPATH']
to include the possible parameters in the path, see my answer below. –
Acerbic Simplest solution I can come up with in 2015 (verified using Rails 4, but should also work using Rails 3)
request.url
# => "http://localhost:3000/lists/7/items"
request.path
# => "/lists/7/items"
<form action="<%= request.path %>">
–
Lepto You can do this
Rails.application.routes.recognize_path "/your/path"
It works for me in rails 3.1.0.rc4
In rails 3 you can access the Rack::Mount::RouteSet object via the Rails.application.routes object, then call recognize on it directly
route, match, params = Rails.application.routes.set.recognize(controller.request)
that gets the first (best) match, the following block form loops over the matching routes:
Rails.application.routes.set.recognize(controller.request) do |r, m, p|
... do something here ...
end
once you have the route, you can get the route name via route.name. If you need to get the route name for a particular URL, not the current request path, then you'll need to mock up a fake request object to pass down to rack, check out ActionController::Routing::Routes.recognize_path to see how they're doing it.
undefined method 'recognize' for #<Journey::Routes:0x007f893dcfa648>
–
Cott Based on @AmNaN suggestion (more details):
class ApplicationController < ActionController::Base
def current_controller?(names)
names.include?(params[:controller]) unless params[:controller].blank? || false
end
helper_method :current_controller?
end
Now you can call it e.g. in a navigation layout for marking list items as active:
<ul class="nav nav-tabs">
<li role="presentation" class="<%= current_controller?('items') ? 'active' : '' %>">
<%= link_to user_items_path(current_user) do %>
<i class="fa fa-cloud-upload"></i>
<% end %>
</li>
<li role="presentation" class="<%= current_controller?('users') ? 'active' : '' %>">
<%= link_to users_path do %>
<i class="fa fa-newspaper-o"></i>
<% end %>
</li>
<li role="presentation" class="<%= current_controller?('alerts') ? 'active' : '' %>">
<%= link_to alerts_path do %>
<i class="fa fa-bell-o"></i>
<% end %>
</li>
</ul>
For the users
and alerts
routes, current_page?
would be enough:
current_page?(users_path)
current_page?(alerts_path)
But with nested routes and request for all actions of a controller (comparable with items
), current_controller?
was the better method for me:
resources :users do
resources :items
end
The first menu entry is that way active for the following routes:
/users/x/items #index
/users/x/items/x #show
/users/x/items/new #new
/users/x/items/x/edit #edit
Or, more elegantly: request.path_info
Source:
Request Rack Documentation
Should you also need the parameters:
current_fullpath = request.env['ORIGINAL_FULLPATH'] # If you are browsing http://example.com/my/test/path?param_n=N # then current_fullpath will point to "/my/test/path?param_n=N"
And remember you can always call <%= debug request.env %>
in a view to see all the available options.
I'll assume you mean the URI:
class BankController < ActionController::Base
before_filter :pre_process
def index
# do something
end
private
def pre_process
logger.debug("The URL" + request.url)
end
end
As per your comment below, if you need the name of the controller, you can simply do this:
private
def pre_process
self.controller_name # Will return "order"
self.controller_class_name # Will return "OrderController"
end
self.
in self.controller_name
and self.controller_class_name
–
Synergetic request.url
request.path #to get path except the base url
You can see all routes via rake:routes (this might help you).
You can do this:
def active_action?(controller)
'active' if controller.remove('/') == controller_name
end
Now, you can use like this:
<%= link_to users_path, class: "some-class #{active_action? users_path}" %>
I find that the the approved answer, request.env['PATH_INFO']
, works for getting the base URL, but this does not always contain the full path if you have nested routes. You can use request.env['HTTP_REFERER']
to get the full path and then see if it matches a given route:
request.env['HTTP_REFERER'].match?(my_cool_path)
You can do request.env['REQUEST_URI']
to see the full requested URI.. it will output something like below
http://localhost:3000/client/1/users/1?name=test
© 2022 - 2024 — McMap. All rights reserved.