I'm trying to have ajax login using devise, but I can't seem to get this working. The problem is that I have confirmable strategy enabled on devise, warden.authenticate! should fail on inactive users and render the failure
action, instead it renders the default action. I notice that many tutorials have the same set ups. I am using rails 4.0.0 and devise 3.2.2.
class SessionsController < Devise::SessionsController
def create
#problem: failure not getting called
resource = warden.authenticate!(scope: resource_name, recall: "#{controller_path}#failure")
sign_in(resource_name, resource)
render json: {success: true}
end
def failure
render json: {success: false, errors: ["Login failed!"]}
end
end
The devise.rb is set up as follow,
config.http_authenticatable_on_xhr = false
config.navigational_formats = ['*/*', :'*/*', :html, :json]
The routes.rb has the following,
devise_for :users, controllers: {registrations: "registrations", sessions: "sessions"}
The signin form,
<%= form_for(resource, as: resource_name,
url: session_path(resource_name),
format: :json,
html:{id:"signin_form"},
remote: true) do |f| %>
<%= f.label(:email, "Email") %>
<%= f.text_field(:email, class: "field text") %>
<%= f.label(:password, "Password") %>
<%= f.text_field(:password, class: "field text", id: "user_signin_password") %>
<%= f.submit "Sign in", class: "theme_color btn key" %>
<% end %>
Since the failure
action is not getting called, the default new
action is rendered with response header as follow,
Content-Type text/html; charset=utf-8
Location http://localhost:3000/users/sign_in.js
I am also curious why it renders .js
instead of .json
.
Can someone point me out what I missed? Thanks
After spending hours debugging the app, I found there's a bug inside devise's activatable.rb file. As I follow along with the options and found that the devise's registered hook after_set_user
does not throw with the recall
option.
This seems only happen to inactive accounts(have confirmable strategy enabled, but account has not yet confirmed) trying to login with an existed email/username. However, if trying to login with a nonexisten email/username, the above does works as authenticate!
throws :warden with the recall
option.
I'm glad there's someone also found the same bug and provided the patch, but am curious why they don't merge with it. solution can be found here!
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With