Einführung & Vorbereitung


In diesem Tutorial lernst du, was du mit EntityFramework in VisualStudio in der Programmiersprache C# machen kannst und was die Code-First und Database-First Workflows sind.

Um zu beginnen, öffne Visual Studio und erstelle eine neue Konsolenapplikation (Console Application). Nun wurde das Projekt erstellt und bereits die Program.cs Datei geöffnet. Wird die App mit dem grünen Startbutton (oder mit F5) gestartet, öffnet sich ein Konsolenfenster und der Code in der Main Method wird aufgerufen.

Los geht's!


Hinweis

Ein sehr detailliertes Tutorial zum EntityFramework findest du auf der Microsoft-Website.

Bei Code-First steht der Code an erster Stelle. Alles richtet sich nach dem Code. Code-First ist wohl der meist verwendete Ansatz unter MVC-Programmierern.

Bei Database-First werden die Modelle anhand der Datenbank erzeugt. Eignet sich gut, wenn man bereits eine Datenbank hat.

Code-First


Hinweis

Ein sehr detailliertes, jedoch veraltetes, Tutorial zu Code-First findest du auf der Microsoft-Website.

Um EntityFramework Core zu installieren machst du einen Rechtsklick auf dein Projekt und klickst auf "Manage NuGet Packages" ("NuGet Pakete verwalten").

Im NuGetPackagemanager suchst du dann nach "EntityFrameworkCore" und installierst dieses Package.

Du wirst zudem auch noch folgende Packages brauchen:

  1. Microsoft.EntityFrameworkCore.Tools
  2. Microsoft.EntityFrameworkCore.Design
  3. Microsoft.EntityFrameworkCore.Sqlite

Nun erstellen wir eine neue Klasse, die unser Datenmodell repräsentiert. Um eine leserliche Struktur zu haben, erstelle vorher einen Ordner "Model".

In diesem Ordner werden alle unsere Modelle sein. Erstelle gleich mal eine "Author" und eine "Book" Klasse.

Deine Struktur sollte jetzt etwa so aussehen:

Nun kannst du deine Modelle mit Properties befüllen. 

Ein Author soll einen Vornamen, Nachnamen und einen Geburtstag haben. Zudem braucht er auch eine ID, damit eindeutig klar ist, welcher Author das ist.

Ein Buch soll einen Titel und eine ID haben. Zudem soll ein Buch auch einen Author haben, aber wie macht man das am Besten? Dafür gibt es ForeignKeys ("Fremdschlüssel") bei SQL-Datenbanken. Ein ForeignKey sagt aus, dass diese Property eine Verknüpfung zu einer anderen Tabelle (Modell) ist.

Um einen ForeignKey zu erstellen fügst zu 2 Properties hinzu. 

  1. AuthorId: Sie gibt an, welcher Author das Buch geschrieben hat.
  2. Author-Objekt: Hierbei ist wichtig, dass du als Datentyp Author, also das Author-Modell nimmst und das Keyword "virtual" davor schreibst.

Deine Modelle sollten nun etwa so aussehen:

public class Author { public int Id { get; set; } public string FirstName { get; set; } public string LastName { get; set; } public DateTime Birthday { get; set; } }
text/x-csharp
public class Book { public int Id { get; set; } public string Title { get; set; } public int AuthorId { get; set; } public virtual Author Author { get; set; } }
text/x-csharp

Erstellen des Datenbank-Context

Erstelle eine neue Klasse im Ordner "Model" namens "DatabaseContext" und leite diese von "DbContext" ab. Hierzu musst du den Namespace "Microsoft.EntityFrameworkCore" importieren. (Füge dazu "using Microsoft.EntityFrameworkCore" an den Anfang der Datei)

Nun musst du für jedes Modell eine DbSet<MODEL> Property in dieser Klasse erstellen.

Als nächstes müssen wir angeben, welche Datenbank verwendet werden soll.
Ich erkläre dir hier, wie du das mit einer lokalen Datenbank-Datei umsetzen kannst.

Überschreibe die OnConfiguring-Methode und rufe die UseSqlite-Methode auf und gib als Parameter "Data Source" + den Pfad, wo du deine Datenbank-Datei lagern möchtest mit.

Die DatabaseContext Klasse sollte dann so aussehen:

public class DatabaseContext : DbContext { public DbSet<Author> Authors { get; set; } public DbSet<Book> Books { get; set; } protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder) { var folder = Environment.SpecialFolder.LocalApplicationData; var path = Environment.GetFolderPath(folder); var DbPath = $"{path}{Path.DirectorySeparatorChar}ef-tutorial.db"; optionsBuilder.UseSqlite($"Data Source={DbPath}"); } }
text/x-csharp

Datenbank erstellen

Um die Datenbank zu erstellen müssen wir zuerst eine Migration erstellen.

Dies machst du, indem du in der Package Manager Konsole (Reiter unten bzw über View -> Other Windows -> Package Manager Console) folgenden Befehl ausführst:

Add-Migration CreateDB

Dieser Befehl wird eine Migration in einem "Migrations" Ordner in deinem Projekt mit dem Namen "CreateDB" erstellen.

Hier sind alle Informationen enthalten, wie die Datenbank aktualisiert/rückgängig gemacht werden soll.

Um diese Änderungen auf die Datenbank zu übertragen führe folgenden Befehl aus:

Update-Database

Dieser Befehl erstellt auch eine neue Datenbank, falls keine Vorhanden ist. Du kannst dahinter auch einen Namen einer Migration angeben, um auf eine Spezielle Migration zu updaten/downgraden.

Hinweis

Der Name der Migration ist nur der Name, den du auch beim Erstellen eingegeben hast, ohne des Datums.

Also nicht "20210929080911_CreateDB" sondern "CreateDB".

Nun wurde deine Datenbank erstellt und Tabellen für deine Modelle generiert.

Hinweis

Wenn du Änderungen an deinen Modellen machst, zb wenn du Properties umbenennst/hinzufügst/löschst oder Modelle hinzufügst/löschst, musst du wieder eine Migration erstellen und Update-Database ausführen, so dass deine Datenbank-Struktur wieder deinen Modellen entspricht

Zugriff auf die Datenbank im Code

static void Main(string[] args) { using (var db = new DatabaseContext()) { var jkRowling = new Author { FirstName = "Joanne", LastName = "Rowling", Birthday = new DateTime(1965, 7, 31) }; db.Authors.Add(jkRowling); db.Books.Add(new Book { Title = "Harry Potter and the Philosopher's Stone", Author = jkRowling }); db.SaveChanges(); } }
text/x-csharp

Wir verwenden hier das "using"-Keyword. Es sorgt dafür, dass die Verbindung zur Datenbank automatisch geschlossen wird, wenn der Code im using fertig ist.

Innerhalb des "using"-Blocks kann man so die Datenbank verwenden. Mit db.Authors.Add kann man beispielsweise einen neuen Author hinzufügen.

In unserem derzeitigen Modell hat nur ein Buch eine Referenz zu seinem Autor. Wenn man beispielsweise sehen möchte, welche Bücher ein bestimmter Autor verfasst hat, müssten wir bei allen Büchern prüfen, ob die AuthorId die von unserem Autor ist, was nicht effizient und äußerst unpraktisch ist.

Füg also eine neue Property zum Author Modell hinzu. Diese soll virtual und vom Typ ICollection<Book> sein und den Namen "Books" tragen.

Du musst hier keine Migration machen, da diese Property "virtual" ist, also nicht in der Datenbank vorhanden ist.

Nun kannst du bei jedem Autor sehen, welche Bücher dieser hat, ohne extra alle Bücher zu überprüfen.

var jkRowling = db.Authors.Include(a => a.Books).First(author => author.FirstName == "Joanne"); foreach (var book in jkRowling.Books) { Console.WriteLine(book.Title); }
text/x-csharp

Hier verwenden wir die Include-Methode, in dieser kann man spezifizieren, dass eine bestimmte virtuelle Property mitgeladen werden soll, denn ansonsten wird Books nicht geladen und ist somit null.

Mit der First-Methode können wir nur einen bestimmten Autoren laden - hier den Ersten Autor, welcher den Vorname "Joanne" hat.

Danach iterieren wir durch alle Bücher dieses Autors und geben den Titel in der Konsole aus.

Üben auf Zeit?

Perfektioniere mit kleinen Übungen dein Know-how!

Zu den Katas

Database-First


Hinweis

Ein sehr detailliertes, jedoch veraltetes, Tutorial zu Database-First findest du auf der Microsoft-Website.

Erstelle eine neue Konsolenanwendung (in .net, nicht .net core) und installiere EF-Core, wie bereits beschrieben.

Nun musst du deine Datenbank-Verbindung erstellen. Öffne dafür den Server Explorer (Reiter links oder über View -> "Server Explorer"). 

Wenn du dich mit einer bestehenden Datenbank verbinden möchtest mache einen Rechtsklick auf "Data Connection" und wähle "Add Connection". 
Wenn du eine neue Datenbank erstellen willst wähle "Create New Database" und gib den Servernamen (zb. localhost) und einen Datenbanknamen ein.

Um Database-First aufzusetzen gib folgenden Befehl in der Kommandozeile ein

Scaffold-DbContext -Connection CONNECTION_STRING Microsoft.EntityFrameworkCore.SqlServer -o Models
text/x-csharp

Anstelle von "CONNECTION_STRING" schreibst du in Anführungszeichen deinen Connection String, also beispielsweise:

"Data Source=localhost;Initial Catalog=EF-Database-First;Integrated Security=True;Pooling=False"
text/x-csharp

Das würde bedeuten, dass du auf dem Server "localhost" die Datenbank "EF-Database-First" ansprechen willst.

Wenn du deine Modelle neu generieren willst hast du 2 Optionen:

  1. Models-Ordner löschen und den Befehl erneut ausführen
  2. Befehl ausführen, aber an den Befehl die Flag -force anhängen

Nun kannst du auf deine Datenbank wie im Beispiel bei Code-First zugreifen.

Bist du bereit, C# Aufgaben zu lösen?

Leg gleich los

Über Digital Dojo

Das Digital Dojo ist der virtuelle Übungsraum von COUNT IT.

Angehende Programmierer*innen, Code-Neulinge, Wiedereinsteiger*innen und Fortgeschrittene finden hier das nötige Rüstzeug für ihre Karriere.

Du möchtest deine Lehre bei COUNT IT starten? Dann bist du hier richtig - besiege deine Gegner im Dojo Game und sichere dir deine Lehrstelle!

Inspire your career.

Newsletter abonnieren

Der COUNT IT Newsletter liefert viermal jährlich interessante Neuigkeiten über das Unternehmen. Gleich anfordern!