Datenbank Autonomie

Oder warum sollten sich mehrere Anwendungen nicht dieselbe Datenbank teilen? http://www.flickr.com/photos/breville/10731809645/sizes/l/ Viele Köche verderben den Brei: Diseconomy of Scale Eine gemeinsame Datenbank (geteilt zwischen Anwendungen und/oder Teams) sorgt für unterschiedliche Interessen und erhöhten Absprachebedarf, damit es nicht zu einer Art Wildwuchs kommt. Wenn keine klaren Schnittstellen definiert sind sinkt die Produktivität aufgrund des erhöhten Kommunikationsaufwandes. Das gilt in Firmen unter Abteilungen und Mitarbeitern, genauso wie für Software-Projekt-Teams als auch für Software selbst. Bei wenigen Parteien ist die Komplexität oft noch nicht zu sehen. Desto mehr Parteien es werden, desto komplexer wird es jedoch. Wikipedia: http://en.wikipedia.org/wiki/Diseconomy_of_scale “Diseconomies of scale are the forces that cause larger firms and governments to produce goods and services at increased per-unit costs” Zu Deutsch: “desto mehr Parteien an einer Sache beteiligt sind, desto höher wird der Kommunikationsaufwand.“ Dazu gibt es auch eine mathematische Formel: Workers Communication Channels 1 0 2 1 3 3 4 6 5 10 n Zur Thematik in der Software-Entwicklung findet man folgende Definition: http://www.softwaremetrics.com/se.htm “In all software projects there are some basic principles which cause diseconomies of scale. That is: Communication becomes difficult as project becomes larger. Multiple logical paths grow in a nonlinear manner as size increases. Interrelationships of functions grow geometrically as project becomes large. Zu Deutsch: “In allen Software-Projekten gibt es einfache Gründe, die zur negativen Produktivität führen. Diese sind: Kommunikation wird schwieriger, wenn das Projekt größer wird. Wenn ein Projekt größer wird, wachsen die Interessen mit un-linearem Faktor auseinander. Abhängigkeiten von Funktionalitäten steigen im Quadrat wenn das Projekt größer wird. Dazu findet man beim „Massachusetts Institute of Technology“ (MIT) die folgende These um die Komplexität einzugrenzen: http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.115.350&rep=rep1&type=pdf „… a manager could choose to divide the project into several smaller projects in order to increase the productivity.“ Zu Deutsch: “Ein Manager kann sich dazu entscheiden das Projekt in kleinere (unabhängige) Projekte zu teilen, um die Produktivität zu erhöhen.” IBM schreibt dazu in einem Whitepaper zu Software Economies wie die Ressourcen in einem Software-Projekt zu berechnen sindftp://public.dhe.ibm.com/common/ssi/ecm/en/raw14148usen/RAW14148USEN.PDF: Resources = (Complexity) * (Process) * (Teamwork) * (Tools) Wobei je 10% weniger beim Vorgänger mehr als 10% mehr Produktivität beim Nachfolger erzeugen. In diesem Dokument wird auch sehr gut Argumentiert, warum ein Wasserfall-Model (Erst alles Planen und dann erst Bauen, gegenüber einem agilen Ansatz(Kleine Iterationen von Planung und Ausführung zur besseren Kurskorrektur getrieben durch sich mit der Zeit ändernde Anforderungen) im Nachteil ist. Abstraktion und Muster/Patterns Die Abstraktion dient in der Software-Entwicklung zur Steigerung der Robustheit gegenüber Änderungen. Seit (spätestens) 21.10.1994, dem Erscheinungsdatum von „Design-Patterns“ der „Gang of four“ (http://en.wikipedia.org/wiki/Design_Patterns), sollte bekannt sein, dass Abstraktion und lose Koppelung höchste Güter er Software-Entwicklung sind. Als Beispiel dafür der Mediator (http://www.cs.ucsb.edu/~mikec/cs48/misc/Design_Class_Diagrams.htm): Eine Komponente, die zwischen den Anderen steht, um die Komplexität und das Wissen übereinander zu verringern. Schon in einer einzelnen Anwendung gehört es zu den „best practices“ den Datenzugriff zu abstrahieren(http://martinfowler.com/eaaCatalog/repository.html) um Änderungen an einer zentralen Stelle zu verwalten und nicht über die gesamte Anwendung ausufern zu lassen. Direct Data Access vs. Services Der direkte Zugriff auf eine Datenbank zieht bei einer Änderung des Schemas, also der Datenbank-Strukturen, z.B. hervorgerufen, durch Perfomance-Anforderungen, Geschäftsprozessänderungen oder der Migration auf eine neue oder andere Datenbankversion, Entwicklungsaufwände in JEDER direkt darauf zugreifenden Anwendung nach sich. Dies kann durch Abstraktion des Datenzugriffs undAutonomie der der Datenbank verhindert werden. Wikipedia schreibt dazu (http://en.wikipedia.org/wiki/Database_abstraction_layer): „Database abstraction layers reduce the amount of work by providing a consistent API to the developer and hide the database specifics behind this interface as much as possible“ Zu Deutsch: “… Abstraktion reduziert die Aufwände durch einen klar definierte Schnittstelle für den Entwickler und versteckt/schützt die Implementierungsdetails so gut wie möglich” In einem der bekanntesten Portalen der Software-Entwicklung, in dem alle Programmiersprachen diskutiert, und die Antworten allen bewertet werden können findet man den folgenden Eintrag:http://stackoverflow.com/questions/1530551/direct-acces-database-vs-web-service “Direct database access couples you tightly to the schema. Any changes on either end affects the other.” Zu Deutsch: “Jede Änderung auf einer Seite hat Auswirkungen auf alle anderen” Und… „ I would try to go the direct database access route, unless several applications need to share the data...“ Zu Deutsch: “Ich würde den direkten Datenbankzugriff wählen, es sei denn, mehrere Anwendungen sollen sich die Daten teilen…“ Zu „Entwicklungen“, die über die Zeit eine Datenbank mach und die Vorteile eines zentralisierten Datenzugriffs (http://www.agiledata.org/essays/implementationStrategies.html): “…a single encapsulation layer … reduce the effort it takes to evolve your database schemas” Zu Deutsch: “… ein Einzige Datenzugriffsschicht reduziert die Aufwände die entstehen, wenn eine Datenbank sich weiterentwickelt/wächst” Globaler Datenzugriff: Die neuen globalen Variablen Der Einsatz von globalen Variablen ist seit Jahren in der Software-Entwicklung verpönt (http://c2.com/cgi/wiki?GlobalVariablesAreBad). Das liegt daran, dass Code, der mit globalen Variablen arbeitet folgende Eigenschaften mit sich bringt: Er verlässt sich darauf, dass eine Variable einen bestimmten Wert enthält. Er lässt sich also nur durch aufsetzen diese Vorbedingungen (Infrastruktur) testen. ABER: Jeder kann den Wert ändern, da ja keiner die Zuständigkeit besitzt (z.B. eine Funktionalität/Service) zu kontrollieren, ob dies zum aktuellen Zeitpunkt auch korrekt ist. Dadurch: Entsteht ein System von Unvorhersehbarkeiten Eine Datenbank mit „Zugriff für ALLE“ verhält sich genauso. Wie eine globale Variable oder eine Gruppe Kinder zu einem Süßigkeiten-Glas. Das gilt übrigens technologieübergreifend - auch in JAVA und in allen anderen Programmiersprachen (http://stackoverflow.com/questions/2867862/service-bus-vs-direct-database-access). Es handelt sich dabei um ein Architektur- bzw. Vorgehens-Problem. Daten als Dienstleistung Wenn man sich fragt, was eine Anwendung will, würde man wohl eher sagen, dass sie mit den Daten arbeiten will (z.B. einen Geschäftsprozess abbilden), als, dass sie auf die Datenbank zugreifen will. Das würde sonst schließlich bedeuten, dass die Software zu Selbstzweck oder der Technologie willens existiert. Es ist wie beim Verschicken eines Briefes. Man muss nicht wissen, ob der Briefträger mit dem Fahrrad kommt, zu Fuß unterwegs ist oder mit dem Postauto ausliefert. Es zählt die Dienstleistung! Darüber schreibt Wikipedia: http://en.wikipedia.org/wiki/Data_as_a_service “As the number of bundled software/data packages proliferated and required interaction among one another, another layer of interface was required.” Zu Deutsch: “Wenn die Zahl der der Anwendungen/Daten wächst ist eine weitere (Abstraktions-) Schicht nötig” Service-orientierung Der Dienstleistungsgedanke ist nicht neu – vor allem nicht in der Software-Entwicklung (siehe Wikipedia http://de.wikipedia.org/wiki/Serviceorientierte_Architektur). Dabei geht uns nicht um „das große Enterprise“, sondern darum, die IT aus der Perspektive der Geschäftsprozesse und Anforderungen zu sehen. Dabei gilt (für uns) Think big, start small - Nach vorne sehen und sich keine Steine in den Weg von morgen zu legen UND die Aufwände zu jedem Zeitpunkt durch Kontrolle und Steuerung der Komplexität realistisch zu halten und somit agil reagieren zu können. Mit diesen Gedanken kommt auch ein anderer Blick auf Daten (http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.97.8639&rep=rep1&type=pdf): Datenzugriff muss koordiniert und kontrolliert werden (Security und Änderungsresistenz) Daten gehören einem Dienst (so wird Kontrolle sichergestellt) Direkter Datenzugriff ermöglicht üblicherweise ein CRUD (Create, Read, Update & Delete – Erstellen, Lesen, Aktualisieren und Löschen) wohingegen ein Dienst die Funktionalität bereitstellt (z.B. „Bestellen“ oder „UmfrageAuswerten“). Änderungen am Schema und Skalierung Neben der Tatsache, das sich Geschäftsfelder erweitern und/oder ändern können und sich dadurch Änderungen an den Strukturen in der Datenbank ergeben können, bedeutet es (gerade) für eine (Web-)Plattform, dass wenn sie Erfolg, die Lasten steigen und andere Konzepte nötig werden um die Daten zu speichern und zu lesen. Ein zentralisierter Datenzugriff reduziert die Aufwände in den Anwendungen und ermöglicht Skalierung, Sharding(http://en.wikipedia.org/wiki/Shard_(database_architecture)) und Integrations-Konzepte (http://en.wikipedia.org/wiki/Data_Integration).

