Archiv der Kategorie: Architecture

Microservices don’t like thinking in conventional entities

I recently had one of these special AHA-moments in a workshop held by Udi Dahan, CEO of Particular. In his example he was using the classic entity of a customer.

To realise microservices means cutting functionality in a clean way and to transfer it into separate pillars (or silos). Each silo has to have the responsibility over it’s own data, on which it builds the respective business processes. So far, so good. But how can we realise this for our typical customer, who’s model is shown in the screenshot? Different properties are needed or changed by different microservices.

If the same entity is used in all pillars, there needs to be a respective synchronisation between all microservices. This results in a considerable impact on scalability and performance. In an application with lots of parallel changes of an entitiy the failing of the business processes will increase – or lead to inconsistencies in the worst case.

Conventional Customer

conventional entity of a customer

Udi suggests the following modelling

New Customer

Customer is modelled with independent entities

To identify which data belongs together, Udi suggests an interesting approach:

Ask the operating department if changing a property has a consequence for another property.

Would changing the last name of customer have an influence on the price calculation? Or on the way of marketing?

Now we need to solve the problem of aggregation, for example if I want to show different data from different microservices in my view. In a classic approach we would have a table with following columns:

ID_Customer ID_MasterData ID_Marketing ID_Pricing

This leads to the following two problems:

  1. The table needs to be extended if a new microservice is added
  2. If a microservice covers the same functionality in the form of data, you would have to add multiple columns for each microservice and allow NULL values as well

An example for the second point could be a microservice which covers the matter of payment methods. In the beginning you could only use credit cards and debit charges. Then Paypal. Bitcoin soon after. The microservice would have different tables on which the respective data for the payment method would be stored. In the aggregated table shown above it would be necessary to fill a separate column for each payment method the customer is using. If he doesn’t use it, a NULL value would be written. As you can see: This sucks.

Another approach is much more convenient for this. Which one this is and how it’s realised technically you can find on the GitHub repository of Particular.

 

Advertisements

Microservices mögen kein Denken in klassischen Entitäten

Einen ganz besonderen AHA Moment hatte ich kürzlich in einem Workshop bei Udi Dahan, CEO von Particular. In seinem Beispiel ging es um die klassische Entität eines Kunden.

Microservices zu realisieren bedeutet Fachlichkeiten sauber schneiden und in eigenständige Silos (oder Säulen) packen zu müssen. Jedes Silo muss dabei die Hohheit über die eigenen Daten besitzen, auf denen es die zugehörigen Geschäftsprozesse abbildet. Soweit so gut. Doch wie lässt sich dies im Falle eines Kunden bewerkstelligen, der klassischerweise wie im Screenshot zu sehen modelliert ist? Unterschiedliche Eigenschaften werden von unterschiedlichen Microservices benötigt bzw. verändert.

Wird die gleiche Entität in allen Silos verwendet, muss es eine entsprechende Synchronisierung zw. den Microservices geben. Das hat erhelbiche Auswirkungen auf Skalierbarkeit und Performance. In einer Applikation mit häufig parallelen Änderungen an einer Entität wird das Fehlschlagen von Geschäftsprozessen zunehmen – oder im schlimmsten Fall zu Inkonsistenzen führen.

Klassische Kundeentität

Klassische Kundeentität

 

Udi schlägt die folgende Modellierung vor:

Neue Modellierung eines Kunden

Der Kunde wird durch unabhängige Entitäten modelliert

Zur Identifikation, welche Daten zusammengehören, schlägt Udi einen Interessanten Ansatz vor:

Fragt die Fachabteilung, ob das Ändern einer Eigenschaft Auswirkung auf eine andere Eigenschaft hat. 

Würde das Ändern des Nachnamens einen Einfluss auf die Preiskalkulation haben? Oder auf die Art der Marketings?

Nun gilt es noch das Problem der Aggregation zu lösen, sprich wenn ich in meiner Anzeige unterschiedliche Daten unterschiedlicher Microserivces anzeigen möchte. Klassischerweise würde es jetzt eine Tabelle geben, die die Spalten

 

ID_Kunde ID_Kundenstamm ID_Bestandskundenmarketing ID_Preiskalkulation

 

