views:

39

answers:

2

I am trying to get the controller and action name based on a path. I have a route:

map.resources :permissions

I thought that I could use:

ActionController::Routing::Routes.recognize_path "/permissions/1"

To get a hash like:

{ :controller => "permissions", :action => "show" }

The actual hash that comes back is:

{ :controller => "permissions", :action => "1" }

How do I get the correct action name instead of just my passed in ID? The dispatcher must be able to get at it somehow or Rails wouldn't work, but I am having trouble locating how it is accomplished.

A: 

What are you really after? If you're really after the action name and controller name... you can just ask for

controller.controller_name

and

controller.action_name

Does that help, or do you really need to parse a string to do it?

mylescarrick
I have route-based authorization in place. Basically, in my database I plug in controllers and actions that I only want accessible to certain users and treat them as permissions. I bundle these permissions into roles and assign them to my users. When a protected page is visited, a before filter will determine if the user is allowed to be on that page. That is working great (by using the methods you suggested). Now I need to dynamically display a link based on whether or not the user is allowed to visit the page behind the link. I don't have access to the target controller, only the path.
retailevolved
A: 

This is what I ended up doing. It is ugly and there must be a better way, but it works for now. It happens in a before_filter so that I can see if the user has access to the controller / action they are attempting to access.

I chose to use route-based authorization as opposed to model-based authorization.

# Get method of current request
method = options[:method] ? options[:method] : 'get'

# Create a new request - hate this that is required
env = Rack::MockRequest.env_for(url, {:method => method})
request = ActionController::Request.new(env)

# For some reason, calling this fills in the controller / action information for the request
# just using recognize_path doesn't work correctly with resources...
ActionController::Routing::Routes.recognize(request)

Then you access the controller and action with request.params[:controller] and request.params[:action].

All of this would not be necessary if ActionController::Routing::Routes.recognize_path("/permissions/1") returned the correct action.

retailevolved