Sitzungslos/Statuslos

http://www.flickr.com/photos/toofarnorth/8670157331/ Aus der RFC 2616: “It is a generic, stateless, protocol” Das heißt, das Fundament auf dem wir aufsetzen ist Sitzungslos. Wenn das Applikations-Framework, egal ob mit Web Forms oder MVC, oder Python, oder PHP, oder Rails…, das respektiert, wird es den Anforderungen des Web gerecht: Skaliert besser – Ich brauche mir im NLB-Szenario (Network Load Balancing) keine Gedanken über Shared Memory machen oder mit dem ASP.NET State-Server einen SPOF (Single Point of Failure) einführen. Skaliert kostengünstiger – Mit MS SQL-Server kann ich State zwar auch *Hochverfügbar* ablegen. Dazu sind dann aber SAN (Storage Area Network), Glasfaser, Switches, Kable, Blech, Strom, Betrieb-System & SQL-Server-Lizenzen zusätzliche Kostenfaktoren. Ist leichter zu testen – Code der auf State reagiert kann nur getestet werden wenn der State reproduzierbar (im Test) erstellt wird. Tests werden komplizierter. Tests dauern länger – letzten Endes auch ein Kostenfaktor. Ist weniger komplex – Code wird verständlicher und transparenter da State sich wie globale Variablen verhält (http://c2.com/cgi/wiki?GlobalVariablesAreBad). Um mal als Beispiel ein Bild zu malen: Wenn ich eine Rakete bauen will um zum Mond zu Fliegen. Bin ich dann schneller auf dem Mond, wenn ich mich mit Thema  Schwerkraft auseinandersetze? Was ist eigentlich State? Oder besser was ist nicht State? Als State werden meist Daten bezeichnet, die temporär sind – also eine sehr befristete Lebensdauer. Häufig ist das aber eine Frage der Perspektive und Granularität. Beispiel E-Commerce Sind es nicht die Daten, der Produkte im Warenkorb, die früher oder später zu Positionen in einer Bestellung werden? Ja und Nein. Natürlich, es sei denn, der User entscheidet sich NICHT dazu die Bestellen-Schaltfläche zu betätigen. Alternativen Cookies In Cookies kann eine begrenzte Datenmenge (1024kb) auf dem Rechner des Users abgelegt werden. VORSICHT: Der User kann die Datei modifizieren. Nicht dass die Produkte im Warenkorb alle nur noch 0 EUR kosten. Auch sensible Daten (selbst wenn verschlüsselt) würde ich hier nicht ablegen: Stichwort Cookie-Hi-Jacking. Je nach Expiration-Date bleiben die Daten hier auch über mehrere Browser-Sitzungen erhalten. HTML5 Web Storage Das neue HTML5 API ermöglicht das Speichern von Dateien im sog. Isolated Storage (http://msdn.microsoft.com/en-us/library/3ak841sy(v=vs.80).aspx) einem Benutzerbezogenen lokalen Verzeichnis. Im Gegensatz zu Cookies, die implizit geladen werden ist es schwieriger diese Daten zu hijacken. Hierbei bleiben die Daten über mehrere Browser-Sitzungen erhalten. http://dev.w3.org/html5/webstorage/ HTML5 Indexed Database API Mit HTML5 kommt eine weitere API. Diese ermöglicht das Ablegen indizierter Daten, wie in einer Datenbank z.B. MS SQL Server, im Isolated Storage. Wie beim Web Storage werden auch hier werden die Daten explizit geladen. Auch hierbei bleiben die Daten über mehrere Browser-Sitzungen erhalten. http://www.w3.org/TR/IndexedDB/ Datenbank Wenn Die Daten (Beispiel E-Commerce) sowieso früher oder später zu einer Bestellung werden, könnte man diese doch einfach so behandeln. Alles was dazu benötigt wird ist eine weiter Spalte in der Datenbank-Tabelle namens z.B. „State“ mit den Werten für „Im Warenkorb“ und „Bestellt“. Hierbei ergeben sich zudem tolle Möglichkeiten: Die Daten bleiben (nur für Angemeldete Benutzer) über mehrere Browser-Sitzungen erhalten Auch über Devices hinweg. Für das Reporting: „TOP 10 Produkte im Warenkorb die aber selten verkauft werden“ und „Verhältnis von Im Warenkorb zu Bestellt“. Nichts desto trotz die *Dateileichen* irgendwann mal aufgeräumt. Der MS SQL Server bietet mit dem SQL Server Agent die Möglichkeit in definierten Intervallen Jobs auszuführen: Backups genauso wie Aufräumarbeiten. Im Zweifel tun es aber auch „Scheduled Tasks“ (http://support.microsoft.com/kb/308569) bzw. von der Konsole die at.exe (http://support.microsoft.com/kb/313289) oder einfach CODE.

