How do I render a rails named route properly from controller?
routes.rb:
get "logout" => "sessions#destroy", :as => "logout"
get "login" => "sessions#new", :as => "login"
get "signup" => "users#new", :as => "signup"
root :to => "home#index"
resources :users
resources :sessions
resources :likes
user_controller.rb:
def new
#user = User.new
end
def create
#user = User.new params[:user]
if #user.save
login(params[:user][:email], params[:user][:password])
redirect_to root_url, :notice => "Welcome! You have signed up successfully."
else
render :new
end
end
Problem is: the signup page is on /signup and when the data in #user is not filled out properly and render :new is called, instead of going to the url /signup it goes to /users. I would use redirect_to but id prefer not to because I want the errors saved off on the page to tell the users which data was not provided.
Update after added match "signup" => "users#create", :via => "post"
root / {:controller=>"home", :action=>"index"}
users GET /users(.:format) {:action=>"index", :controller=>"users"}
POST /users(.:format) {:action=>"create", :controller=>"users"}
edit_user GET /users/:id/edit(.:format) {:action=>"edit", :controller=>"users"}
user GET /users/:id(.:format) {:action=>"show", :controller=>"users"}
PUT /users/:id(.:format) {:action=>"update", :controller=>"users"}
DELETE /users/:id(.:format) {:action=>"destroy", :controller=>"users"}
signup GET /signup(.:format) {:action=>"new", :controller=>"users"}
POST /signup(.:format) {:action=>"create", :controller=>"users"}
Thanks
Add this route also:
match "signup" => "users#create", :via => "post"
In routes.rb You can add
get "signup", to: "users#new"
post "signup", to: "users#create"
put "signup", to: "users#update"
And in Registration form - Check signup_path
form_for(resource, as: resource_name, url: signup_path, html: {method: 'post'})
For Other Readers who has used devise_for :users, can defined routes as:
devise_scope :user do
get "signup", to: "devise/registrations#new"
post "signup", to: "devise/registrations#create"
put "signup", to: "devise/registrations#update"
end
And Registration form as above.
By adding this routes, you can use your named routes like (register, signup) even after user fills register form with some error.
Related
The issue is I get this nasty little controller error...
NoMethodError in Contacts#new
undefined method `contacts_path' for #<#:0x0000000124b228>
Did you mean? contact_path
on my view: contact#new
<%= form_for #contact do |f| %>
<div class="col-xs-6 form-group contact-input">
<h1><%= f.label :Feedback %></h1>
<%= f.text_area :text, class: "input-lg form-control", rows: "10" %>
<%= f.submit "Send Feedback", class: "btn btn-primary btn-lg" %>
</div>
<% end %>
controller: contacts_controller.rb
class ContactsController < ApplicationController
def new
#contact = Contact.new
end
def create
#contact = Contact.new
if #contact.save
redirect_to '/'
flash[:success] = "Thanks for the Post!"
else
redirect_to contact_path
flash[:alert] = "Please provide input!"
end
end
end
migration:
class CreateContacts < ActiveRecord::Migration
def change
create_table :contacts do |t|
t.text :text
t.timestamps null: false
end
end
end
The error is complaining about line 3 in the view. My model is contact.rb incase I have a plural issue somewhere, but I really do not think that I do. Any help would be much appreciated. This is rails 4.2... I am also a rails beginner.
I know I don't have the flash even setup yet.
rake routes:
Prefix Verb URI Pattern Controller#Action
root GET / static_pages#home
about GET /about(.:format) static_pages#about
news GET /news(.:format) static_pages#news
advertise GET /advertise(.:format) static_pages#advertise
fishing GET /fishing(.:format) static_pages#fishing
signup GET /signup(.:format) users#new
users GET /users(.:format) users#index
POST /users(.:format) users#create
new_user GET /users/new(.:format) users#new
edit_user GET /users/:id/edit(.:format) users#edit
user GET /users/:id(.:format) users#show
PATCH /users/:id(.:format) users#update
PUT /users/:id(.:format) users#update
DELETE /users/:id(.:format) users#destroy
contact GET /contact(.:format) contacts#new
contact_index GET /contact(.:format) contact#index
POST /contact(.:format) contact#create
new_contact GET /contact/new(.:format) contact#new
edit_contact GET /contact/:id/edit(.:format) contact#edit
GET /contact/:id(.:format) contact#show
PATCH /contact/:id(.:format) contact#update
PUT /contact/:id(.:format) contact#update
DELETE /contact/:id(.:format) contact#destroy
forum_comments GET /forums/:forum_id/comments(.:format) comments#index
POST /forums/:forum_id/comments(.:format) comments#create
new_forum_comment GET /forums/:forum_id/comments/new(.:format) comments#new
edit_forum_comment GET /forums/:forum_id/comments/:id/edit(.:format) comments#edit
forum_comment GET /forums/:forum_id/comments/:id(.:format) comments#show
PATCH /forums/:forum_id/comments/:id(.:format) comments#update
PUT /forums/:forum_id/comments/:id(.:format) comments#update
DELETE /forums/:forum_id/comments/:id(.:format) comments#destroy
forums GET /forums(.:format) forums#index
POST /forums(.:format) forums#create
new_forum GET /forums/new(.:format) forums#new
edit_forum GET /forums/:id/edit(.:format) forums#edit
forum GET /forums/:id(.:format) forums#show
PATCH /forums/:id(.:format) forums#update
PUT /forums/:id(.:format) forums#update
DELETE /forums/:id(.:format) forums#destroy
logout DELETE /logout(.:format) sessions#destroy
sessions POST /sessions(.:format) sessions#create
new_session GET /sessions/new(.:format) sessions#new
routes.rb :
Rails.application.routes.draw do
root 'static_pages#home'
get 'about' => 'static_pages#about'
get 'news' => 'static_pages#news'
get 'advertise' => 'static_pages#advertise'
get 'fishing' => 'static_pages#fishing'
get 'signup' => 'users#new'
resources :users
get 'contact' => 'contacts#new'
resources :contact
resources :forums do
resources :comments
end
delete 'logout' => 'sessions#destroy'
resources :sessions, only: [:new, :create]
end
Change resources :contact to resources :contacts in your routes.rb
I am an idiot and thanks to Zepplock just thinking about my routes showed my problem. The get
get 'contact' => 'contacts#new'
was the problem I had. I also switched my resources :contact to :contacts. All my issues were solved. Thanks for asking for the right stuff again Zepplock!
In rails how do I do a link_to a user show page of the current user. Basically i want a link that go to a account page.
I tried it but i get this.
Routing Error No route matches {:action=>"show", :controller=>"users"}
Routes.rb
LootApp::Application.routes.draw do
get "password_resets/new"
get "sessions/new"
get "static_pages/home"
get "static_pages/help"
resources :sessions
resources :password_resets
resources :email_activations
resources :users do
collection do
get :accept_invitation
end
end
root to: 'static_pages#home'
match "sign_up", to: "users#new"
match '/help', to: 'static_pages#help'
match '/log_in', to: 'sessions#new'
match '/log_out', to: 'sessions#destroy'
Application.html.haml
- if current_user
= link_to "log out", log_out_path
- if current_user.admin?
# your admin
- else
= link_to "My account", user_path
- else
= link_to "log in", log_in_path
Users controller
class UsersController < ApplicationController
before_filter :admin_and_user, only: [:destory, :edit, :show]
def show
#user = User.find(params[:id])
end
rake routes
users GET /users(.:format) users#index
POST /users(.:format) users#create
new_user GET /users/new(.:format) users#new
edit_user GET /users/:id/edit(.:format) users#edit
user GET /users/:id(.:format) users#show
PUT /users/:id(.:format) users#update
DELETE /users/:id(.:format) users#destroy
just
<%= link_to current_user.name, current_user%>
The current answer is the best solution, but just to elaborate: The problem that was causing an error in your code was that you needed to specify which user the link should link to. So instead of just user_path should you do like this:
= link_to "My account", user_path(current_user)
A shortcut for this is (as shown in the current answer by #Muntasim)
= link_to "My account", current_user
I have the following going on:
rspec test in users_controller_spec:
it "should redirect to the user show page" do
post :create, :user => #attr
response.should redirect_to(user_path(assigns(:user)))
end
In my users_controller I have the following:
def show
#user = User.find(params[:id])
#title = #user.name
end
def create
#title = "Sign up"
#user = User.new(params[:user])
if #user.save
redirect_to #user, :notice => "Signed Up!"
else
#title = "Sign up"
render "new"
end
end
In my routes.rb I have the following:
Psra::Application.routes.draw do
resources :users
resources :sessions
# Root Route
root :to => 'pages#home'
# Pages Routes
match '/contact', :to => 'pages#contact'
match '/about', :to => 'pages#about'
match '/help', :to => 'pages#help'
match '/signup', :to => 'users#new'
# Users Route
match '/signup', :to => 'users#new'
#Sessions Routes
get "logout" => "sessions#destroy", :as => "logout"
get "login" => "sessions#new", :as => "login"
end
And Here is my rake routes
users GET /users(.:format) {:action=>"index", :controller=>"users"}
POST /users(.:format) {:action=>"create", :controller=>"users"}
new_user GET /users/new(.:format) {:action=>"new", :controller=>"users"}
edit_user GET /users/:id/edit(.:format) {:action=>"edit", :controller=>"users"}
user GET /users/:id(.:format) {:action=>"show", :controller=>"users"}
PUT /users/:id(.:format) {:action=>"update", :controller=>"users"}
DELETE /users/:id(.:format) {:action=>"destroy", :controller=>"users"}
sessions GET /sessions(.:format) {:action=>"index", :controller=>"sessions"}
POST /sessions(.:format) {:action=>"create", :controller=>"sessions"}
new_session GET /sessions/new(.:format) {:action=>"new", :controller=>"sessions"}
edit_session GET /sessions/:id/edit(.:format) {:action=>"edit", :controller=>"sessions"}
session GET /sessions/:id(.:format) {:action=>"show", :controller=>"sessions"}
PUT /sessions/:id(.:format) {:action=>"update", :controller=>"sessions"}
DELETE /sessions/:id(.:format) {:action=>"destroy", :controller=>"sessions"}
root / {:controller=>"pages", :action=>"home"}
contact /contact(.:format) {:controller=>"pages", :action=>"contact"}
about /about(.:format) {:controller=>"pages", :action=>"about"}
help /help(.:format) {:controller=>"pages", :action=>"help"}
signup /signup(.:format) {:controller=>"users", :action=>"new"}
/signup(.:format) {:controller=>"users", :action=>"new"}
logout GET /logout(.:format) {:action=>"destroy", :controller=>"sessions"}
login GET /login(.:format) {:action=>"new", :controller=>"sessions"}
This all results in the following error:
1) UsersController POST 'create' success should redirect to the user show page
Failure/Error: response.should redirect_to(user_path(assigns(:user)))
ActionController::RoutingError:
No route matches {:action=>"show", :controller=>"users"}
# ./spec/controllers/users_controller_spec.rb:95:in `block (4 levels) in <top (required)>'
Any ideas on what I'm doing wrong?
It looks like to me that the show action isn't getting the user information it needs to get the correct page. The assigns method is just creating an instance variable. The user_path call will need a User mock or object to make the call work correctly.
I tried to follow the instructions here (GitHub Devise Wiki) but it's not working for me.
I'm trying to get Devise to redirect to /welcome after user signs up. I created a Registrations controller but it's never going into the view. What am I doing wrong here?
Ruby 1.9.2
Rails 3.1.0.rc4
Devise 1.4.2
Thank you
UPDATE:
For some reason after_sign_up_path_for is not triggered but after_sign_in_path_for is triggered. I would still like to get after_sign_up_path_for to work though
_app/controllers/registrations_controller.rb_
class RegistrationsController < Devise::RegistrationsController
protected
def after_sign_up_path_for(resource)
welcome_path
end
end
Here's my config/routs.rb
MyApp::Application.routes.draw do
devise_for :users
root :to => 'pages#home'
match "/users", :to => "users#all"
match "/users/:id", :to => "users#show", :as => :user
match "/welcome", :to => "users#welcome", :as => :user
devise_for :users, :controllers => { :registrations => "registrations" } do
get "/login", :to => "devise/sessions#new"
get "/register", :to => "devise/registrations#new"
get "/logout", :to => "devise/sessions#destroy"
get '/account' => 'devise/registrations#edit'
end
end
Output from rake routes
new_user_session GET /users/sign_in(.:format) {:action=>"new", :controller=>"devise/sessions"}
user_session POST /users/sign_in(.:format) {:action=>"create", :controller=>"devise/sessions"}
destroy_user_session DELETE /users/sign_out(.:format) {:action=>"destroy", :controller=>"devise/sessions"}
user_omniauth_callback /users/auth/:action/callback(.:format) {:action=>/(?!)/, :controller=>"devise/omniauth_callbacks"}
user_password POST /users/password(.:format) {:action=>"create", :controller=>"devise/passwords"}
new_user_password GET /users/password/new(.:format) {:action=>"new", :controller=>"devise/passwords"}
edit_user_password GET /users/password/edit(.:format) {:action=>"edit", :controller=>"devise/passwords"}
PUT /users/password(.:format) {:action=>"update", :controller=>"devise/passwords"}
cancel_user_registration GET /users/cancel(.:format) {:action=>"cancel", :controller=>"devise/registrations"}
user_registration POST /users(.:format) {:action=>"create", :controller=>"devise/registrations"}
new_user_registration GET /users/sign_up(.:format) {:action=>"new", :controller=>"devise/registrations"}
edit_user_registration GET /users/edit(.:format) {:action=>"edit", :controller=>"devise/registrations"}
PUT /users(.:format) {:action=>"update", :controller=>"devise/registrations"}
DELETE /users(.:format) {:action=>"destroy", :controller=>"devise/registrations"}
root / {:controller=>"pages", :action=>"home"}
users /users(.:format) {:controller=>"users", :action=>"all"}
user /users/:id(.:format) {:controller=>"users", :action=>"show"}
user /welcome(.:format) {:controller=>"users", :action=>"welcome"}
login GET /login(.:format) {:controller=>"devise/sessions", :action=>"new"}
register GET /register(.:format) {:controller=>"devise/registrations", :action=>"new"}
logout GET /logout(.:format) {:controller=>"devise/sessions", :action=>"destroy"}
account GET /account(.:format) {:controller=>"devise/registrations", :action=>"edit"}
new_user_session GET /users/sign_in(.:format) {:action=>"new", :controller=>"devise/sessions"}
POST /users/sign_in(.:format) {:action=>"create", :controller=>"devise/sessions"}
destroy_user_session DELETE /users/sign_out(.:format) {:action=>"destroy", :controller=>"devise/sessions"}
user_omniauth_callback /users/auth/:action/callback(.:format) {:action=>/(?!)/, :controller=>"devise/omniauth_callbacks"}
POST /users/password(.:format) {:action=>"create", :controller=>"devise/passwords"}
GET /users/password/new(.:format) {:action=>"new", :controller=>"devise/passwords"}
GET /users/password/edit(.:format) {:action=>"edit", :controller=>"devise/passwords"}
PUT /users/password(.:format) {:action=>"update", :controller=>"devise/passwords"}
GET /users/cancel(.:format) {:action=>"cancel", :controller=>"registrations"}
POST /users(.:format) {:action=>"create", :controller=>"registrations"}
GET /users/sign_up(.:format) {:action=>"new", :controller=>"registrations"}
GET /users/edit(.:format) {:action=>"edit", :controller=>"registrations"}
PUT /users(.:format) {:action=>"update", :controller=>"registrations"}
DELETE /users(.:format) {:action=>"destroy", :controller=>"registrations"}
You have devise_for :users twice in your routes.rb. Change the routes.rb as follows:
MyApp::Application.routes.draw do
devise_for :users, :controllers => { :registrations => "registrations" } do
get "/login", :to => "devise/sessions#new"
get "/register", :to => "devise/registrations#new"
get "/logout", :to => "devise/sessions#destroy"
get '/account' => 'devise/registrations#edit'
end
root :to => 'pages#home'
match "/users", :to => "users#all"
match "/users/:id", :to => "users#show", :as => :user
match "/welcome", :to => "users#welcome", :as => :user
end
If you have activation/deactivation logic, you have to override after_inactive_sign_up_path_for too as mentioned in the devise wiki. Can you tell where it is getting redirected to after sign up?
The reason why after_sign_in_path_for is working may be that you have the same sessions_controller and different registrations_controller, so sign-in works as you expected and the registrations route is getting blocked because you have defined it twice, so all the registration requests and actions are executed in the devise/registrations rather than your custom registrations controller.
So remove that, change the routes.rb as mentioned above, and see what happens.
Your devise_for looks kind of odd. The after_sign_up_path_for should go fine as a public method in your application_controller.rb
Change your routes file to just be devise_for :users, as well as placing after_sign_up_path_for in your application_controller.rb
You have duplicate devise_for listings in your routes.rb file. Try removing the first one, the simple devise_for :users, and leaving only the second one.
In my application I have the after_sign_in_path_for method in my application_controller.rb file. Try putting it in there, restarting your server and see if that makes any difference. Also, I don't have my method listed under protected but rather private.
If you want to redirect users to a welcome page after signup, it sounds like you just want to redirect them after a successful user create. So your users_controller would look something like this:
class UsersController < ApplicationController
def new
#user = User.new
end
def create
#user = User.new(params[:user])
if #user.save
flash[:notice] = "Registration successful."
redirect_to welcome_path
else
render :action => 'new'
end
end
def show
#user = User.find(params[:id])
end
def edit
#user = User.find(params[:id])
end
def update
#user = User.find(params[:id])
if #user.update_attributes(params[:user])
flash[:notice] = "Successfully updated user."
redirect_to #user
else
render :action => 'edit'
end
end
end
The instructions worked fine for me (new Registrations controller, modify routes.rb and copy the registrations views to app/view/registrations) but I needed to change my routes.rb slightly so that registrations controllers was picked up. Order is important as the first matching route is going to be used - and you want that to be the new registration route.
devise_for :users, :controllers => { :registrations => "registrations" }
devise_for :users
(make sure devise_for :users comes after the new route for registrations)
https://github.com/plataformatec/devise/blob/master/app/controllers/devise/registrations_controller.rb#L82
I am trying to track down a particularly elusive bug in working through Michael Hartl's ROR Tutorial.
When clicking on 'Delete' for a micropost (from the home page or the user/show page) the url is http://localhost:3000/microposts/303, but the result is "Routing Error - No route matches"/microposts/303".
I have gone through each page of my code that is involved and replaced them with code from Hartl's gitHub project site. https://github.com/railstutorial/sample_app. For example, for the microposts_controller, I copied the code from the gitHub depot and replaced my code with the copied code. I then restarted the server. Same result. I then reverted back to my code to test the next page.
The pages I swapped the code with are
CONTROLLERS
microposts_controller
users_controller (show method)
MODEL
micropost.rb (model)
VIEWS
microposts/_micropost.haml
shared/_micropost_form.html.haml
shared/_feed.haml
shared/_feed_item.haml
and the Routes file.
I am at a loss for other things to check. Does anyone have any suggestions?
Thanks,
Dave
The results of rake routes
sessions POST /sessions(.:format) {:action=>"create", :controller=>"sessions"}
new_session GET /sessions/new(.:format) {:action=>"new", :controller=>"sessions"}
session DELETE /sessions/:id(.:format) {:action=>"destroy", :controller=>"sessions"}
signin /signin(.:format) {:controller=>"sessions", :action=>"new"}
signout /signout(.:format) {:controller=>"sessions", :action=>"destroy"}
microposts POST /microposts(.:format) {:action=>"create", :controller=>"microposts"}
micropost DELETE /microposts/:id(.:format) {:action=>"destroy", :controller=>"microposts"}
root /(.:format) {:controller=>"pages", :action=>"home"}
contact /contact(.:format) {:controller=>"pages", :action=>"contact"}
about /about(.:format) {:controller=>"pages", :action=>"about"}
help /help(.:format) {:controller=>"pages", :action=>"help"}
signup /signup(.:format) {:controller=>"users", :action=>"new"}
development /development(.:format) {:controller=>"pages", :action=>"development"}
/signup(.:format) {:controller=>"users", :action=>"new"}
users GET /users(.:format) {:action=>"index", :controller=>"users"}
POST /users(.:format) {:action=>"create", :controller=>"users"}
new_user GET /users/new(.:format) {:action=>"new", :controller=>"users"}
edit_user GET /users/:id/edit(.:format) {:action=>"edit", :controller=>"users"}
user GET /users/:id(.:format) {:action=>"show", :controller=>"users"}
PUT /users/:id(.:format) {:action=>"update", :controller=>"users"}
DELETE /users/:id(.:format) {:action=>"destroy", :controller=>"users"}
The Routes.rb file is
SampleApp::Application.routes.draw do
#Sign in Routes
resources :sessions, :only => [:new, :create, :destroy]
match '/signin', :to => 'sessions#new'
match '/signout', :to => 'sessions#destroy'
#Microposts Routes
resources :microposts, :only => [:create, :destroy]
#Pages Routes
root :to => "pages#home"
match '/contact', :to => 'pages#contact'
match '/about', :to => 'pages#about'
match '/help', :to => 'pages#help'
match '/signup', :to => 'users#new'
match '/development', :to => 'pages#development'
#Users Routes
match '/signup', :to => 'users#new'
resources :users
end
But, as I said, even replacing my routes file with the one on gitHub did not resolve the issue.
The link to delete is
= link_to "delete", micropost, :method => :delete,
:confirm => "You sure?",
:title => micropost.content
link_to :method => :delete uses unobtrusive javascript to create the DELETE request. My guess is that you either don't have the necessary javascript files in your project (prototype.js/jquery.js and rails.js) or you are not including them in your layout.