在编写评分系统时,我希望人们能够对帖子进行评分,但我只希望每个用户有一个评分。
所以在我的架构中我有类似
的东西{:db/id #db/id[:db.part/db -1]
:db/ident :rating/value
:db/valueType :db.type/ref
:db/cardinality :db.cardinality/one <<thinking this serves a purpose
:db/doc "rating applied to this particular post"
:db.install/_attribute :db.part/db}
{:db/id #db/id[:db.part/user -2]
:db/ident :rating.value/verypositive}
{:db/id #db/id[:db.part/user -3]
:db/ident :rating.value/positive}
{:db/id #db/id[:db.part/user -4]
:db/ident :rating.value/needswork}
我只希望随时可以在每封电子邮件中获得一个评级,但我有点难过。
当我向帖子提交多个评分时
>(add-rating-to-post 1759 "so@gm.co" "verypositive")
>(add-rating-to-post 1759 "so@gm.co" "needswork")
>(add-rating-to-post 1759 "so@gm.co" "positive")
>(add-rating-to-post 1759 "so@gm.co" "verypositive")
交易运作正常,但当我查询附加到特定帖子后的评级时,我会得到类似的内容
({:bid 1759,
:rating :rating.value/verypositive
:email "sova@web"}
{:bid 1759,
:rating :rating.value/positive,
:email "sova@web"}
{:bid 1759,
:rating :rating.value/needswork,
:email "sova@web"})
真的,我想要的只是最新的一个,所以用户提交的所有评分的返回列表(最后的x)都会很棒。
...但是它会填充,直到每个枚举类型中都有一个,然后忽略添加。
关于如何实现我正在努力的行为的任何建议?
非常感谢提前
答案 0 :(得分:1)
您的架构目前基本上说的是,每个rating.value只允许一个值
我建议每位用户使用“单一评分”&#39;不应该是架构约束,而是域级问题 - 实现此问题的适当方法是允许每个用户每个帖子多个评级,然后编写一个transactor函数来检查用户是否有之前评了一个帖子,并再次拒绝评级,或者撤消旧评级(取决于您想要的行为)。
如果您还没有这样做,您还希望将评级本身视为一个实体。这样您就拥有:rating/post :ref
,:rating/value :ref
和:rating/email
属性,并为每个评级创建一个新实体。
答案 1 :(得分:1)
您的架构是正确的。您使用ident进行枚举是正确的。
不是每次都创建一个新的评级实体,而是使用查询检查是否已有评分为:bid
且评分为:email
的用户。如果是这样,请使用:rating
断言处理新的:db/add
属性(不要担心撤消,它们是为:cardinality/one
属性隐式创建的)。如果没有,请创建一个像您已经在做的那样。
如果你需要原子地做,e。 G。为了避免同一用户在竞争条件下在一篇文章上创建两个评级实体,您需要通过编写和使用database function.
来在交易者中完成所有这些工作。如果您需要查看用户提供的所有评分,请使用history database等功能查询实体:rating
值的变化情况。