Wenn Sie ein Abonnement des Magazins 'DATENBANKENTWICKLER' besitzen, können Sie sich anmelden und den kompletten Artikel lesen.
Anderenfalls können Sie das Abonnement hier im Shop erwerben.
EDM: Backend ändern
Unsere aktuellen Beispieldatenbanken haben ein WPF/C#-Frontend, ein SQLite-Backend und das Entity Data Model als Zwischenschicht. Was geschieht nun, wenn wir einmal die Datenbank ändern wollen – etwa, weil wir neue Tabellen oder neue Felder in bestehenden Tabellen benötigen? Wie ist die genaue Vorgehensweise, die auch berücksichtigt, dass der Benutzer eine neue Version installieren möchte, ohne die bereits im vorhandenen Backend gespeicherten Daten zu verlieren? Wie dies gelingt, zeigt der vorliegende Artikel.
Bei der Entwicklung würden wir so vorgehen, dass wir das Datenmodell der SQLite-Datenbank ändern, indem wir die gewünschten Tabellen oder Felder hinzufügen. Dann wechseln wir zu Visual Studio und aktualisieren das Entity Data Model, gegebenenfalls müssen wir noch die Benutzeroberfläche beziehungsweise die Code behind-Klassen anpassen.
Aber was, wenn die Anwendung bereits beim Kunden im Produktiveinsatz ist? Dann würden wir die Entwicklung natürlich genau so betreiben, wie wir es oben beschrieben haben. Allerdings können wir natürlich nicht so einfach die neue Version des Datenbankbackends beim Kunden installieren, denn dieser hat ja bereits ein Backend mit gegebenenfalls neuen Daten, die wir dann überschreiben würden. Also was tun? Die neue Anwendung exklusive Backend können wir ja bei Kunden über die alte Version installieren, aber für das Backend müssen wir uns etwas einfallen lassen. Denn das neue Frontend wird auch spätestens beim Versuch, auf eines der neuen Felder per Entity Framework zuzugreifen, Probleme verursachen.
Allerdings gibt es ja die Möglichkeit, Datenmodelle per Code zu ändern. Wir können zum Beispiel neue Tabellen anlegen oder bestehende Tabellen entfernen, Felder zu Tabellen hinzufügen oder entfernen oder auch Einschränkungen ändern. Allerdings will dies gut geplant sein, denn vielleicht wollen wir das Datenmodell des Backends nicht nur einmal ändern, sondern im Laufe der Zeit je nach den geänderten Anforderungen auch öfter.
Versionsstand prüfen
In diesem Fall müssen wir in irgendeiner Form einen Versionsstand des Backends speichern, damit wir wissen, welche Aktualisierungen in Abhängigkeit vom Versionsstand durchzuführen sind. Da wir mit einem Datenbankbackend arbeiten, bietet sich dazu natürlich eine Tabelle an, die wir etwa Versions nennen. Die Tabelle braucht lediglich ein Feld namens Version, in das wir dann den Versionsstand der Tabelle eintragen.
Wir würden dann eine neue Version des Frontends installieren, diese starten und nach dem Start soll das Frontend dann prüfen, ob das Backend die dem Frontend entsprechende Version aufweist. Dazu soll das Frontend dann die Tabelle Versions öffnen und den Wert des Feldes Version prüfen. Wenn die Version kleiner als die geforderte Version ist, soll das Frontend die benötigten Änderungen am Backend durchführen und schließlich den Versionsstand in der Tabelle Versions aktualisieren.
Natürlich müssen wir auch einen umgekehrten Mechanismus vorsehen, der reagiert, wenn der Versionsstand des Backends aktueller ist als der des Frontends. Das kann etwa der Fall sein, wenn der Kunde das Frontend an mehr als einem Arbeitsplatz einsetzt und dieses nur an einem Arbeitsplatz auf den aktuellen Versionsstand bringt. Sollte dann ein Benutzer auf einem anderen Arbeitsplatz ein veraltetes Frontend starten, sollte dieses mit einer entsprechenden Meldung darauf hinweisen, dass das Frontend aktualisiert werden soll.
Dazu gibt es natürlich noch weiterführende Techniken, bei denen das Frontend beim Start automatisch über das Internet prüft, ob es eine aktuellere Version des Frontends gibt, doch das soll nicht das Thema dieses Artikels sein.
Versionstabelle hinzufügen
Wir wollen die Schritte dieses Artikels anhand unserer Beispieldatenbank Bestellverwaltung.db auf Basis von SQLite erläutern. Diese enthält im aktuellen Zustand noch gar keine Tabelle namens Versions, sodass der erste Schritt sein wird, diese Tabelle dem Entwicklungsbackend hinzuzufügen und das Frontend um eine Funktion zu ergänzen, die beim Starten des Frontends prüft, ob die Tabelle Versions im Backend vorhanden ist oder nicht. Falls nicht, soll diese einfach ergänzt werden. Der Einfachheit halber finden Sie die Lösung in einer stark reduzierten Version der in den übrigen Artikeln verwendeten Anwendung, die nur das Fenster MainWindow enthält.
Ort von Backendänderungen bei der Entwicklung
Wenn Sie, wie wir in diesem Artikel, mit einem Backend auf Dateibasis arbeiten (also mit SQLite und nicht etwa mit SQL Server), müssen Sie sich entscheiden, an welcher Stelle Sie die Änderungen durchführen. Wir führen eine Version des Backends direkt im Projektordner, also im gleichen Verzeichnis wie etwa die .xaml- und .cs-Dateien (später werden wir diese gegebenenfalls auch einmal in eigenen Ordnern strukturieren, aber aktuell reicht ein Verzeichnis dazu aus). Dieses fügen wir auch zum Projektmappen-Explorer hinzu. Dann stellen wir die Eigenschaft In Ausgabeverzeichnis kopieren für diese Eintrag auf Kopieren, wenn neuer ein (siehe Bild 1). Die Datenbankdatei wird dann nur erneut in das Ausgabeverzeichnis kopiert, wenn die Ausgangsdatei aktualisiert wurde und somit ein neueres Änderungsdatum als die im Ausgabeverzeichnis enthaltene Datei enthält.
Bild 1: Eigenschaften der DatenbankdateiHinzufügen der Tabelle Versions
Nun starten wir SQLite Studio, um die Tabelle Versions zur Datenbank hinzuzufügen. Hier wählen Sie den Menübefehl Datenbank|Datenbank hinzufügen und wählen im folgenden Dateiauswahl-Dialog die Datei Bestellverwaltung.db aus unserem Projektverzeichnis aus. Klicken Sie dann doppelt auf den Eintrag für diese Datenbank, sodass die enthaltenen Tabellen angezeigt werden. Klicken Sie mit der rechten Maustaste auf den Eintrag Tabellen und wählen Sie den Kontextmenü-Eintrag Tabelle erstellen aus. Geben Sie oben als Tabellenname Versions an und fügen Sie mit der Schaltfläche Add Column eine neue Spalte zur Tabelle hinzu. Dieses soll das Primärschlüsselfeld mit dem Spaltennamen VersionID und dem Datentyp INTEGER sowie automatischem Hinzufügen der Feldwerte sein. Für das zweite Feld legen Sie als Spaltenname Version fest und geben als Datentyp String mit der Länge 50 an (sicher ist sicher). Danach sieht die Definition der Tabelle wie in Bild 2 aus und Sie können mit einem Klick auf die Schaltfläche Commit structure changes die Änderungen in die Datei schreiben.
Bild 2: Anlegen der Tabelle VersionsEs erscheint dann der Dialog aus Bild 3 mit dem SQL-Code der auszuführenden Abfrage. Das ist recht praktisch, denn so können Sie den Code direkt kopieren und diesen später hervorholen, wenn Sie das Anlegen dieser Tabelle per C# programmieren wollen.
Bild 3: SQL-Code zum Erstellen der neuen TabelleDas waren schon alle Schritte, die wir von hier aus erledigen wollen.
Geändertes Datenmodell in Entity Data Model übernehmen
Danach müssen wir das Entity Data Model an das neue Datenmodell anpassen. Dazu öffnen Sie dieses per Doppelklick auf de Eintrag Bestellverwaltung.edmx im Projektmappen-Explorer. Dies öffnet die Übersicht, die per Klick mit der rechten Maustaste den Kontextmenü-Befehl Modell aus der Datenbank aktualisieren... offenbart (siehe Bild 4). Es erscheint dann nach einigen Sekunden der Update-Assistent und bittet um die Auswahl der Datenverbindung (eventuell erkennt er auch die korrekte Verbindung und zeigt direkt den folgenden Dialog an). Die vorhandene Einstellung können Sie in der Regel beibehalten und mit einem Klick auf die Schaltfläche Weiter den nächsten Schritt aufrufen.
Bild 4: Aktualisieren des Modells aus der DatenbankNun kann es zu folgendem kommen: Es erscheint der Schritt mit der Überschrift Wählen Sie Ihre Datenbankobjekte und Einstellungen., aber es lässt sich keine der Optionen Tabellen, Sichten oder Gespeicherte Prozeduren und Funktionen aktivieren (siehe Bild 5). Der Grund für diesen Zustand ist vermutlich, dass es tatsächlich keine zu aktualisierenden Objekte gibt. Das kann zwei Ursachen haben:
Bild 5: Es stehen keine Objekte zur Aktualisierung zur Verfügung.- Sie haben die Änderungen nicht in die Datenbank übernommen. Prüfen Sie, ob zum Beispiel die neue Tabelle Versions in der Liste der Tabellen in SQLite Studio angezeigt wird.
- Sie haben die Änderungen an einer anderen Datenbank vorgenommen, als an der, die Sie nun zum Übertragen der Änderungen in das Entity Data Model verwenden wollen.
Wenn Sie den ersten Fall ausschließen können, sollten Sie im Update-Assistenten für das Entity Data Model nochmal zum ersten Schritt zurückkehren. Hier stellen Sie dann unter Umständen fest, dass Sie mehrere Verbindungen über das Kombinationsfeld auswählen können und vielleicht die falsche Datenbank ausgewählt haben. Hier sollten Sie dann sichergehen, dass Sie die richtige gewählt haben – beispielsweise, indem Sie unten unter Verbindungszeichenfolge prüfen, ob dort auch tatsächlich die Datenbankdatei im richtigen Verzeichnis angegeben ist (siehe Bild 6).
Bild 6: Prüfen der korrekten Datenverbindung anhand der Verbindungszeichenfolge
Achtung: Wenn Sie mit den Beispieldateien aus dem Download arbeiten, müssen Sie auf jeden Fall eine neue Verbindung anlegen und die Quelldatenbank neu auswählen – außer, Sie verwenden zufällig genau die gleiche Verzeichnisstruktur wie wir.
Wenn Sie danach einen Schritt weitergehen, erscheint die Tabelle Versions auch in der Liste der zur Aktualisierung bereitstehenden Tabellen und Sie können diese nun auswählen (siehe Bild 7). Klicken Sie dann auf Fertigstellen, erscheint schon kurz danach die Tabelle Versions im Entity Data Model.
Bild 7: Einbinden der Tabelle Versions in das Entity Data ModelSie können somit auch über das Entity Data Model auf die Tabelle und ihre Inhalte zugreifen.
Code zum Prüfen der Version des Backends
Nun wollen wir Code zur Anwendung hinzufügen, der beim Öffnen prüft, ob die richtige Version des Backends vorliegt. Dabei unterscheiden wir zwei Fälle:
- Das Backend enthält noch gar keine Tabelle Versions. Dann muss diese zunächst angelegt werden. Danach sollen alle Updates des Backends bis zum aktuellen Versionsstand ausgeführt werden.
- Die Tabelle Versions liegt bereits vor. Dann prüfen wir den Versionsstand des Backends und führen alle Updates des Backends bis zum aktuellen Versionsstand aus.
Ort des Update-Codes
Dies war die Leseprobe dieses Artikels.
Melden Sie sich an, um auf den vollständigen Artikel zuzugreifen.