besitzt. Das führt aber zu 2 Problemen:

  1. Die Tabelle muss immer erweitert werden, wenn ein neuer Microservices hinzugefügt wird.
  2. Sofern ein Microservices die gleiche Funktionalität in Form unterschiedlicher Daten abdeckt, müssten pro Microservices mehrere Spalten hinzugefügt und NULL Werte zugelassen werden.

Ein Beispiel für Punkt 2 wäre ein Microservices, der das Thema Bezahlmethoden abdeckt. Anfangs gab es beispielsweise nur Kreditkarte und Kontoeinzug. Dann folgte Paypal. Und kurze Zeit später dann Bitcoin. Der Microservices hätte hierzu mehrere Tabellen, wo er die individuelle Daten für die jeweilige Bezahlmethode halten würde. In oben gezeigter Aggregationstabelle müsste aber für jede Bezahlmethode, die der Kunde nutzt, eine Spalte gefüllt werden. Wenn er sie nicht benutzt, würde NULL geschrieben werden. Man merkt schon: Das stinkt.

Ein anderer Ansatz ist da deutlich besser geeignet. Welcher das ist und wie man diesen technischen realisieren kann, könnt ihr im GitHub Repository von Particular nachschauen.

 

Quellen zu Defensives Design und Separation of Concerns sind jetzt online

Den Quellcode zu meinen Vorträgen auf den Karlsruher Entwicklertagen und der DWX sind jetzt online:

  • Zu Super Mario Kata mit Fokus auf Defensivem Design geht es hier.
  • Zur Prüfsummen Kata mit fokus auf Separation of Concerns gelangt ihr hier.

Auf beiden Seiten findet ihr auch die Links zu den PowerPoint Folien. Im Juli 2018 werde ich den Code der Prüfsummen Kata noch in Form von Iterationen veröffentlichen und beide Talks als YouTube Video freigeben.

IMG_20180627_145405

Defensives Design Talk auf der DWX

Ihr wollt Teile davon in euren Vorträgen verwenden, ihr wollt ein Training zu dem Thema oder ich soll dazu in euerer Community einen Vortrag halten, dann kontaktiert mich über die auf GitHub genannten Kanäle.

Workshop: Conquer your Codebase – Bewährter Clean Code aus der Praxis (Materialien)

Einen herzlichen Dank an alle Teilnehmer des Workshops am vergangenen Freitag beim Developer Open Space 2017. Trotz des völlig unterschiedlichen Backgrounds – von Ruby, über PHP, zu Java oder gar nicht objektorientierte Sprachen wie JavaScript – war ebenso alles vertreten wie vom Azubi bis hin zum Entwickler mit 20-jähriger Berufserfahrung.

IMG_20171013_132904

Einer von vielen mutigen Freiwilligen

Den Code zur Super Mario Kata gibt es hier. Beachtet die neuen Anforderungen (9-12), die ich auf dem Heimweg im Zug noch hinzugefügt habe. Damit einhergehend habe ich noch ein Refactoring des Konzepts ‚Leben‘ durchgeführt, sodass keine Actions bzw. Funcs mehr an die Methoden übergeben werden müssen. Gleichfalls fällt das Branching-Statement raus und es ergibt sich eine nahezu völlig flexible Möglichkeit zur Erstellung von Spielmodi. Die Tests sind nun ebenfalls alle umgesetzt, was wir gegen Ende hin aufgrund von Zeitmangel ausgelassen haben. Eine Testmethode hat in der Regel eine Zeile und wie schon im Workshop erwähnt: Was gut zu testen ist, ist in der Regel auch eine saubere Lösung.

IMG_20171013_132938

20 Teilnehmer mit unterschiedlichen Backgrounds

Derjenige, der noch eine Lösung mit dem Command-Pattern umsetzt und dadurch das Anpassen bestehender Klassen völlständig vermeidet, erhält von mir einen Gutschein für unsere Trainings. Damit kann er kostenlos an jedem beliebigen 3-tägigen Workshop in unseren Karlsruher Büros teilnehmen (Fahrt- und Übernachtungskosten sind ausgeschlossen).

Alle, die über den Workshop bloggen oder twittern, erhalten darüber hinaus noch einen 30% Rabattcode. Einfach Link schicken, dann kriegt er diesen per Mail.

tweet-workshop

