我正在使用devise
和apartment
宝石创建多租户应用。我正在使用postgresql数据库。我创造了一些模型。 '用户'模型位于全局命名空间中,用于由devise gem进行身份验证。还有一些其他模型(例如Project,Setting等)位于租户命名空间中。
我已经按照本教程创建了这个多租户应用:https://gorails.com/episodes/multitenancy-with-apartment?autoplay=1
如果我从相关帐户(例如user1@gmail.com和user2 @)登录两个单独的子域(例如user1.example.com和user2.example.com),多租户功能在某种意义上工作正常gmail.com)它工作正常,我可以为每个租户创建独特的记录。
现在,问题是,我可以使用任何电子邮件登录任何子域,并且将根据地址栏中的子域显示租户记录。例如我可以user1@gmail.com
在user2.example.com
登录,它会成功验证并显示user2
租户的记录。
我的问题是,在登录时如何检查当前用户的子域是否与请求的子域匹配(在地址栏上),如果匹配则继续进行身份验证并显示管理仪表板,如果不匹配(从错误的子域登录或从TLD)对用户进行身份验证,但将其重定向到相关子域的仪表板。我怎么能这样做?
更新#1:
我可以通过使用较小的设计配置来限制用户登录到其特定的子域。在devise.rb
文件中,我在身份验证密钥列表中添加了:subdomain
属性,因此它还会检查正确的子域值以及电子邮件,但是我不确定如何提供子域值登录表单正确。我可以在登录表单<%= f.hidden_field :subdomain, value: request.subdomain %>
中使用这样的隐藏字段,但由于用户可以从浏览器检查器更改它的值,因此它是可以破解的。
更新#2:
我能够应用一种傻瓜式方法来限制用户登录其特定的子域。我遵循了这个方法:https://github.com/plataformatec/devise/wiki/How-to:-Scope-login-to-subdomain
现在,我唯一的问题是用户无法从TLD(例如example.com)登录,我希望它可以,但登录后用户必须通过活动会话重定向到相关的子域。
答案 0 :(得分:0)
假设您要在User
模型上保存子域,您可以在控制器中创建验证,您可以使用以下内容:
if user.subdomain == request.subdomain
redirect_to root_url(subdomain: user.subdomain)
else
everything_is_ok
end
答案 1 :(得分:0)
如果您将子域存储在用户表中,并且通过request.subdomain
进行检查,那么有人如何加入另一个租户(公司)?它们可以包含在多个公司中。
这就是为什么,我创建了两个中间表来处理它。
因此,当user1
来到user2.example.com
时,我正在查询我的Account_permissions
,如果它有user2.example.com
的权限,我就放手。
这种方式似乎很有道理。