2016-04-30 76 views
0

我有3个用户角色,称之为标准,高级和管理员。每个人都可以发帖。高级版和管理员可以选择是发布私人帖子还是非私人帖子(私有:false或private:true)。标准用户将不会被选择选择他们的帖子是否是私人的;默认情况下,所有标准用户的帖子将具有私人:无状态。Ruby on Rails三元运算符显示零和虚假

总结:

  • 标准用户帖子永远是私人:无
  • 高级版/管理员用户帖子可以是私有的:真正的或私有:假

我想创建一个范围,以便在标准用户查看索引页面时,他们可以看到包含Private:nil和Private:false的帖子,而Premium和Admin用户可以查看所有帖子。我的问题是,我不能想出一个允许标准用户同时查看private:nil和private:false Posts的三元运算符。

这是我对Post模型:

scope :visible_to, -> (user) { user.admin? || user.premium? ? all : where(private: false) || where(private: nil)} 

上面的代码只显示与私人帖子:假的。 我已经尝试过各种组合:

... where(private: false || nil)} 

只显示私人:虚假职位

... where(private: nil || false)} 

只显示私人:无帖子

... where(private: nil && false)} 

只显示私人:无帖子

... where(private: false && nil)} 

个显示私人:虚假职位

等几种组合 -

我还注意到,当我切换的虚假和无秩序,它会显示不同的结果。我以为||或& &运营商是非交换。也许有一些关于范围或三元运营商,我不知道...

谢谢!

+0

你有没有考虑使用授权库,例如[权威人士](https://github.com/elabs/pundit)? – mysmallidea

回答

1

这听起来像你只是想知道如何做一个或运营商在哪里? http://guides.rubyonrails.org/active_record_querying.html

第2.3.3子集条件

... where(private: [false, nil])} 

这应该把它转换为SQL

WHERE private in (false, nil) 

这对于SQL多或声明的简写。 您还可以使用arel表来获得更高级的sql功能,而不必分解为纯sql字符串。使用与AREL实例一起结帐这篇文章关于你的情况

https://robots.thoughtbot.com/using-arel-to-compose-sql-queries

# It even handles arrays containing nil! 
where(foo: ['bar', 'baz', nil]) # => (WHERE foo IN ('bar', 'baz') OR foo IS NULL) 
+0

它像魔术一样工作! (或者它本身就是魔法......)谢谢! – Iggy

0

对我来说,范围更多是为了传达您的数据模型的一部分。根据您的设置和偏好,此逻辑应该位于模型或控制器中。这是一般性建议。

对于零值,我会设置该列的默认值,并将当前所有的零值迁移为false。这会让你的生活变得更加容易,而不是推断那些零假的或未定的。

class User 
    def can_view_private_posts 
    admin? || premium? 
    end 
end 

class Posts 
    scope :private, -> { where(private: false) } 
end 

然后让你的服务对象或控制器处理用户之间能够看到私人帖子的关系。

+0

从来没有想过这样做。谢谢! – Iggy