Ein Teilnehmer versucht sich in einer Lösung mit Java statt C#

Weiterführende Links

  • Das erwähnte Video zu Enumeration mit Verhalten könnt ihr hier anschauen.
  • Danke an Tim für den Link zum Case Converter für Visual Studio.
  • Außerdem lege ich euch die Reactive Extensions ans Herz, die es für unterschiedliche, gängige Programmiersprachen gibt.
  • Git Snippet
  • Wer noch ein wenig üben möchte, kann dies mit der erweiterten FizzBuzz Kata tun.
  • Blog Post über die Migration von NHibernate zu EntityFramework in 3 Tagen.

 

Demnächst geht ein Video mit dem theoretischen Teil (Why-How-What) online, in dem ich nochmal die Zusammenhänge zw. „schlechtem Code“ und den Gründen dafür erläutere. Wer automatisch informiert werden will, wenn es veröffentlich wird, abonniert einfach meinen Blog oder schickt mir eine Nachricht.

 

 

Workshop: Conquer your Codebase – Bewährter Clean Code aus der Praxis

Am Developer Open Space 2017 halt ich einen 1-tägigen Workshop zu obigem Thema. In reduzierter, kompakter Form werde ich dazu bewährte Inhalte aus meinem 3-tägigen Seminar nehmen und die Ursachen für folgende Probleme adressieren:

  • Unverständlicher bzw. schlecht wartbarer Code
  • Bugs
  • Skalierungsprobleme
  • Go Live Probleme
  • Verpasste Deadlines und lange Entwicklungszeiten

 

Wir werden uns anschauen wie es dazu kommen kann, z.B. weil

  • die Infrastruktur nicht wiederverwendbar ist,
  • die Domänenlogik nicht erweiterbar ist,
  • eine falsche Nutzung der API möglich ist,
  • der Code nicht ausdrucksstark ist,
  • oder starke Abhängigkeiten bestehen.

 

Wir werden das Open Closed Principle genauer besprechen und Seperation of Concerns am konkreten Beispiel umsetzen. Speziell für Freunde der Objektorientierung werde ich je nach verfügbare Zeit praktische Lösungen zur Vermeidung von If-Else-Zweigen und NULL-Checks zeigen.

 

Ein Laptop mit Visual Studio oder Visual Studio Code und .NET 4.6 wären wünschenswert. Prinzipiell ist der Workshop aber für alle Entwickler des objektorientierten Paradigmas geeignet, da bis auf Delegaten (Action/ Func) und Erweiterungsmethoden kaum Sprachspezifika verwendet werden. Darüber hinaus können Teilnehmer auch ohne Hardware beiwohnen, weil wir beim Live Coding am Präsentations-PC mit Code Monkey Runden arbeiten werden.

Gerne dürfen die Teilnehmer mir vorab Fragen und Probleme z.B. hier in Form von Kommentaren oder per E-Mail zukommen lassen.

Open Closed Principle mit 2 Zeilen Code

In meinem Video zu 60 Minuten mit der Pfadfinderregel war ich noch die Lösung zu Castle.Windsor schuldig. In diesem Webcast zeige ich wie die CollectionResolver-Funktionalität genutzt werden kann, um nachträglich hinzugefügte Implementierungen automatisch im Container zu registrieren.

Dadurch kann das OCP vollständig eingehalten werden, da lediglich eine neue Klasse hinzugefügt werden und der restliche Code nicht angefasst werden muss. Den Code habe ich hier zur Verfügung gestellt. Fragen und Feedback einfach in die Kommentare.

Durch Klicken auf das Bild geht es zum Video

Durch Klicken auf das Bild geht es zum Video

Testen von Datenbankabfragen – Es geht auch einfach

In diesem Screencast zeige ich wie selbst Abfragen mit mehreren Bedingungen und Sortierungen einfach getestet werden können. Unter der Haube kommt das Entity Framework zum Einsatz. Davon kriegt man dank Dependency Injection aber nichts mit.

Die erwähnte Webcast Serie, sowie weiteren Beispielcode und das Projekt auf Github gibt es hier. Feedback oder Fragen nehme ich gerne entgegen. Wenn ihr wollt, dass ich die Serie fortsetze, sprecht mich über einen Kanal eurer Wahl an.

%d Bloggern gefällt das: