Ruby on rails RubyonRails上的多种用户类型
我是RubyonRails新手,一直在学习教程。 但我需要更多的信息 我正在构建一个应用程序,允许访问各种类型的用户,他们是,学生,家长,教师和管理人员(所有人都有相同的属性) 到目前为止,我有一个用户模型,它有字段、电子邮件和密码,作为登录站点的凭据 然后我为每种类型的用户创建了一个模板。 模范学生 模范教师 .... 我想知道的是如何注册一个用户,指的是每种类型的用户,而我已经有了一个表用户 我一直在寻找,我意识到使用“设计”将是一个可行的解决方案,但我不太明白它是如何工作的Ruby on rails RubyonRails上的多种用户类型,ruby-on-rails,Ruby On Rails,我是RubyonRails新手,一直在学习教程。 但我需要更多的信息 我正在构建一个应用程序,允许访问各种类型的用户,他们是,学生,家长,教师和管理人员(所有人都有相同的属性) 到目前为止,我有一个用户模型,它有字段、电子邮件和密码,作为登录站点的凭据 然后我为每种类型的用户创建了一个模板。 模范学生 模范教师 .... 我想知道的是如何注册一个用户,指的是每种类型的用户,而我已经有了一个表用户 我一直在寻找,我意识到使用“设计”将是一个可行的解决方案,但我不太明白它是如何工作的 有人向我解释
有人向我解释一下最好的方法吗?以最简单的形式,您希望能够在注册时选择用户类型
class User
belongs_to: user_type
end
class UserType
has_many: users
end
基于这种简单的一对多关系,您可以将表单中的用户类型传递给控制器,并让控制器负责创建/关联对象
user = User.create(params[:user])
user.user_type = UserType.find(params[:user][:user_type])
这是一些非常简单、快速的代码,目的是让我的观点更加清晰。好吧,下面是我将如何实现它 1) 创建帐户模型并在其迁移中添加多态引用,如下所示
class Account < ActiveRecord:Migration
def change
create_table :accounts do |t|
t.references :user, :polymorphic => true
t.column :name, :string
end
end
end
类帐户true
t、 列:名称,:字符串
结束
结束
结束
2) 在每个模型类中,例如学生类,我将添加以下代码行
class Student < ActiveRecord::Base
has_one :account, :as => :user
end
class-Student:用户
结束
3) 帐户模型类中的
class Account < ActiveRecord::Base
belongs_to :user, :polymorphic => true
end
类帐户true
结束
4) 为帐户模型使用设计生成器
5) 最大的挑战是创建一个新的学生,基本上您将创建一个帐户记录,然后将此帐户记录分配给新创建的学生记录
a) 有两种方法可以做到这一点:
*使用嵌套表单。
*使用一个简单的表单,让控制器完成工作
我鼓励第二种选择,选择最适合您的,如果您有任何问题,请告诉我。如果您需要不同的应用程序权限,也许您希望为您的用户分配角色。这可以通过许多不同的方式实现。一个简单的方法是使用RolifGem:正如其他答案所示,有几种方法可以解决这个问题。首先,确保您了解身份验证(创建用户并登录)和基于角色的授权(根据用户的角色控制对web应用程序不同部分的访问)之间的区别。您可以自己实现身份验证,但大多数Rails开发人员使用Desive gem,因为它健壮、功能齐全且经过良好测试。授权可以通过简单地添加到用户模型中来实现,尽管开发人员通常在复杂的应用程序中使用或gems 对于您描述的用例,我建议在您的用户模型中实现一种非常基本的基于角色的授权形式。首先,您必须使用Desive创建一个用户模型 Rails 4.1中引入的活动记录的一个新特性Enum是实现基于角色的授权的最简单方法 创建迁移:
$ rails generate migration AddRoleToUsers role:integer
迁移将如下所示:
class AddRoleToUsers < ActiveRecord::Migration
def change
add_column :users, :role, :integer
end
end
您可以在控制器中使用条件:
class UsersController < ApplicationController
def index
unless current_user.admin?
redirect_to :back, :alert => "Access denied."
end
@users = User.all
end
end
class UsersController“访问被拒绝。”
结束
@users=User.all
结束
结束
或者在视图中使用它:
<% if current_user.parent? %>
<li><%= link_to 'Grade Reports', some_path %></li>
<% end %>
通常,如果访问控制向控制器添加了大量代码,建议您使用或,因为您可以将复杂的授权逻辑移动到与控制器隔离的中心位置(“瘦控制器”)。但是,如果您的需求像您描述的那样简单,那么控制器中基于角色的授权是最佳的
我已经编写了一个教程,比较了这两种方法,并提供了有关简单的基于角色的授权以及使用Pundit的基于角色的授权的更多详细信息。
type
属性是为单表继承保留的,在这种情况下什么是合适的,但至少您应该指定这个答案意味着STI,学生和教师模型应该继承自用户。谢谢您的评论@CV Gate。我修改了我的答案。这里我没有使用STI。谢谢你的回答。也许我不是很清楚,但我已经有了一个页面,可以通过我的用户模型创建一个用户(我可以登录和注销,并验证这个“表”的所有数据)。现在,我想把两个模型的数据(User和UserType-Student/Parents/Admin/etc)放在同一个页面中,然后将所有数据保存到各自的模型中。回答得很好!注意:我得到一个错误,说我不能在枚举中有一个字段“:parent”,因为这个类已经有一个方法“parent”,它是由活动记录定义的。谢谢Daniel,我喜欢使用自定义代码而不是gem。我只是想知道如果我想让用户拥有多个角色该怎么办。例如,用户有角色::teacher和:adminNice。另外,由于默认角色是在初始化之后设置的。迁移可以包括默认值,而不是使用回调。类似于:add_column:users,:role,:integer,默认值:0
在学生模型/其他模型中是否仍有必要/可能将用户模型的用户标识定义为外键?谢谢
class UsersController < ApplicationController
def index
unless current_user.admin?
redirect_to :back, :alert => "Access denied."
end
@users = User.all
end
end
<% if current_user.parent? %>
<li><%= link_to 'Grade Reports', some_path %></li>
<% end %>