表之间有唯一约束

时间:2016-03-29 20:21:32

标签: postgresql unique-constraint

我需要验证元素的唯一性,但每个元素都可能有n个代码,我需要验证它。元素,类型,提供者,时间和代码应该是唯一的。当一个元素被创建时,如果任何代码与现有元素代码重叠,那么它就有一个代码数组,这意味着该元素是相同的。

例如

| id     | code|
|:-------| ---:| 
| 1      | 123 | 
| 2      | 456 |

元素

| id     | type          | provider_id  | time       |
|:-------|:-------------:| ------------:|-----------:|
| 1      | A             | 1            | 01/01/2016 |

codes_elements

| code_id | element_id  |
|:--------|------------:| 
| 1       | 1           | 

期望:

当我尝试插入时:

`Element = type: A, provider: 1, codes: [1], time: 01/01/2015`

我预计这会因违反禁忌而失败

当我尝试插入时:

`Element = type: B, provider: 1, codes: [1], time: 01/01/2015`

我希望这会创建一个具有代码关系的新元素

当我尝试插入时:

`Element = type: A, provider: 1, codes: [2], time: 01/01/2015`

我希望这会创建一个新元素,因为元素是相同的,但代码数组不与任何其他元素重叠

当我尝试插入时:

`Element = type: A, provider: 1, codes: [1, 2], time: 01/01/2015`

我希望在codes_elements中添加关系,因此元素1现在将有2个代码,因为代码1与其他元素重叠,这意味着这是相同的元素所以我需要只包含代码2

我看到的选项

  • 将连接表更改为元素表中的int数组.-在这种情况下,我可以搜索其他列并附加代码id也可以通过代码数组创建禁止,以防止重复。问题是当我通过代码查询元素表时很慢,例如获取代码为1的所有元素。

  • 如果没有创建新元素,请创建一个触发器并检查代码是否与其他元素重叠,只分配代码关系。

我使用Ruby on Rails但是我需要进行模型验证,因为我有多个线程同时进行插入并且可能以重复结束

我想知道更好的选择或评论,目前的想法是提高性能,防止重复等等。

1 个答案:

答案 0 :(得分:0)

为什么不在RoR中设置验证?

如果重复该元素,则无论如何都会出现错误消息。您可以在RoR中上升并处理错误,如果重复,则在元素的末尾添加类似" 1"的字符。其他选择是创建一个"整合" codes_elements表中的列,并将元素+代码值保存在其中。

编辑:

您可以确定不使用事务保存重复的行:

ActiveRecord::Base.transaction do
   elements.code do |c|
     Element.find_or_create_by(code: c, element: e)
    or
     Element.exists? code: c, element: e
   end
end