如何首先使用代码在Entity Framework 6.2中创建索引

时间:2014-03-24 18:58:29

标签: entity-framework entity-framework-6 ef-code-first

有没有办法使用代码优先在属性/列上创建索引,而不是使用新的IndexAttribute

10 个答案:

答案 0 :(得分:84)

目前没有"first class support"通过流畅的API创建索引,但您可以通过流畅的API将属性标记为具有Annotation API的属性。这将允许您通过流畅的界面添加Index属性。

以下是来自EF的问题网站的工作项的一些示例。

在单个列上创建索引:

modelBuilder.Entity<MyEntity>()
    .Property(e => e.MyProperty)
    .HasColumnAnnotation(
        IndexAnnotation.AnnotationName, 
        new IndexAnnotation(new IndexAttribute()));

单个列上的多个索引:

modelBuilder.Entity<MyEntity>()
    .Property(e => e.MyProperty)
    .HasColumnAnnotation(
        IndexAnnotation.AnnotationName, 
        new IndexAnnotation(new[]
            {
                new IndexAttribute("Index1"),
                new IndexAttribute("Index2") { IsUnique = true }
            }));

多列索引:

modelBuilder.Entity<MyEntity>()
    .Property(e => e.MyProperty1)
    .HasColumnAnnotation(
        IndexAnnotation.AnnotationName,
        new IndexAnnotation(new IndexAttribute("MyIndex", 1)));

modelBuilder.Entity<MyEntity>()
    .Property(e => e.MyProperty2)
    .HasColumnAnnotation(
        IndexAnnotation.AnnotationName, 
        new IndexAnnotation(new IndexAttribute("MyIndex", 2)));

使用上述技术将导致.CreateIndex()函数在您构建下一次迁移时自动为您创建Up()调用(如果您不使用迁移,则会在数据库中自动创建)

答案 1 :(得分:64)

26.10.2017井实体框架6.2是officially released。 它包含一个possibility,可以通过Fluent API轻松定义索引。在6.2的测试版中,使用已经是announced

现在,您可以使用HasIndex()方法,如果它应该是唯一索引,则后跟IsUnique()

只是一个小比较(之前/之后)示例:

// before 
modelBuilder.Entity<Person>()
        .Property(e => e.Name)
        .HasColumnAnnotation(
            IndexAnnotation.AnnotationName, 
            new IndexAnnotation(new IndexAttribute { IsUnique = true }));

// after
modelBuilder.Entity<Person>()
    .HasIndex(p => p.Name)
    .IsUnique();

// multi column index
modelBuilder.Entity<Person>()
    .HasIndex(p => new { p.Name, p.Firstname })
    .IsUnique();

也可以将索引标记为使用.IsClustered()进行聚类。

编辑#1

添加了多列索引的示例以及如何将索引标记为群集的其他信息。

编辑#2

作为附加信息,在EF Core 2.1中,它与现在的EF 6.2完全相同 Here是MS Doc artcile的参考。

答案 2 :(得分:36)

我已经创建了一些扩展方法并将它们包装在nuget包中以使这更容易。

安装EntityFramework.IndexingExtensions nuget包。

然后您可以执行以下操作:

public class MyDataContext : DbContext
{
  protected override void OnModelCreating(DbModelBuilder modelBuilder)
  {
    modelBuilder.Entity<Customer>()
        .HasIndex("IX_Customers_Name",          // Provide the index name.
            e => e.Property(x => x.LastName),   // Specify at least one column.
            e => e.Property(x => x.FirstName))  // Multiple columns as desired.

        .HasIndex("IX_Customers_EmailAddress",  // Supports fluent chaining for more indexes.
            IndexOptions.Unique,                // Supports flags for unique and clustered.
            e => e.Property(x => x.EmailAddress)); 
  }
}

The project and source code are here。享受!

答案 3 :(得分:19)

没有明确的名称:

[Index]
public int Rating { get; set; } 

具有特定名称:

[Index("PostRatingIndex")] 
public int Rating { get; set; }

答案 4 :(得分:14)

从EF 6.1开始,支持属性[Index]
使用[Index(IsUnique = true)]获取唯一索引。
这是here

public class User 
{ 
    public int UserId { get; set; } 

    [Index(IsUnique = true)] 
    [StringLength(200)] 
    public string Username { get; set; } 

    public string DisplayName { get; set; } 
}

答案 5 :(得分:8)

实体框架6

Property(c => c.MyColumn)
        .HasColumnAnnotation("Index", new IndexAnnotation(new IndexAttribute("IX_MyIndex")));

并添加使用:

using System.Data.Entity.Infrastructure.Annotations;
using System.ComponentModel.DataAnnotations.Schema;

答案 6 :(得分:6)

您可以使用INDEX数据注释 {{3P>

答案 7 :(得分:2)

如果您不想在POCO上使用属性,那么您可以像以下一样使用:

context.Database.ExecuteSqlCommand("CREATE INDEX IX_NAME ON ..."); 

您可以在自定义DbInitializer派生类中执行此语句。我不知道有任何Fluent API这样做的方法。

答案 8 :(得分:1)

我编写了一个扩展方法,用于流畅的EF以避免额外的代码:

public static PrimitivePropertyConfiguration HasIndexAnnotation(
    this PrimitivePropertyConfiguration primitivePropertyConfiguration, 
    IndexAttribute indexAttribute = null
    )
{
    indexAttribute = indexAttribute ?? new IndexAttribute();

    return primitivePropertyConfiguration
        .HasColumnAnnotation(
            IndexAnnotation.AnnotationName, 
            new IndexAnnotation(indexAttribute)
        );
}

然后像这样使用它:

Property(t => t.CardNo)
    .HasIndexAnnotation();

或者像这样,如果索引需要一些配置:

Property(t => t.CardNo)
    .HasIndexAnnotation(new IndexAttribute("IX_Account") { IsUnique = true });

答案 9 :(得分:1)

您可以使用其中一个

//索引

Table Storage

 this.HasIndex(e => e.IsActive)
            .HasName("IX_IsActive");