I am using Ruby 1.8.7 with Rails 3.1. My application worked fine in Rails 3.0 but when I bumped it up to Rails 3.1.4, all my url helpers broke!
After Googling like a mad man the past 2 days, I have given up and the time has come to seek help. I don't believe the problem is with my routes.rb file but something more on the view/helper side.
I have the following in my routes.rb:
resources :sessions
In my homepage view I have the following link_to, which errors out:
<%= link_to "Login", new_session_path %>
When I do rake routes, I get the following output, so the path exists:
sessions GET /sessions(.:format) {:controller=>"sessions", :action=>"index"}
POST /sessions(.:format) {:controller=>"sessions", :action=>"create"}
new_session GET /sessions/new(.:format) {:controller=>"sessions", :action=>"new"}
edit_session GET /sessions/:id/edit(.:format) {:controller=>"sessions", :action=>"edit"}
session GET /sessions/:id(.:format) {:controller=>"sessions", :action=>"show"}
PUT /sessions/:id(.:format) {:controller=>"sessions", :action=>"update"}
DELETE /sessions/:id(.:format) {:controller=>"sessions", :action=>"destroy"}
When I go to /sessions/new in my browser, the page loads so again, the route exists, but it errors out on a _path based url:
<%= form_tag sessions_path, :method => :post do -%>
The error I get is as follows:
ActionView::Template::Error (undefined local variable or method `sessions_path' for #<#<Class:0x109cb8900>:0x109cab840>):
It has to be something with the url_for helper as the routes do exist. What else should I look for?
UPDATE 1:
I added the following inside application_helper.rb:
include Rails.application.routes.url_helpers
Now when I get the following error:
In order to use #url_for, you must include routing helpers explicitly. For instance, `include Rails.application.routes.url_helpers
Isn't that is what I just did?
Update 2:
The following worked as MrYoshiji suggested:
Rails.application.routes.url_helpers.sessions_path
Update 3:
I got sessions_path working again by removing some old Rails 2 plugins in vendor directory.
Removed some Rails 2 plugins in vendor/plugins did the trick.
Related
I'm building Rails API for AngularJS app. I'm using devise_token_auth and omniauth-steam gems. When I try to authenticate user using the Steam there is an error:
ActionController::RoutingError (No route matches [POST] "/omniauth/steam/callback"
I've added devise_token_auth routes, but they don't create POST callbacks. I've tried to manually create POST route for callback, but it hasn't worked and I'm not sure if it is even correct solution. I'm trying to solve this problem from yesterday and I can't find anyone with the similar one.
config/routes.rb
Rails.application.routes.draw do
namespace 'api' do
namespace 'v1' do
mount_devise_token_auth_for 'Api::V1::User', at: 'auth'
end
end
end
config/initializers/omniauth.rb
Rails.application.config.middleware.use OmniAuth::Builder do
provider :steam, ENV['steam_api_key']
end
I use figaro gem and save steam_api_key in application.yml file.
rake routes task
Prefix Verb URI Pattern Controller#Action
new_api_v1_api_v1_user_session GET /api/v1/auth/sign_in(.:format) devise_token_auth/sessions#new
api_v1_api_v1_user_session POST /api/v1/auth/sign_in(.:format) devise_token_auth/sessions#create
destroy_api_v1_api_v1_user_session DELETE /api/v1/auth/sign_out(.:format) devise_token_auth/sessions#destroy
api_v1_api_v1_user_password POST /api/v1/auth/password(.:format) devise_token_auth/passwords#create
new_api_v1_api_v1_user_password GET /api/v1/auth/password/new(.:format) devise_token_auth/passwords#new
edit_api_v1_api_v1_user_password GET /api/v1/auth/password/edit(.:format) devise_token_auth/passwords#edit
PATCH /api/v1/auth/password(.:format) devise_token_auth/passwords#update
PUT /api/v1/auth/password(.:format) devise_token_auth/passwords#update
cancel_api_v1_api_v1_user_registration GET /api/v1/auth/cancel(.:format) devise_token_auth/registrations#cancel
api_v1_api_v1_user_registration POST /api/v1/auth(.:format) devise_token_auth/registrations#create
new_api_v1_api_v1_user_registration GET /api/v1/auth/sign_up(.:format) devise_token_auth/registrations#new
edit_api_v1_api_v1_user_registration GET /api/v1/auth/edit(.:format) devise_token_auth/registrations#edit
PATCH /api/v1/auth(.:format) devise_token_auth/registrations#update
PUT /api/v1/auth(.:format) devise_token_auth/registrations#update
DELETE /api/v1/auth(.:format) devise_token_auth/registrations#destroy
api_v1_api_v1_user_confirmation POST /api/v1/auth/confirmation(.:format) devise_token_auth/confirmations#create
new_api_v1_api_v1_user_confirmation GET /api/v1/auth/confirmation/new(.:format) devise_token_auth/confirmations#new
GET /api/v1/auth/confirmation(.:format) devise_token_auth/confirmations#show
api_v1_auth_validate_token GET /api/v1/auth/validate_token(.:format) devise_token_auth/token_validations#validate_token
api_v1_auth_failure GET /api/v1/auth/failure(.:format) devise_token_auth/omniauth_callbacks#omniauth_failure
GET /api/v1/auth/:provider/callback(.:format) devise_token_auth/omniauth_callbacks#omniauth_success
GET /omniauth/:provider/callback(.:format) devise_token_auth/omniauth_callbacks#redirect_callbacks
omniauth_failure GET /omniauth/failure(.:format) devise_token_auth/omniauth_callbacks#omniauth_failure
GET /api/v1/auth/:provider(.:format) redirect(301)
I know that it's a bit messy because of namespaces, but it shouldn't cause this problem, right?
EDIT:
I did some research and here is the link https://github.com/lynndylanhurley/devise_token_auth#usage-tldr it says that /:provider/callback url should have GET/POST action, but as we can see I don't have POST action for callback.
Finally I've solved this problem by adding below line to the routes.rb file.
post '/omniauth/steam/callback', to: 'overrides/omniauth_callbacks#redirect_callbacks'
I've created omniauth_callbacks_controller.rb file in controllers/overrides folder and removed below line.
skip_before_action :set_user_by_token, raise: false
The last step was editing line with redirect route. I've changed this:
redirect_route = "#{request.protocol}#{request.host_with_port}/#{Devise.mappings[devise_mapping].fullpath}/#{params[:provider]}/callback"
To hard-coded route.
redirect_route = "/api/v1/auth/steam/callback"
I'm trying to use URL helpers in a 2.3.11 Ruby on Rails application, but I'm facing many problems with whatever the solution I try...
I've read a lot of "solutions" like including include ActionController::UrlWriter before trying to get a path, but I get the same error every time:
>> app.users_path
NameError: undefined method `new_suggestion_path' for class `ActionController::Integration::Session'
I can't find the problem with this. I have a "suggestions" controller and a "new" action on it... Is there any other way to fix this and get a URL from console and/or Rake?
You need to have resource routes defined for the named routes you are trying to access.
To make suggestion paths available in Rails 2.3, add a resource route config/routes.rb:
ActionController::Routing::Routes.draw do |map|
map.resources :suggestions
end
That will define the following routes:
suggestions GET /suggestions(.:format) {:controller=>"suggestions", :action=>"index"}
POST /suggestions(.:format) {:controller=>"suggestions", :action=>"create"}
new_suggestion GET /suggestions/new(.:format) {:controller=>"suggestions", :action=>"new"}
edit_suggestion GET /suggestions/:id/edit(.:format) {:controller=>"suggestions", :action=>"edit"}
suggestion GET /suggestions/:id(.:format) {:controller=>"suggestions", :action=>"show"}
PUT /suggestions/:id(.:format) {:controller=>"suggestions", :action=>"update"}
DELETE /suggestions/:id(.:format) {:controller=>"suggestions", :action=>"destroy"}
Now you can use those routes in the console:
>> app.new_suggestion_path
=> "/suggestions/new"
>>
I'm getting into Rails and trying to add a "vote" feature on a blog setup from here: http://guides.rubyonrails.org/getting_started.html
In app/controllers/posts_controller.rb I created this:
def incvotes
#post = Post.find(params[:id])
post.update_attributes(:upvotes => 1 )
format.html { redirect_to(#post, :notice => 'Vote counted.') }
format.xml { head :ok }
end
In app/views/posts/index.html.erb I created this:
<%= link_to 'Vote', :controller => "posts", :action => "incvotes", :id => post.id %>
But the link is giving the error
No route matches {:controller=>"posts", :action=>"incvotes", :id=>1}
I'm missing something here, but not sure what.
rake routes:
incvotes_post POST /posts/:id/incvotes(.:format) {:action=>"incvotes", :controller=>"posts"}
posts GET /posts(.:format) {:action=>"index", :controller=>"posts"}
POST /posts(.:format) {:action=>"create", :controller=>"posts"}
new_post GET /posts/new(.:format) {:action=>"new", :controller=>"posts"}
edit_post GET /posts/:id/edit(.:format) {:action=>"edit", :controller=>"posts"}
post GET /posts/:id(.:format) {:action=>"show", :controller=>"posts"}
PUT /posts/:id(.:format) {:action=>"update", :controller=>"posts"}
DELETE /posts/:id(.:format) {:action=>"destroy", :controller=>"posts"}
home_index GET /home/index(.:format) {:action=>"index", :controller=>"home"}
root /(.:format) {:action=>"index", :controller=>"home"}
try
= link_to "vote", incvotes_post_path(post), :method=>:post
and if that doesn't work, try changing the method to :put
My guess is that you probably do not have a definition in your routes file for the action you just defined in the controller. Both an action in the controller and an action in the routes file must be defined for Rails to generate urls correctly.
Your routes file probably has something like this:
resources :posts
But you want to add more than the standard actions generated by the resources keyword, so try something like this:
resources :posts do
member do
post 'incvotes'
end
end
This tells routes that you have another action in your posts controller called incvotes that accepts HTTP post requests as long as they are pointed at a member route with the correct action (/posts/14 is a member route, while /posts/ is a 'collection' route). So you will have a new route probably like /posts/14/incvotes that you can post a form to and everything should start working properly.
EDIT:
Actually I guess since you are just adding 1 to an attribute on a model, you don't need a POST action (which are normally associated with posting forms as with create and update). To send a post, you might need to change the HTML in the view to include a form and have it post to the correct url. So you can try that, or you can change your routes file to read get 'incvotes' instead of post 'incvotes'. Sorry for the confusion, hope that helps!
The incvotes_post route only accepts a HTTP POST, and a link always produces a HTTP GET.
Use a form with a button instead (or do a POST using AJAX).
Try using button_to instead link_to:
In your view:
<%= button_to 'Vote', incvotes_post_path(post) %>
In your config/routes.rb add the route to incvotes action as post:
resources :posts do
member do
post 'incvotes'
end
end
And in your controller, create the incvotes action:
def incvotes
# Something
redirect_to :posts
end
I am new to rails and I have a weird problem i don't understand...
I have created a basic application with only one controller. this controller is name routes (for testing purpose...) and it contains index, new and edit actions.
I have added a resource in the routes.rb file: map.resources :routes
The problem I have is when i try to make a link to an action like link_to edit_route_path(some id) I get the error undefined local variable or method `path' for #ActionController::Routing::RouteSet:0x101f4d088>
When I use routes_path directly, it works fine.
Thanks for your help!
output of rake routes:
routes GET /routes(.:format) {:controller=>"routes", :action=>"index"}
POST /routes(.:format) {:controller=>"routes", :action=>"create"}
new_route GET /routes/new(.:format) {:controller=>"routes", :action=>"new"}
edit_route GET /routes/:id/edit(.:format) {:controller=>"routes", :action=>"edit"}
route GET /routes/:id(.:format) {:controller=>"routes", :action=>"show"}
PUT /routes/:id(.:format) {:controller=>"routes", :action=>"update"}
DELETE /routes/:id(.:format) {:controller=>"routes", :action=>"destroy"}
/:controller/:action/:id
/:controller/:action/:id(.:format)
this is the error I have:
undefined local variable or method `path' for #ActionController::Routing::RouteSet:0x101f4d128>
and the stack trace:
/opt/local/lib/ruby/gems/1.8/gems/actionpack-2.3.8/lib/action_controller/routing/route_set.rb:386:in generate'
/opt/local/lib/ruby/gems/1.8/gems/actionpack-2.3.8/lib/action_controller/url_rewriter.rb:208:inrewrite_path'
/opt/local/lib/ruby/gems/1.8/gems/actionpack-2.3.8/lib/action_controller/url_rewriter.rb:187:in rewrite_url'
/opt/local/lib/ruby/gems/1.8/gems/actionpack-2.3.8/lib/action_controller/url_rewriter.rb:165:inrewrite'
/opt/local/lib/ruby/gems/1.8/gems/actionpack-2.3.8/lib/action_controller/base.rb:625:in url_for'
/opt/local/lib/ruby/gems/1.8/gems/actionpack-2.3.8/lib/action_view/helpers/url_helper.rb:85:insend'
/opt/local/lib/ruby/gems/1.8/gems/actionpack-2.3.8/lib/action_view/helpers/url_helper.rb:85:in url_for'
(eval):17:inedit_blog_path'
/Users/guillaume/Projets/rails/testroutes/app/views/blogs/edit.html.erb:4:in `_run_erb_app47views47blogs47edit46html46erb'
ruby version is 1.8.7
gem version is 1.3.7
rails version is 2.3.8
I tried the basic posts scaffold from the rails getting started user guide and i have the same error when I am in the new page or edit page...
ActionController::Routing::Routes.draw do |map|
map.resources :routes
map.connect ':controller/:action/:id'
map.connect ':controller/:action/:id.:format'
end
The weird thing is that everything was working fine last week and I don't know what i have changed...
Thank you very much!!!
Go to terimnal and type
rake routes
It will show you all possible routes define in your routes.rb file.
Then check edit_route_path is there or not
Hi i have this starnge behavoir...
<%= link_to image_tag("image.png"), brain_path(1), :method => "put" %>
produces:
<img alt="Research_4" src="/images/image.png" />
a href="/foobar.1" this is the strange part :( any ideas whqt is causing this?
rake routes gives the following:
new_brain GET /brain/new(.:format) {:controller=>"brains", :action=>"new"}
edit_brain GET /brain/edit(.:format) {:controller=>"brains", :action=>"edit"}
brain GET /brain(.:format) {:controller=>"brains", :action=>"show"}
PUT /brain(.:format) {:controller=>"brains", :action=>"update"}
DELETE /brain(.:format) {:controller=>"brains", :action=>"destroy"}
POST /brain(.:format) {:controller=>"brains", :action=>"create"}
How do you route your foobar? (singular or plural? resource or resources?)
Are you sure that you're using foobar_path(1), not foobars_path(1) (singular form)
in real life foobars_path(1) will return /foobars.1 and foobar_path(1) - /foobar/1
as I see you have to use brain_path(1) not brain_path(1)
UPD
Change your route.rb
map.resources :brain
it will be better if you'll rename your controller into pluralize brains - it is more conventional when you are using resources