.NET Day Franken 2011

Am 21. Mai war ich Sprecher auf dem .NET Day Franken. Ein weiteres tolles Event für die .NET Community. Vielen Dank an Thomas Müller, und Bernd Hengelein und Michael Wiedeking! Zu meinem Vortrag “ASP.NET MVC Localization” hier meine Slides und Demos: Download

dotnet Cologne 2011

Am 6. Mai fand in Köln die dotnet Cologne statt. Neben meinem Sprecher-Engagement hat es mich sehr gefreut, dass unsere Firma, devcoach, dieses gelungene Community-Event als Platin-Sponsor unterstützen konnte. Ein großes Dankeschön an Albert Weinert, Roland Weigelt und Stefan Lange! Zu meinem Vortrag “REST WARS: WCF WebHTTP vs. ASP.NET MVC” hier noch die Slides und Demos: Download

Enable editing of enumerable data in ASP.NET MVC

I’m currently working on an ASP.NET MVC project. Today I stumbled across a requirement that involved enabling the editing of data that is displayed (on a lets call it master page). The specialty of the data is it’s an enumerable. I had a few Ideas how to solve the problem. 1. Ajaxification Pro: I like jQuery. I like that you can directly edit stuff Con: I like to have a low-level fallback 2. The UeberEditorTemplate.ascx  Pro: On first sight an easy way out Con: Yakk! all that logic in one editor template. Both did not really satisfy me. So I started playing around a bit. The first thing I figured out is that editor templates can be used with c# currying: Next I created my action that handles the post to inspect the forms collection the templates would create. This is the time where a custom model binder can be a really be a helpful friend. I switched to a view model that contains the enumerable to enable the model binder through the class attribute: 1 [ModelBinder(typeof(UserContactDataBinder))] 2 public class Xyz 3 { 4 public List<MyDataItem> Data { get; set; } 5 } And finally created the model binder: 1 public object BindModel( 2 ControllerContext controllerContext, 3 ModelBindingContext bindingContext) 4 { 5 var model = new Xyz(); 6 model.Data = new List<MYDataItem>(); 7 var context = 8 controllerContext.HttpContext; 9 var formValues = 10 context.Request.Form; 11 12 var values = 13 formValues["data.Value"].Split(','); 14 15 for (int i = 0; i < values.Length; i++) 16 { 17 var ucd = 18 new MyDataItem 19 { 20 Value = values[i], 21 }; 22 model.Data.Add(ucd); 23 } 24 25 return model; 26 } 27 } That’s it! ASP.NET MVC really rocks!