如何使用实体框架为可空列设置唯一约束?

时间:2016-01-04 11:38:19

标签: c# sql-server entity-framework

我正在使用实体框架版本6,我有一个这样的模型:

public class SizeCount
    {
        public int Count { get; set; }
        public Size Size { get; set; }
        public long? SizeId { get; set; }
        public Color Color { get; set; }
        public long? ColorId { get; set; }
        public Product Product { get; set; }
        public long ProductId { get; set; }
    }

我想阻止ColorIdSizeId都为空,我希望ProductIdColorIdSizeId是唯一的。 一些例子记录:

ProductId SizeId ColorId
1         null   1       > allow
1         null   1       > not allow
1         1      null    > not allow
2         1      null    > allow
2         null   1       > not allow

SizeIdColorId可以为null。 是否有任何属性可以帮助我在实体框架中,或者我应该手动检查它?

2 个答案:

答案 0 :(得分:0)

希望这会有所帮助,它是一个稍微修改过的版本。对于SizeCount类 -

using System.ComponentModel.DataAnnotations.Schema;

public class SizeCount
{
    public int Id { get; set; }
    public int Count { get; set; }

    [Index("IX_SizeUnique", 1, IsUnique = true)]
    public int SizeId { get; set; }
    public virtual Size Size { get; set; }

     [Index("IX_ColorUnique", 1, IsUnique = true)]
    public int ColorId { get; set; }
    public virtual Color Color { get; set; }

     [Index("IX_ProductUnique", 1, IsUnique = true)]
    public int ProductId { get; set; }
    public virtual Product Product { get; set; }

}

public class Product
    {
        public int Id { get; set; }
    }

    public class Color
    {
        public int Id { get; set; }
    }

    public class Size
    {
        public int Id { get; set; }
    }

上下文

public class TestDbContext: DbContext
    {
        public DbSet<SizeCount> SizeCounts { get; set; }
        public DbSet<Product> Products { get; set; }
        public DbSet<Size> Sizes { get; set; }
        public DbSet<Color> Colors { get; set; }

        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
           base.OnModelCreating(modelBuilder);
        }
    }

我还没有对代码进行全面测试,但是有了一些jiggery pokery你应该能够到达那里。然而,我通过迁移对其进行了测试,生成的表格如下所示:

CreateTable(
                "dbo.SizeCounts",
                c => new
                    {
                        Id = c.Int(nullable: false, identity: true),
                        Count = c.Int(nullable: false),
                        SizeId = c.Int(nullable: false),
                        ColorId = c.Int(nullable: false),
                        ProductId = c.Int(nullable: false),
                    })
                .PrimaryKey(t => t.Id)
                .ForeignKey("dbo.Colors", t => t.ColorId, cascadeDelete: true)
                .ForeignKey("dbo.Products", t => t.ProductId, cascadeDelete: true)
                .ForeignKey("dbo.Sizes", t => t.SizeId, cascadeDelete: true)
                .Index(t => t.SizeId, unique: true, name: "IX_SizeUnique")
                .Index(t => t.ColorId, unique: true, name: "IX_ColorUnique")
                .Index(t => t.ProductId, unique: true, name: "IX_ProductUnique");

答案 1 :(得分:0)

具有可空列的唯一约束

万一其他人试图对流利的API数据库环境做类似的事情,这对我有用...

modelBuilder.Entity<AppointmentRequest>()
    .HasIndex(r => new { r.CustomerId, r.StartAt })
    .HasFilter("StartAt IS NOT NULL")
    .IsUnique();

modelBuilder.Entity<AppointmentRequest>()
    .HasIndex(r => r.CustomerId)
    .HasFilter("StartAt IS NULL")
    .IsUnique();

它有效地将null视为值。