Entity Framework
Code First - Fließende API
Suche…
Bemerkungen
Es gibt zwei generelle Möglichkeiten, anzugeben, wie Entity Framework POCO-Klassen Datenbanktabellen, Spalten usw. zuordnet: Datenanmerkungen und Fluent-API .
Während Datenanmerkungen einfach zu lesen und zu verstehen sind, fehlen ihnen bestimmte Funktionen, beispielsweise das Festlegen des Verhaltens "Kaskadieren beim Löschen" für eine Entität. Die Fluent-API ist dagegen etwas komplexer zu bedienen, bietet jedoch weitaus mehr Funktionen.
Modelle zuordnen
Mit der EntityFramewok Fluent-API können Sie Ihre Code-First- Domänenmodelle auf eine zugrunde liegende Datenbank übertragen. Dies kann auch mit Code-First mit der vorhandenen Datenbank verwendet werden . Bei der Verwendung der Fluent-API haben Sie zwei Möglichkeiten: Sie können Ihre Modelle direkt der OnModelCreating- Methode zuordnen oder Sie können Mapper-Klassen erstellen, die von EntityTypeConfiguration erben, und diese Modelle dann in die modelBuilder- Methode OnModelCreating einfügen . Die zweite Option ist die, die ich vorziehen möchte, und werde ein Beispiel davon zeigen.
Schritt eins: Modell erstellen.
public class Employee
{
public int Id { get; set; }
public string Surname { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
public short Age { get; set; }
public decimal MonthlySalary { get; set; }
public string FullName
{
get
{
return $"{Surname} {FirstName} {LastName}";
}
}
}
Schritt 2: Erstellen Sie eine Mapper-Klasse
public class EmployeeMap
: EntityTypeConfiguration<Employee>
{
public EmployeeMap()
{
// Primary key
this.HasKey(m => m.Id);
this.Property(m => m.Id)
.HasColumnType("int")
.HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
// Properties
this.Property(m => m.Surname)
.HasMaxLength(50);
this.Property(m => m.FirstName)
.IsRequired()
.HasMaxLength(50);
this.Property(m => m.LastName)
.HasMaxLength(50);
this.Property(m => m.Age)
.HasColumnType("smallint");
this.Property(m => m.MonthlySalary)
.HasColumnType("number")
.HasPrecision(14, 5);
this.Ignore(m => m.FullName);
// Table & column mappings
this.ToTable("TABLE_NAME", "SCHEMA_NAME");
this.Property(m => m.Id).HasColumnName("ID");
this.Property(m => m.Surname).HasColumnName("SURNAME");
this.Property(m => m.FirstName).HasColumnName("FIRST_NAME");
this.Property(m => m.LastName).HasColumnName("LAST_NAME");
this.Property(m => m.Age).HasColumnName("AGE");
this.Property(m => m.MonthlySalary).HasColumnName("MONTHLY_SALARY");
}
}
Lassen Sie uns Mappings erklären:
- HasKey - Definiert den Primärschlüssel. Zusammengesetzte Primärschlüssel können ebenfalls verwendet werden. Zum Beispiel: this.HasKey (m => new {m.DepartmentId, m.PositionId}) .
- Property - ermöglicht das Konfigurieren von Modelleigenschaften.
- HasColumnType - Angabe des Spaltentyps auf Datenbankebene. Bitte beachten Sie, dass es für verschiedene Datenbanken wie Oracle und MS SQL unterschiedlich sein kann.
- HasDatabaseGeneratedOption - Gibt an, ob die Eigenschaft auf Datenbankebene berechnet wird. Numerische PKs sind standardmäßig DatabaseGeneratedOption.Identity . Sie sollten DatabaseGeneratedOption.None angeben, wenn dies nicht der Fall sein soll.
- HasMaxLength - begrenzt die Länge der Zeichenfolge.
- IsRequired - kennzeichnet die Eigenschaft als erforderlich.
- HasPrecision - lässt uns die Genauigkeit für Dezimalzahlen angeben.
- Ignorieren - Ignoriert die Eigenschaft vollständig und ordnet sie nicht der Datenbank zu. Wir haben FullName ignoriert, da wir diese Spalte nicht in unserer Tabelle haben möchten.
- ToTable - Geben Sie den Tabellennamen und den Schemanamen (optional) für das Modell an.
- HasColumnName - beziehen sich auf den Spaltennamen. Dies ist nicht erforderlich, wenn Eigenschaftsnamen und Spaltennamen identisch sind.
Schritt 3: Mapping-Klasse zu Konfigurationen hinzufügen.
Wir müssen EntityFramework anweisen, unsere Mapper-Klasse zu verwenden. Dazu müssen wir es zu modelBuilder.Configurations auf der OnModelCreating- Methode hinzufügen :
public class DbContext()
: base("Name=DbContext")
{
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Configurations.Add(new EmployeeMap());
}
}
Und das ist alles. Wir sind alle bereit zu gehen.
Primärschlüssel
Mit der Methode .HasKey () kann eine Eigenschaft explizit als Primärschlüssel der Entität konfiguriert werden.
using System.Data.Entity;
// ..
public class PersonContext : DbContext
{
// ..
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
// ..
modelBuilder.Entity<Person>().HasKey(p => p.PersonKey);
}
}
Zusammengesetzter Primärschlüssel
Mit der .HasKey () - Methode kann ein Satz von Eigenschaften explizit als zusammengesetzter Primärschlüssel der Entität konfiguriert werden.
using System.Data.Entity;
// ..
public class PersonContext : DbContext
{
// ..
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
// ..
modelBuilder.Entity<Person>().HasKey(p => new { p.FirstName, p.LastName });
}
}
Maximale Länge
Mit der .HasMaxLength () -Methode kann die maximale Zeichenanzahl für eine Eigenschaft konfiguriert werden.
using System.Data.Entity;
// ..
public class PersonContext : DbContext
{
// ..
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
// ..
modelBuilder.Entity<Person>()
.Property(t => t.Name)
.HasMaxLength(100);
}
}
Die resultierende Spalte mit der angegebenen Spaltenlänge:
Erforderliche Eigenschaften (NOT NULL)
Mithilfe der .IsRequired () - Methode können Eigenschaften als obligatorisch angegeben werden. Dies bedeutet, dass die Spalte eine NOT NULL-Einschränkung aufweist.
using System.Data.Entity;
// ..
public class PersonContext : DbContext
{
// ..
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
// ..
modelBuilder.Entity<Person>()
.Property(t => t.Name)
.IsRequired();
}
}
Die resultierende Spalte mit der NOT NULL-Einschränkung:
Explizite Fremdschlüsselbenennung
Wenn eine Navigationseigenschaft in einem Modell vorhanden ist, erstellt Entity Framework automatisch eine Fremdschlüsselspalte. Wenn ein bestimmter Fremdschlüsselname gewünscht wird, aber nicht als Eigenschaft im Modell enthalten ist, kann er explizit mithilfe der Fluent-API festgelegt werden. Durch Verwendung der Map
Methode beim Herstellen der Fremdschlüsselbeziehung kann für Fremdschlüssel ein eindeutiger Name verwendet werden.
public class Company
{
public int Id { get; set; }
}
public class Employee
{
property int Id { get; set; }
property Company Employer { get; set; }
}
public class EmployeeContext : DbContext
{
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<Employee>()
.HasRequired(x => x.Employer)
.WithRequiredDependent()
.Map(m => m.MapKey("EmployerId"));
}
}
Nach dem Festlegen der Beziehung ermöglicht die Map
Methode, dass der Name des MapKey
durch Ausführen von MapKey
explizit festgelegt wird. In diesem Beispiel lautet die EmployerId jetzt, was zu einem Spaltennamen von Employer_Id geführt hätte.