[英]devise and multiple “user” models
我正在使用rails 3.2和設計2.0,我對Rails很新。
我想實現以下目標:
我用Google搜索並搜索了StackOverflow很長一段時間,但對我來說似乎沒什么問題(我是一個Java人,對不起:)現在我很困惑。 出現了兩個解決方案:
這是最常見的答案。 只需創建默認設備用戶並在會員 - >用戶和客戶 - >用戶之間創建關系。 我關注的是如何為每個模型實現自定義注冊流程? 我嘗試了不同的東西,但一切都結束了!
這解決了自定義注冊過程,對我來說似乎是正確的,但唯一的登錄表單是一個阻止程序。 我在SO( Devise - 從兩個模型登錄 )上找到了答案,建議覆蓋Devise :: Models :: Authenticatable.find_for_authentication(條件)。 這似乎很復雜(?),因為我是鐵桿新手,我想知道這是否有效?
謝謝你的建議!
歡迎加入Java guy =),我希望你會喜歡Rails世界。 簡單地說,要解決您的問題,您有兩個解決方案:
哪一個選擇? 它取決於角色的共同屬性。 如果它們幾乎是常見的(例如,所有都有名稱,電子郵件,移動設備......)並且一些屬性不同,我強烈推薦STI解決方案。
如何做STI? 1.只需使用命令rails generate devise User
創建設計用戶模型和表rails generate devise User
2.使用遷移將名為type
with string datatype的列添加到數據庫中的用戶表。 3.為每個用戶類型創建一個模型(例如rails g model admin
)4。使Admin類繼承自用戶模型
class Admin < User
end
那就是你做完了=)...... Yupeee
要創建管理員,請運行命令Admin.create(...)
,其中點是管理員屬性,例如電子郵件,名稱,...
我認為這個問題對你也有幫助
在嘗試各種各樣的方法之后,我和你一樣,我使用單一的User模型,這將屬於多態角色。 這似乎是實現單一登錄的最簡單方法。
用戶模型將包含特定於登錄的信息。
角色模型將存儲特定於每個角色的字段,以及特定於該角色的其他關聯。
將通過各個控制器為每個用戶類型(角色)自定義新注冊,然后為用戶構建嵌套屬性。
class User < ActiveRecord::Base
#... devise code ...
belongs_to :role, :polymorphic => true
end
class Member < ActiveRecord::Base
attr_accessible :name, :tel, :city #etc etc....
attr_accessible :user_attributes #this is needed for nested attributes assignment
#model specific associations like
has_many :resumes
has_one :user, :as => :role, dependent: :destroy
accepts_nested_attributes_for :user
end
路線 - 只是會員模型的常規內容。
resources :members
#maybe make a new path for New signups, but for now its new_member_path
控制器 - 您必須使用build_user來嵌套屬性
#controllers/members_controller.rb
def new
@member = Member.new
@member.build_user
end
def create
#... standard controller stuff
end
視圖/構件/ new.html.erb
<h2>Sign up for new members!</h2>
<%= simple_form_for @member do |f| %>
# user fields
<%= f.fields_for :user do |u| %>
<%= u.input :email, :required => true, :autofocus => true %>
<%= u.input :password, :required => true %>
<%= u.input :password_confirmation, :required => true %>
<% end %>
# member fields
<%= f.input :name %>
<%= f.input :tel %>
<%= f.input :city %>
<%= f.button :submit, "Sign up" %>
<% end %>
我想指出,沒有必要達到nested_form gem; 因為要求是用戶只能屬於一種類型的角色。
我找到了一條路可走,到目前為止我對它很滿意。 我會在這里為其他人描述。
我選擇了單一的“用戶”課程。 我的問題是為每個偽模型實現自定義注冊過程。
型號/ user.rb:
class User < ActiveRecord::Base
devise :confirmable,
:database_authenticatable,
:lockable,
:recoverable,
:registerable,
:rememberable,
:timeoutable,
:trackable,
:validatable
# Setup accessible (or protected) attributes for your model
attr_accessible :email, :password, :password_confirmation, :remember_me, :role
as_enum :role, [:administrator, :client, :member]
validates_as_enum :role
## Rails 4+ for the above two lines
# enum role: [:administrator, :client, :member]
end
然后我調整了http://railscasts.com/episodes/217-multistep-forms和http://pastie.org/1084054以獲得兩個帶有重寫控制器的注冊路徑:
配置/ routes.rb文件:
get 'users/sign_up' => 'users/registrations#new', :as => 'new_user_registration'
get 'clients/sign_up' => 'users/registrations#new_client', :as => 'new_client_registration'
post 'clients/sign_up' => 'users/registrations#create', :as => 'client_registration'
get 'members/sign_up' => 'users/registrations#new_member', :as => 'new_member_registration'
post 'members/sign_up' => 'users/registrations#create', :as => 'member_registration'
控制器/用戶/ registrations_controller.rb:
我創建了一個向導類,它知道要在每一步驗證的字段
class Users::RegistrationsController < Devise::RegistrationsController
# GET /resource/sign_up
def new
session[:user] ||= { }
@user = build_resource(session[:user])
@wizard = ClientRegistrationWizard.new(current_step)
respond_with @user
end
# GET /clients/sign_up
def new_client
session[:user] ||= { }
session[:user]['role'] = :client
@user = build_resource(session[:user])
@wizard = ClientRegistrationWizard.new(current_step)
render 'new_client'
end
# GET /members/sign_up
def new_member
# same
end
# POST /clients/sign_up
# POST /members/sign_up
def create
session[:user].deep_merge!(params[:user]) if params[:user]
@user = build_resource(session[:user])
@wizard = ClientRegistrationWizard.new(current_step)
if params[:previous_button]
@wizard.previous
elsif @user.valid?(@wizard)
if @wizard.last_step?
@user.save if @user.valid?
else
@wizard.next
end
end
session[:registration_current_step] = @wizard.current_step
if @user.new_record?
clean_up_passwords @user
render 'new_client'
else
#session[:registration_current_step] = nil
session[:user_params] = nil
if @user.active_for_authentication?
set_flash_message :notice, :signed_up if is_navigational_format?
sign_in(:user, @user)
respond_with @user, :location => after_sign_up_path_for(@user)
else
set_flash_message :notice, :"signed_up_but_#{@user.inactive_message}" if is_navigational_format?
expire_session_data_after_sign_in!
respond_with @user, :location => after_inactive_sign_up_path_for(@user)
end
end
end
private
def current_step
if params[:wizard] && params[:wizard][:current_step]
return params[:wizard][:current_step]
end
return session[:registration_current_step]
end
end
我的意見是:
new.rb
new_client.rb
包括根據向導步驟的部分:
_new_client_1.rb
_new_client_2.rb
new_member.rb
包括根據向導步驟的部分:
_new_member_1.rb
_new_member_2.rb
那有什么不對? 只需運行rails g devise:views [model_name]
,自定義每個注冊表單,並在config/initializer/devise.rb
config.scoped_views = true
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.