KHS Linienoptimierung – Technische Umsetzung

17. Januar 2018

KHS,100-prozentige Tochtergesellschaft der Salzgitter AG, hat vor einiger Zeit den Enterprise Mobility Award 2016 für die Anwendung “KHS Linienoptimierung – erfolgreiche Digitalisierung im Maschinenbau” gewonnen.
.
Die Anwendung wurde aufgrund der fachlichen Anforderungen von KHS durch SDX erstellt, weshalb auch wir uns sehr über diese Auszeichnung freuen :-).
.
Der letzte Beitrag stellte die Anwendung selbst vor, dieser Beitrag geht auf die technische Umsetzung ein.

Hinweis: Dieser Beitrag erfolgt in Abstimmung mit KHS; gezeigte Inhalte wurden anonymisiert.

 

KHS Linienoptimierung

Die Herangehensweise bei der Umsetzung von “KHS Linienoptimierung” bzw. den drei Teilanwendungen ist in mancher Hinsicht sicher auf andere Szenarien übertragbar, es gibt aber auch diverse Aspekte, die durch die besonderen technischen Randbedingungen und fachlichen Anforderungen geprägt sind.

Im Folgenden greife ich einige Detailthemen auf, stelle den Lösungsansatz kurz vor und gebe Hinweise, warum der jeweilige Ansatz gewählt wurde. Themen sind:

  • Anwendungsarchitektur
  • Datenhaltung
  • Synchronisierung

Zunächst jedoch ein …

Überblick zur technischen Umsetzung

Das folgende Bild stellt das Zusammenspiel der drei Teilanwendungen Linienoptimierungs-App (LOA), Linienoptimierungs-Manager (LOM) und Linienoptimierungs-Backend (LOB), sowie die Einbindung der relevanten Bestandssysteme dar:

image

Der Abbildung können ebenfalls die eingesetzten Technologien und zentrale Frameworks entnommen werden. SAP taucht hier nicht auf, weil dies außerhalb des Projektes gelöst wurde.

Anwendungsarchitektur

In vielen Cross-Plattform-Projekten wird die Möglichkeit des Code-Sharings bis hin zu ViewModels und XAML (über Xamarin.Forms) betont. Da die GUIs der App und des Managers jedoch sehr unterschiedlich aufgebaut sind, wurde von Anfang an bewusst auf Code-Sharing von GUI-Aspekten verzichtet.

Das hatte zum Beispiel zur Konsequenz, dass bei der GUI-Entwicklung keinerlei Rücksichten genommen werden mussten. Im Manager wurde letztlich Caliburn.Micro für eine effiziente Entwicklung und Mahapps.Metro für ein ansprechendes UI-Design eingesetzt. Für die iOS-App kommt Xamarin.Forms aufgrund der damit einhergehenden Produktivität zum Einsatz. Es gab jedoch diverse Stellen, an denen mit Custom Renderern auf Plattformfunktionen zurückgegriffen werden musste.

Gemeinsam genutzte Funktionalität, etwa für die Synchronisierung, wurde konsequent in tieferliegende Schichten ausgelagert und wird dort (teilweise plattformübergreifend als portable class library PCL) für alle Teilanwendungen bereitgestellt. Dies gilt auch für die Datenhaltung. Hier wird das gleiche Datenmodell von allen drei Teilanwendungen verwendet; es lag also nahe, von vorne herein die Gemeinsamkeiten zu betonen.

Dieser Ansatz – Unterschiede je Plattform wo es Sinn macht, gemeinsam verwendeter Code wo möglich – wurde durch eine vereinheitlichte Anwendungsarchitektur erreicht, die von allen drei Teilanwendungen eingehalten und anwendungsspezifisch mit Leben gefüllt wird:

Anwendungsarchitektur

Jede Teilanwendung füllt diese Blöcke für ihre Konstellation mit Leben. Die gelb markierten Teile werden von mehr als einer Teilanwendung gemeinsam verwendet, entweder als Bibliothek (teilweise PCL) oder über Code-Generierung. Hier die Variante für die iOS-App:

Anwendungsarchitektur LOA

Man erkennt gut, dass sich die Unterschiede auf die GUI, also Views und ViewModels (weil spezifisch für die App) beschränken. Dazu kommt die (rein technische) Adaption der Datenbank …

Datenhaltung

