簡體   English   中英

設計-通過電子郵件或用戶名登錄

[英]Devise - sign in by email OR username

我已經完成了所有本教程: Devise Wiki

但是,當我嘗試登錄時,在瀏覽器中出現錯誤:

SQLite3::SQLException: no such column: users.login: SELECT "users".* FROM "users" WHERE "users"."login" = 'jan12345' ORDER BY "users"."id" ASC LIMIT 1

哪里可能有問題? 如何調試呢?

我在users表上沒有login字段,但是有username段。

我的模型文件:

class ApplicationController < ActionController::Base
  # Prevent CSRF attacks by raising an exception.
  # For APIs, you may want to use :null_session instead.
  attr_accessor :login
  protect_from_forgery with: :exception

  before_action :configure_permitted_parameters, if: :devise_controller?

  protected

  def configure_permitted_parameters
    devise_parameter_sanitizer.for(:sign_up) { |u| u.permit(:username, :email, :password, :password_confirmation, :remember_me, :first_name, :last_name, :expiration_date) }
    devise_parameter_sanitizer.for(:sign_in) { |u| u.permit(:login, :username, :email, :password, :remember_me) }
  end
end

您正在將login屬性發送到數據庫; 您需要將其設置為usernameemail ,這是根據docs結合使用自定義屬性和特殊查找來完成的

#app/models/user.rb
class User < ActiveRecord::Base
  #remove attr_accessor :login (it just makes getter/setter methods which we do manually below)

  protected

  def login=(login)
    @login = login
  end

  def login
    @login || self.username || self.email
  end

  private

  def self.find_for_database_authentication(warden_conditions)
      conditions = warden_conditions.dup
      if login = conditions.delete(:login)
         where(conditions.to_h).where(["lower(username) = :value OR lower(email) = :value", { :value => login.downcase }]).first
      else
         where(conditions.to_h).first
      end
  end
end

-

你已經做了消毒液等大量的工作-你正在做的是采取單一的“登錄”屬性及制作設計請使用 loginusernameemail找到User的記錄。

目前,錯誤提示無法找到users.login ,這意味着您的Devise安裝程序應在login username (帶有login屬性的email搜索時查找login (不在數據庫中)。

代碼的第二位( self.find_for_database_authentication )對Devise執行查找。 如果你讀了查詢,它需要的login 屬性,並將其設置為查找任何 usernameemail 這是您的實現中缺少的,應該添加。

添加后,請記住重新啟動服務器。


更新資料

您的attr_accessor應該在模型中 (您在控制器中)。

它所做的只是為您定義的屬性定義一個settergetter方法。 它最通常稱為“虛擬”屬性 ,因為它沒有保存在數據庫中。

如果需要的話,我可以告訴您有關setter / getter方法的信息,為避免混淆,我將暫時保留

在您的initializer / devise.rb中,編寫以下代碼:

config.authentication_keys = [:用戶名]

在應用程序控制器中,編寫以下代碼:

 def configure_permitted_parameters
    devise_parameter_sanitizer.for(:sign_up) { |u| u.permit(:username) }
    devise_parameter_sanitizer.for(:sign_in) { |u| u.permit(:username) }
 end

您不必做那么多的代碼,

您可以從https://stackoverflow.com/a/55184048/9490901檢查,

僅將contact_number替換為username:

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM