{"id":55000120,"date":"2018-02-01T00:00:00","date_gmt":"2020-03-27T19:30:31","guid":{"rendered":"http:\/\/access-im-unternehmen.aix-dev.de\/aiu\/?p=120"},"modified":"-0001-11-30T00:00:00","modified_gmt":"-0001-11-30T00:00:00","slug":"EDM_Der_Code_FirstAnsatz","status":"publish","type":"post","link":"https:\/\/vbentwickler.de\/EDM_Der_Code_FirstAnsatz\/","title":{"rendered":"EDM: Der Code First-Ansatz"},"content":{"rendered":"<p><b>In den bisherigen Ausgaben haben wir immer mit dem Database First-Ansatz gearbeitet, das hei&szlig;t, dass wir unser Entity Data Model auf Basis einer bestehenden Datenbank im SQL Server oder SQLite generiert haben. Das geht auch andersherum: Sie erstellen ein paar Klassen, geben eine Verbindungszeichenfolge an und beim ersten Versuch, auf die Daten der Datenbank zuzugreifen, erstellt die Anwendung automatisch die Datenbank im angegebenen SQL Server. Wie das gelingt und wie die Klassen und die Verbindungszeichenfolge aussehen m&uuml;ssen, erfahren Sie in diesem Beitrag.<\/b><\/p>\n<p>Als Beispiel w&auml;hlen wir unsere Anwendung zum Erstellen von Anschreiben mit Word von einem WPF-Fenster aus. Dieser haben wir im ersten Schritt ja nur einfache Textfelder als Eingabem&ouml;glichkeit hinzugef&uuml;gt, in die der Benutzer Anschrift, Datum, Betreff und Inhalt des Anschreibens eintragen kann, bevor daraus ein Word-Dokument auf Basis der gew&auml;hlten Vorlage erstellt wird. Nun wollen wir dies erweitern &#8211; und zwar um die M&ouml;glichkeit, sowohl verschiedene Anschriften zu verwalten als auch um die Anschreiben abzuspeichern, um diese gegebenenfalls sp&auml;ter noch einmal aufzurufen oder auch als Vorlage f&uuml;r neue Anschreiben zu verwenden.<\/p>\n<p>Unter Access w&uuml;rden wir das Formular einfach an eine Tabelle zum Speichern der Daten des Anschreibens binden und gegebenenfalls noch eine Tabelle f&uuml;r die verschiedenen Anschriften hinzuf&uuml;gen. Allerdings wollen wir ja in diesem Magazin lernen, mit den unter WPF g&auml;ngigen Techniken umzugehen &#8211; wie etwa dem Entity Data Model als M&ouml;glichkeit, Daten zwischen Benutzeroberfl&auml;che und Datenbank hin- und herzuschieben.<\/p>\n<p>In den vorherigen Ausgaben haben wir meist eine vorhandene Datenbank genutzt und mit dem daf&uuml;r vorgesehenen Assistenten ein Entity Data Model erstellen lassen. Dieses enth&auml;lt die Klassen und Auflistungen, mit denen wir dann von der Benutzeroberfl&auml;che beziehungsweise von der Anwendungslogik aus auf die Daten der Datenbank zugreifen konnten. In diesem Beispiel wollen wir es einmal andersherum versuchen: Wir wollen zuerst die Klassen f&uuml;r die beiden Entit&auml;ten programmieren, also f&uuml;r die Anschreiben und die Adressen, und daraus dann ein Datenmodell generieren. Auch dieser Fall ist vom Entity Framework als M&ouml;glichkeit vorgesehen und nennt sich Code First. Wir erstellen also erst den Code und lassen daraus dann die Datenbank erzeugen. Das wir f&uuml;r das erste Beispiel eine relativ einfache Konstellation mit nur zwei Entit&auml;ten nutzen (okay, mit Anreden f&uuml;r die Adressen vielleicht drei), wird die Komplexit&auml;t ein wenig vermindern.<\/p>\n<h2>Vorbereitungen<\/h2>\n<p>Als Erstes erstellen wir ein neues, leeres Projekt namens <b>CodeFirst<\/b> &#8211; und zwar mit der Vorlage <b>Visual Basic|Windows|WPF-Anwendung <\/b>oder <b>Visual C#|Windows|WPF-Anwendung<\/b>. Diesem Projekt f&uuml;gen Sie nach Markierung des Eintrags mit dem Projektnamen <b>CodeFirst <\/b>im Projektmappen-Explorer ein Element des Typs <b>ADO.NET Entity Data Model <\/b>hinzu. Den dazu n&ouml;tigen Dialog <b>Neues Element hinzuf&uuml;gen&#8230; <\/b>&ouml;ffnen Sie mit der Tastenkombination <b>Strg + Umschalt + A<\/b>. Hier w&auml;hlen Sie den passenden Elementtyp aus und legen als Name den Wert <b>Wordgenerator <\/b>fest (siehe Bild 1).<\/p>\n<p class=\"image\"><img decoding=\"async\" src=\"..\/fileadmin\/_temp_\/2018_01\/pic_120_001.png\" alt=\"Entity Data Model zum Projekt hinzuf&uuml;gen\" width=\"649,559\" height=\"340,9415\" \/><\/p>\n<p><b><span style=\"color:darkgrey;\">Bild 1: Entity Data Model zum Projekt hinzuf&uuml;gen<\/span><\/b><\/p>\n<p>Im folgenden <b>Assistent f&uuml;r Entity Data Model <\/b>w&auml;hlen Sie den Eintrag <b>Leeres Code First-Modell <\/b>aus (siehe Bild 2). Im Gegensatz zu der Variante, die wir sonst gew&auml;hlt haben, n&auml;mlich <b>EF Designer aus Datenbank<\/b>, ist dies gleichzeitig schon der letzte Schritt in diesem Assistenten, den wir mit einem Klick auf die Schaltfl&auml;che <b>Fertigstellen <\/b>beenden.<\/p>\n<p class=\"image\"><img decoding=\"async\" src=\"..\/fileadmin\/_temp_\/2018_01\/pic_120_002.png\" alt=\"Modelltyp Leeres Code First-Modell ausw&auml;hlen\" width=\"549,6265\" height=\"497,9601\" \/><\/p>\n<p><b><span style=\"color:darkgrey;\">Bild 2: Modelltyp Leeres Code First-Modell ausw&auml;hlen<\/span><\/b><\/p>\n<p>Diesmal geschieht auch gar nicht viel in unserem Projekt. Die augenscheinlichste &Auml;nderung ist, dass der Assistent ein Klassenmodul namens <b>Wordgenerator.vb <\/b>(beziehungsweise <b>Wordgenerator.cs <\/b>unter C#) angelegt hat (siehe Bild 3). Die Klasse Wordgenerator erbt von der Klasse <b>DbContext<\/b>.<\/p>\n<p class=\"image\"><img decoding=\"async\" src=\"..\/fileadmin\/_temp_\/2018_01\/pic_120_003.png\" alt=\"Durch den Assistenten angelegte Klasse\" width=\"700\" height=\"359,4778\" \/><\/p>\n<p><b><span style=\"color:darkgrey;\">Bild 3: Durch den Assistenten angelegte Klasse<\/span><\/b><\/p>\n<h2>Modell programmieren<\/h2>\n<p>Nun programmieren wir die Klassen f&uuml;r unser Modell, auf dessen Basis wir sp&auml;ter eine Datenbank erstellen lassen wollen. <\/p>\n<p>Dazu legen wir drei neue Klassen an &#8211; jeweils wieder &uuml;ber die Tastenkombination <b>Strg + Umschalt + A <\/b>und den dadurch aufgerufenen Dialog <b>Neues Element einf&uuml;gen&#8230;<\/b>. Hier w&auml;hlen wir nun jeweils den Eintrag Klasse aus und legen die Namen <b>Anschreiben.vb<\/b>, <b>Adresse.vb <\/b>und <b>Anrede.vb <\/b>fest. Die Klasse <b>Anrede.vb <\/b>sieht wie folgt aus:<\/p>\n<pre><span style=\"color:blue;\">Public Class<\/span> Anrede\r\n     <span style=\"color:blue;\">Public <\/span>Property ID<span style=\"color:blue;\"> As Integer<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Anrede<span style=\"color:blue;\"> As String<\/span>\r\n<span style=\"color:blue;\">End Class<\/span><\/pre>\n<p>F&uuml;r die Klasse Adresse legen wir den folgenden Code fest, wobei wir als Typ der Eigenschaft Anrede auch gleich die frisch angelegte Klasse gleichen Namens verwenden:<\/p>\n<pre><span style=\"color:blue;\">Public Class<\/span> Adresse\r\n     <span style=\"color:blue;\">Public <\/span>Property ID<span style=\"color:blue;\"> As Integer<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Firma<span style=\"color:blue;\"> As String<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Anrede<span style=\"color:blue;\"> As <\/span>Anrede\r\n     <span style=\"color:blue;\">Public <\/span>Property Vorname<span style=\"color:blue;\"> As String<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Nachname<span style=\"color:blue;\"> As String<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Strasse<span style=\"color:blue;\"> As String<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property PLZ<span style=\"color:blue;\"> As String<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Ort<span style=\"color:blue;\"> As String<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Land<span style=\"color:blue;\"> As String<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property EMail<span style=\"color:blue;\"> As String<\/span>\r\n<span style=\"color:blue;\">End Class<\/span><\/pre>\n<p>Nachdem wir die Klasse <b>Adresse <\/b>erzeugt haben, die wir auch als Collection der Klasse <b>Anrede <\/b>zuordnen wollen &#8211; jede Anrede geh&ouml;rt ja zu keiner, einer oder mehreren Adressen -, k&ouml;nnen wir die Klasse <b>Anrede <\/b>noch um die Auflistung <b>Adressen <\/b>mit dem Typ <b>Adresse <\/b>erweitern:<\/p>\n<pre><span style=\"color:blue;\">Public Class<\/span> Anrede\r\n     ...\r\n     <span style=\"color:blue;\">Public <\/span>Property Adressen<span style=\"color:blue;\"> As <\/span>ICollection(Of Adresse)\r\n<span style=\"color:blue;\">End Class<\/span><\/pre>\n<p>Die Klasse <b>Anschreiben <\/b>erh&auml;lt schlie&szlig;lich die folgenden Eigenschaften:<\/p>\n<pre><span style=\"color:blue;\">Public Class<\/span> Anschreiben\r\n     <span style=\"color:blue;\">Public <\/span>Property ID<span style=\"color:blue;\"> As Integer<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Adresse<span style=\"color:blue;\"> As <\/span>Adresse\r\n     <span style=\"color:blue;\">Public <\/span>Property Datum<span style=\"color:blue;\"> As Date<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Betreff<span style=\"color:blue;\"> As String<\/span>\r\n     <span style=\"color:blue;\">Public <\/span>Property Inhalt<span style=\"color:blue;\"> As String<\/span>\r\n<span style=\"color:blue;\">End Class<\/span><\/pre>\n<p>Auch hier k&ouml;nnen wir nun die Klasse <b>Adresse <\/b>um die Auflistung der Anschreiben erg&auml;nzen:<\/p>\n<pre><span style=\"color:blue;\">Public Class<\/span> Adresse\r\n     ...\r\n     <span style=\"color:blue;\">Public <\/span>Property Anschreiben<span style=\"color:blue;\"> As <\/span>ICollection(Of Anschreiben)\r\n<span style=\"color:blue;\">End Class<\/span><\/pre>\n<p>Mit der Angabe der beiden <b>ICollections <\/b>in den Klassen <b>Anschreiben <\/b>und <b>Adresse <\/b>legen wir praktisch die 1:n-Beziehung zwischen den Klassen fest. Damit kann dann eine Adresse mehreren Anschreiben zugeordnet werden und eine Anrede mehreren Adressen.<\/p>\n<h2>Auflistungen in der DBContext-Klasse definieren<\/h2>\n<div class=\"rcp_restricted\"><p><span style=\"color: #ff0000\">M&ouml;chten Sie weiterlesen? Dann l&ouml;sen Sie Ihr Ticket!<\/span><br \/>\n<span style=\"color: #ff0000\">Hier geht es zur Bestellung des Jahresabonnements des Magazins <strong>Visual Basic Entwickler<\/strong>:<\/span><br \/>\n<span style=\"color: #ff0000\"><a style=\"color: #ff0000\" href=\"https:\/\/shop.minhorst.com\/magazine\/363\/visual-basic-entwickler-jahresabonnement?c=77\">Zur Bestellung ...<\/a><\/span><br \/>\n<span style=\"color: #ff0000\">Danach greifen Sie sofort auf <strong>alle rund 200 Artikel<\/strong> unseres Angebots zu - auch auf diesen hier!<\/span><br \/>\n<span style=\"color: #000000\">Oder haben Sie bereits Zugangsdaten? Dann loggen Sie sich gleich hier ein:<\/span><\/p>\n<\/div>\n\n\t\n\t<form id=\"rcp_login_form\"  class=\"rcp_form\" method=\"POST\" action=\"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts\/55000120\/\">\n\n\t\t\n\t\t<fieldset class=\"rcp_login_data\">\n\t\t\t<p>\n\t\t\t\t<label for=\"rcp_user_login\">Username or Email<\/label>\n\t\t\t\t<input name=\"rcp_user_login\" id=\"rcp_user_login\" class=\"required\" type=\"text\"\/>\n\t\t\t<\/p>\n\t\t\t<p>\n\t\t\t\t<label for=\"rcp_user_pass\">Password<\/label>\n\t\t\t\t<input name=\"rcp_user_pass\" id=\"rcp_user_pass\" class=\"required\" type=\"password\"\/>\n\t\t\t<\/p>\n\t\t\t\t\t\t<p>\n\t\t\t\t<input type=\"checkbox\" name=\"rcp_user_remember\" id=\"rcp_user_remember\" value=\"1\"\/>\n\t\t\t\t<label for=\"rcp_user_remember\">Remember me<\/label>\n\t\t\t<\/p>\n\t\t\t<p class=\"rcp_lost_password\"><a href=\"\/data\/wp\/v2\/posts\/55000120?rcp_action=lostpassword\"><\/a><\/p>\n\t\t\t<p>\n\t\t\t\t<input type=\"hidden\" name=\"rcp_action\" value=\"login\"\/>\n\t\t\t\t\t\t\t\t\t<input type=\"hidden\" name=\"rcp_redirect\" value=\"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts\/55000120\/\"\/>\n\t\t\t\t\t\t\t\t<input type=\"hidden\" name=\"rcp_login_nonce\" value=\"b0e70d76fb\"\/>\n\t\t\t\t<input id=\"rcp_login_submit\" class=\"rcp-button\" type=\"submit\" value=\"Login\"\/>\n\t\t\t<\/p>\n\t\t\t\t\t<\/fieldset>\n\n\t\t\n\t<\/form>\n<\/p>\n","protected":false},"excerpt":{"rendered":"<p>In den bisherigen Ausgaben haben wir immer mit dem Database First-Ansatz gearbeitet, das hei&szlig;t, dass wir unser Entity Data Model auf Basis einer bestehenden Datenbank im SQL Server oder SQLite generiert haben. Das geht auch andersherum: Sie erstellen ein paar Klassen, geben eine Verbindungszeichenfolge an und beim ersten Versuch, auf die Daten der Datenbank zuzugreifen, erstellt die Anwendung automatisch die Datenbank im angegebenen SQL Server. Wie das gelingt und wie die Klassen und die Verbindungszeichenfolge aussehen m&uuml;ssen, erfahren Sie in diesem Beitrag.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"om_disable_all_campaigns":false,"_monsterinsights_skip_tracking":false,"_monsterinsights_sitenote_active":false,"_monsterinsights_sitenote_note":"","_monsterinsights_sitenote_category":0,"_uf_show_specific_survey":0,"_uf_disable_surveys":false,"footnotes":""},"categories":[66012018,662018,44000008,44000021,44000004,44000025],"tags":[],"yst_prominent_words":[],"class_list":["post-55000120","post","type-post","status-publish","format-standard","hentry","category-66012018","category-662018","category-Datenzugriffstechnik","category-Entity_Framework","category-Loesungen","category-VBAProgrammierung"],"aioseo_notices":[],"_links":{"self":[{"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts\/55000120","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/comments?post=55000120"}],"version-history":[{"count":0,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts\/55000120\/revisions"}],"wp:attachment":[{"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/media?parent=55000120"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/categories?post=55000120"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/tags?post=55000120"},{"taxonomy":"yst_prominent_words","embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/yst_prominent_words?post=55000120"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}