I create URL for sign out from system:
<li><%= link_to("Выйти", "http://bookworm.az:3000/logout") %></li>
Sessions Controllers Destroy action:
def destroy
session[:username] = nil
redirect_to "http://bookworm.az:3000/login"
end
And my routes are:
get '/logout' => 'sessions#destroy'
But when I click on link it redirects me to the
http://bookworm.az:3000/logout
Not to
http://bookworm.az:3000/login
What is the problem?
Your code is breaking Rails conventions. You should use this one instead:
view.rb
link_to "Delete", session_path(current_session), method: :delete
You should not change routes.rb resources. Keep it simple:
routes.rb
resources :sessions
Also, you should use URL helper that Rails generates from your routes.rb file, instead of using an absolute path (unless there is no other way).
I'm newer to Rails and having an issue with my routes on a simple blog. I have the following routes below. When I navigate to example.com/posts then click on a post, everything seems to work fine. If I click on the Post link in my navbar to go back to example.com/post I end up with example.com/posts/posts. I've tried several different things from the Rails guide and just can't seem to figure this out. Thank you in advance for the assistance.
TestBed::Application.routes.draw do
resources :posts do
resources :comments
end
root "pages#home"
get "/home", to: "pages#home", as: "home"
end
Edited to add navbar details
<li><%= link_to "Blog", "posts" %></li>
In your link_to helper you have "posts" as the URL. This appends the string posts to the end of the current url, which is the reason why you're seeing example.com/posts/posts.
To have the link properly point to /posts, modify your link_to call as follows:
<li><%= link_to "Blog", "/posts" %></li>
or use route helper:
<li><%= link_to "Blog", posts_path %></li>
Sign-out link isn't working in my rails application.
I have checked my routes.rb which is listed below and my application.html.erb looks to follow the right path.
Getting the following error.
ActiveRecord::RecordNotFound in UsersController#show
Couldn't find User with id=sign_out
Rails.root: /Users/patrickwalsh/rails_projects/ytutorial
Application Trace | Framework Trace | Full Trace
app/controllers/users_controller.rb:4:in `show'
lib/disable_assets_logger.rb:11:in `call'
My routes.rb
Refectory::Application.routes.draw do
devise_for :users, :controllers => { :registrations => "users" }
devise_scope :user do
get 'login', to: "devise/sessions#new", as: "login"
get 'logout', to: "devise/sessions#destroy", as: "logout"
get 'logout', to: "users/sessions#destroy", as: "logout"
get 'signup', to: "users#new", as: "signup"
match '/users/:id', :to => 'users#show', :as => :user
end
root :to => 'tutorials#index'
devise_for :users do get '/users/sign_out' => 'devise/sessions#destroy'
get 'users/:id' => 'users#show'
end
resources :tutorials
resources :comments, only: [:show, :create, :update, :destroy]
resources :tutorials do
member { post :vote }
end
if Rails.env == "development"
match 'errors/404' => 'errors#error_404'
match 'errors/500' => 'errors#error_500'
end
unless Rails.application.config.consider_all_requests_local
match '*not_found', to: 'errors#error_404'
end
match 'tagged' => 'tutorials#tagged', :as => 'tagged'
end
and my application.html which seems to be following the right route from what I can see.
Any help is greatly appreciated!
<% if current_user.present? %>
<li><%= link_to "Log out", destroy_user_session_path, (:method => "delete") %></li>
<% else %>
<li><%= link_to "Log in", new_user_session_path %></li>
<li><%= link_to "Sign up", new_user_registration_path %></li>
<% end %>
My users controller as well as I have a suspicion this is where the problem lies but not sure what the error is.
class UsersController < Devise::RegistrationsController
def show
#user = User.find(params[:id])
#tutorials = #user.tutorials
end
end
I had the same issue. My routes were in the correct order, the link_to method was properly used, and Rails kept triggering the users/:id route with :id => :sign_out. I figured out that was because I removed jquery_ujs from my application.js file...
jquery_ujs handles the data-method attribute in the links (generated by link_to when you use the method option), which is used to determine the correct route as explained here: https://thoughtbot.com/blog/a-tour-of-rails-jquery-ujs
So just make sure the you have the following included in your application.js:
//= require jquery
//= require jquery_ujs
If you are calling /users/sign_out directly from the URL it won't work because the routes is:
destroy_user_session DELETE /users/sign_out(.:format) devise/sessions#destroy
id est, it uses the DELETE method. You need to change your devise initializer to:
config.sign_out_via = :get
other option would be to create a small form and its button with DELETE as method.
This worked for me
#form
<%= link_to(destroy_user_session_path, {:class => "nav-link", :method => :delete}) do %>
<span class="sidebar-normal"> Logout </span>
<% end %>
#routes
devise_scope :user do
get '/users/sign_out' => 'devise/sessions#destroy'
end
I have started noticing this error after removing rails-ujs. This was done as part of the upgrade to Rails 7 with ImportMap and Hotwire suite. Changing link_to to button_to has fixed this error in this case.
<%= button_to 'Log out', destroy_user_session_path, method: :delete %>
https://edgeguides.rubyonrails.org/working_with_javascript_in_rails.html#replacements-for-rails-ujs-functionality
None of this solutions worked for me.
Also it happens just in development mode for me...
I fixed it by adding
if params[:id] = "sign_out"
sign_out current_user
return
end
in the set user function. Not the prettiest solution but it works...
You need to move:
devise_for :users do get '/users/sign_out' => 'devise/sessions#destroy'
over your devise_scope. Rails is looking for routes from top of Routes file. Your sign out url matches users/:id, hence it is trying to render show action with sign_out being an id.
UPDATE:
Actually, do you really need the last line in your devise_scope block?
Since non of the other answers worked, I found that you could change the base path for every Devise endpoint as described here. So, what I did was to user devise_for on routes.rb:
devise_for :users,
path: 'devise'
Then, all my Devise routes started with devise instead of users so the conflict was gone.
Sorry to bump this up but the "correct" anwser is not to mess around with routes risking breaking many things.
IF you want a disconnect on a GET then actually configure Devise like so in initializer/devise.rb
# The default HTTP method used to sign out a resource. Default is :delete.
config.sign_out_via = :get
As mentionned in the Devise documentation.
Short answer: use link_to with method DELETE
<%= link_to 'Logout', destroy_user_session_path(current_user), method: :delete %>
explanation:
If you take a look at your Routes you'll see
Helper
destroy_user_session_path
the HTTP verb is
DELETE
the Path
/users/sign_out(.:format)
Controller#Action
devise/sessions#destroy
link_to defaoult method is get, this is "the why" (in a simplistic way of explaning). However, you can specify by using method: :method name
I got this error when using devise in a rails 7 app (with bootstrap):
ActiveRecord::RecordNotFound (Couldn't find User with 'id'=sign_out)
I don't fully understand it myself yet, but basically just open another terminal window, type ./bin/dev and hit enter, and (I guess) it loads your javascripts.
I have a logout link that should be routing to users#do_logout but no matter what I do, if I click the link, it routes to the users#show. Here is the code:
Route:
resources :users do
member do
get :profile
post :profile
end
collection do
get "signup", to: 'users#new'
get "login"
post "do_login"
post "do_logout"
end
end
Link:
li = link_to "Sign Out", do_logout_users_path
Users controller action:
def do_logout
session[:user_id] = nil
redirect_to :root
end
Any help would be much appreciated. This is driving me insane.
Your code is not working because, you have set up a POST route for do_logout and your Sign Out link is making a GET request.
To do a POST request from the view, you have to create a form
= form_tag do_logout_users_path do
= submit_tag 'Sign Out'
OR
You could use delete method for this
in routes
delete "do_logout"
and the link
= link_to "Sign Out", do_logout_users_path, :method => :delete
I think it is a routing issue where the controller is not matched properly. I am confused because there is clearly a new action in my ComicTitlesController.
Here is the error I receive when I load the home page, which has the new_user_comic_title_path in the navbar:
Routing Error
No route matches {:action=>"new", :controller=>"comic_titles"}
Try running rake routes for more information on available routes.
In my views:
<li><%= link_to 'Publish' , new_user_comic_title_path %></li>
The ComicTitles controller:
def new
#user = current_user
#comic_title = #user.comic_titles.new
end
Note that ComicTitle is nested under User. Here is the route file:
resources :users, shallow: true do
resources :comic_titles
end
When I run rake routes:
user_comic_titles GET /users/:user_id/comic_titles(.:format) comic_titles#index
POST /users/:user_id/comic_titles(.:format) comic_titles#create
new_user_comic_title GET /users/:user_id/comic_titles/new(.:format) comic_titles#new
edit_comic_title GET /comic_titles/:id/edit(.:format) comic_titles#edit
comic_title GET /comic_titles/:id(.:format) comic_titles#show
PUT /comic_titles/:id(.:format) comic_titles#update
DELETE /comic_titles/:id(.:format) comic_titles#destroy
As you can see the route requires parameter :user_id and your link_to is missing that parameter.
Try updating your link_to definition to following:
<li><%= link_to 'Publish' , new_user_comic_title_path(#user) %></li>
Since you have a nested route, I believe the route is expecting a user_id parameter.
In your link_to helper try adding the following:
<li><%= link_to 'Publish' , new_user_comic_title_path(user_id: current_user.id) %></li>