2017-04-13 61 views
1

我的道歉,如果这已经问...树结构,唯一的名称/父,实体框架的交易或锁定

我有一些EF模型类是这样的:

public class Folder 
{ 
    [Key] 
    [Column("folder_id")] 
    public int FolderId { get; set; } 

    [Required] 
    [Column("organization_id")] 
    public int OrganizationId { get; set; } 
    public virtual Organization Organization { get; set; } 

    [Column("name")] 
    [MaxLength(MAX_NAME_LENGTH)] 
    public string Name { get; set; } 

    [Column("parent_folder_id")] 
    public int? ParentFolderId { get; set; } 
    [ForeignKey("ParentFolderId")] 
    public virtual Folder ParentFolder { get; set; } 

    public virtual ICollection<File> Files { get; set; } 
    public virtual ICollection<Folder> Folders { get; set; } 
} 

public class File 
{ 
    [Key] 
    [Column("file_id")] 
    public int FileId { get; set; } 

    [Column("name")] 
    [Required] 
    public string Name { get; set; } 

    [Column("folder_id")] 
    [Required] 
    public int FolderId { get; set; } 
    public virtual Folder Folder { get; set; } 

} 

我的工作对这两个表格进行了几项操作。我想运行一个阅读,做一些检查,然后回写。尽管我担心的是并发。例如:

  1. 创建文件“塞缪尔”在文件夹“贾米森”接收请求

    • 检查,看看有没有文件或文件夹名为“撒母耳记”中的“贾米森”
    • 创建文件“塞缪尔”在文件夹“贾米森”
  2. 在文件夹“贾米森”创建文件夹“塞缪尔”接收请求

    • 检查,看看有没有在“贾米森”命名为“塞缪尔”文件或文件夹
    • 创建文件夹文件夹“塞缪尔”,“贾米森”

这些检查是在应用程序完成,那么我怎样才能确保这些支票不会都成功并导致成功的创建操作?

我的第一个想法是交易,但我觉得我需要改变隔离级别或做一些悲观的锁定。或者,也许是另一种方法?你们如何在Entity Framework中解决这个问题?

回答

0

建议的EF并发处理是乐观并发。 基本上,你需要一个时间戳列添加到您的模型,并指定此列是并发处理:

[Timestamp] 
public DateTimeOffset UpdatedDate { get; set; } 

这将指示到EF检查,如果你的实体时间戳的当前值中的版本匹配数据库;如果这样做,操作将成功,否则将引发DbUpdateConcurrencyException,并且可以捕获它以向用户显示错误消息。

查看here了解更多详情。

如何使用此方法,每次添加文件或子文件夹时都会修改Parent的UpdatedDate值(这将确保只有一个操作会通过)。

+0

谢谢你的回应。不过,我觉得这可以确保我不覆盖更新的行。这里的问题是我需要确保不同的行在彼此之间保持完整性。换句话说,我需要确保当我更新一行时,没有其他具有相同ParentFolderId的行具有相同的名称,等等。编辑:虽然,也许我只是不理解你的答案可以用来解决我的问题? –

+0

想想更多,我想我可以排队一堆操作。我做我的支票,我更新ParentFolder上的日期,然后保存。我的假设是,如果存在并发异常,编辑中的任何一个都不会通过。然后,我只需要更新每个修改父级内部操作的操作的日期。以这种方式,我确保没有两个操作针对同一个父对象发生,而不会引发异常。这听起来正确吗? –

+0

附加问题,是否有更新只有时间戳字段?我使用的是按照您显示的链接中指定的byte []数组而不是DateTimeOffset。我没有修改父行的任何内容,我更像是使用同步构造。 –