Nachdem die Daten über alle drei Teilanwendungen hinweg synchronisiert werden müssen, lag es auf der Hand, ein gemeinsames Datenmodell zu verwenden. Ein vollständiges Code-Sharing schied jedoch aus, weil jede Teilanwendung ein anderes DBMS – SQL Server, SQL Server Compact, SQLite – und damit einhergehend ein anderes Framework zum Zugriff verwendet. Stattdessen wurde eine Lösung basierend auf Code-Generierung umgesetzt.

Datenmapper T4 Skripte Ein Datenbank-Projekt und eine Anbindung über Entity Framework (database first) dient als Referenz. Das EF-Modell wird vom WCF-Service im Backend und dem Manager direkt verwendet, für die App wird der Code für den Zugriff auf SQLite durch angepasste T4-Scripte in einem eigenen Projekt – aber basierend auf dem gleichen Entity Framework-Datenmodell – erzeugt.

Ebenso werden benötigte Datenmapper und die typischen CRUD-Methoden durch T4-Scripte angelegt, vgl. Bild rechts.

Durch diesen Code-Generierungsansatz war es möglich, über alle drei Anwendungen hinweg den jeweils benötigten Code konsistent, aktuell und ohne große Aufwände bei Änderungen verfügbar zu haben – exakt so, wie er gerade im jeweiligen Kontext benötigt wird.

Synchronisierung

Auch bei der Synchronisierung wurde auf Synergien geachtet: Da sich die Synchronisierung zwischen der App und dem Manager nicht wesentlich von der zwischen dem Manager und dem Backend unterscheidet, kommt in beiden Fällen der gleiche WCF-Service zum Einsatz. Das Backend hostet diesen wie üblich über eine .svc-Datei im IIS, der Manager nutzt die gleiche Implementierung für ein Self-Hosting.

Typische Falle beim Self-Hosting: Windows lässt das Öffnen eines http-Endpoints aus Sicherheitsgründen nicht ohne weiteres zu. Entweder muss die Anwendung mit Administratorrechten ausgeführt werden, oder ein Administrator muss dem Anwender die entsprechenden Rechte erteilen.

Ein typischer Ablauf beginnt mit dem “Verbindungsaufbau” (ein einfaches Ping um die Erreichbarkeit zu verifizieren):

LOM_Verbindungsaufbau

Gefolgt von der eigentlichen Synchronisierung, deren Ablauf in der Oberfläche nachvollziehbar ist:

LOM_Upload

Technisch ist der Ablauf im folgenden Sequenzdiagramm dargestellt:

LOM_LOB_UploadProject

Der “Verbindungsaufbau” über einen einfachen Ping-Aufruf ohne zusätzliche Übertragung von irgendwelchen Nutzdaten soll die grundsätzliche Erreichbarkeit des Services sicherstellen. Diese ist weder über das Ad-Hoc-WLAN-Netzwerk, noch bei der Verbindung zum Backend über VPN garantiert. Die Trennung von inhaltlichen Aufrufen erlaubt eine saubere Unterscheidung grundsätzlicher Nichterreichbarkeit von anderen Problemen.

Fazit

Die KHS Linienoptimierung unterscheidet sich von anderen typischen Cross-Plattform-Projekten, weil sich die Teilanwendungen auf den unterschiedlichen Plattformen inhaltlich nicht entsprechen. Daher wurden Fragen nach Synergien zwischen den Teilanwendungen auch anders beantwortet, als man das in den üblichen Tutorials findet:

  • Für das Sharing des Zugriffs auf die Datenhaltung kam Code-Generierung zum Einsatz.
  • Die gemeinsam verwendete Geschäftslogik, z.B. für die Synchronisierung, wurde über portable class libraries (PCL) bereitgestellt.
  • Im GUI wurde bewusst auf Code-Sharing verzichtet, obwohl das technisch zumindest in Teilbereichen möglich gewesen wäre.

Diese Entscheidungen waren wesentlicher Schlüsselfaktor, um in diesem Szenario eine effiziente Entwicklung – Synergien wo möglich, Flexibilität wo nötig – zu ermöglichen. Um diese Entscheidungen zu treffen, war zu Beginn des Projektes eine saubere Planung und Architekturphase entscheidend.

Oder wie unser Marketing das formuliert: One App, multiple devices – Architektur ist entscheidend! Eine Erfahrung, die wir häufiger machen

autor Alexander Jung

Alexander Jung

Chief eXpert Alexander.Jung@sdx-ag.de