Existe-t-il un moyen de créer un index sur une propriété / colonne en utilisant d'abord le code, au lieu d'utiliser le nouveau IndexAttribute
?
Existe-t-il un moyen de créer un index sur une propriété / colonne en utilisant d'abord le code, au lieu d'utiliser le nouveau IndexAttribute
?
Réponses:
Eh bien 26.10.2017 Entity Framework 6.2 a été officiellement publié . Il inclut la possibilité de définir facilement des index via Fluent API. Ho il est à utiliser était déjà annoncé dans la version bêta de 6.2.
Vous pouvez maintenant utiliser la HasIndex()
méthode, suivie de IsUnique()
s'il doit s'agir d'un index unique.
Juste un petit exemple de comparaison (avant / après):
// 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();
Il est également possible de marquer l'index comme clusterisé avec .IsClustered()
.
MODIFIER N ° 1
Ajout d'un exemple d'index multi-colonnes et d'informations supplémentaires sur la façon de marquer un index comme clusterisé.
MODIFIER # 2
Comme information supplémentaire, dans EF Core 2.1, c'est exactement la même chose que dans EF 6.2 maintenant.
Voici l'artcile MS Doc comme référence.
new
. Je le réparerai.
Actuellement, il n'y a pas de "support de première classe" pour la création d'un index via l'API fluent, mais ce que vous pouvez faire, c'est via l'API fluent, vous pouvez marquer les propriétés comme ayant des attributs de l'API d'annotation. Cela vous permettra d'ajouter l' Index
attribut via une interface fluide.
Voici quelques exemples de l'élément de travail du site Problèmes pour EF.
Créez un index sur une seule colonne:
modelBuilder.Entity<MyEntity>()
.Property(e => e.MyProperty)
.HasColumnAnnotation(
IndexAnnotation.AnnotationName,
new IndexAnnotation(new IndexAttribute()));
Plusieurs index sur une seule colonne:
modelBuilder.Entity<MyEntity>()
.Property(e => e.MyProperty)
.HasColumnAnnotation(
IndexAnnotation.AnnotationName,
new IndexAnnotation(new[]
{
new IndexAttribute("Index1"),
new IndexAttribute("Index2") { IsUnique = true }
}));
Index multi-colonnes:
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)));
L'utilisation des techniques ci-dessus entraînera .CreateIndex()
la création automatique d'appels pour vous dans votre Up()
fonction lors de l'échafaudage de votre prochaine migration (ou la création automatique dans la base de données si vous n'utilisez pas de migrations).
.Primarykey(x=>x.id,clustered:false)
méthode
HasAnnotation
méthode et il n'y a AUCUNE méthode comme celle-ci. mais j'ai trouvé une méthode dont le nom HasColumnAnnotation
accepte les paramètres que vous fournissez. Avez-vous besoin de mettre à jour votre réponse ou ai-je tort?
J'ai créé quelques méthodes d'extension et les ai enveloppées dans un package nuget pour rendre cela beaucoup plus facile.
Installez le EntityFramework.IndexingExtensions
package nuget.
Ensuite, vous pouvez faire ce qui suit:
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));
}
}
Le projet et le code source sont ici . Prendre plaisir!
IndexAttribute
classe d'EF , je ne peux donc pas l'inclure dans ma bibliothèque.
Sans nom explicite:
[Index]
public int Rating { get; set; }
Avec un nom spécifique:
[Index("PostRatingIndex")]
public int Rating { get; set; }
EntityFramework
. il est inclus dans cette assemblée. juste confus au sujet de la NS.
instead of using the new IndexAttribute
avez-vous remarqué?
À partir d'EF 6.1, l'attribut [Index]
est pris en charge.
Utiliser [Index(IsUnique = true)]
pour un index unique.
Voici le lien de Microsoft
public class User
{
public int UserId { get; set; }
[Index(IsUnique = true)]
[StringLength(200)]
public string Username { get; set; }
public string DisplayName { get; set; }
}
[Index("IX_BlogIdAndRating", 2)]
public int Rating { get; set; }
[Index("IX_BlogIdAndRating", 1)]
public int BlogId { get; set; }
ici la référence de Microsoft
Entity Framework 6
Property(c => c.MyColumn)
.HasColumnAnnotation("Index", new IndexAnnotation(new IndexAttribute("IX_MyIndex")));
Et ajoutez en utilisant:
using System.Data.Entity.Infrastructure.Annotations;
using System.ComponentModel.DataAnnotations.Schema;
Vous pouvez utiliser l'annotation de données INDEX Code First Data Annotations
Si vous ne souhaitez pas utiliser d'attributs sur vos POCO, vous pouvez toujours le faire comme suit:
context.Database.ExecuteSqlCommand("CREATE INDEX IX_NAME ON ...");
Vous pouvez exécuter cette instruction dans votre DbInitializer
classe dérivée personnalisée . Cependant, je ne connais aucun moyen de l'API Fluent de le faire.
J'écris une méthode d'extension à utiliser dans EF fluent pour éviter du code supplémentaire:
public static PrimitivePropertyConfiguration HasIndexAnnotation(
this PrimitivePropertyConfiguration primitivePropertyConfiguration,
IndexAttribute indexAttribute = null
)
{
indexAttribute = indexAttribute ?? new IndexAttribute();
return primitivePropertyConfiguration
.HasColumnAnnotation(
IndexAnnotation.AnnotationName,
new IndexAnnotation(indexAttribute)
);
}
puis utilisez-le comme ceci:
Property(t => t.CardNo)
.HasIndexAnnotation();
ou comme ceci si l'index a besoin de certaines configurations:
Property(t => t.CardNo)
.HasIndexAnnotation(new IndexAttribute("IX_Account") { IsUnique = true });
Vous pouvez utiliser l'un de ces
// Index
this.HasIndex(e => e.IsActive)
.HasName("IX_IsActive");
ou
this.Property(e => e.IsActive).HasColumnAnnotation(
"Index",
new IndexAnnotation(new IndexAttribute("IX_IsActive")));