RPA-Kompendium: Tidy data matters

Die meisten Daten unserer real existierenden Business-Welt sind Messy Data. Da werden optisch trennende Leerzeilen in Excel-Tabellen (dem kleinsten gemeinsamen Nenner der IT im Unternehmen) eingefügt und Zellen verbunden, Schriftfarben eine Bedeutung zugewiesen und leere Spalten eingesetzt um Abstände zwischen die Daten zu bekommen. Die Benutzung dieser Tabellen orientiert sich eher am menschlichen Benutzer als am Roboter der damit nun arbeiten soll.

Das Problem mit den Messy Data beschränkt sich allerdings nicht nur auf das von mir bei Controllern als Berufskrankheit akzeptierte Excel, sondern tritt überall auf. Meistens sind Bestände an Messy Data historisch gewachsen und dadurch bedingt, dass die Daten an verschiedenen Orten zu unterschiedlichen Aufgaben gesammelt oder erfasst wurden. Der Gipfel von Messy Data betrifft den Themenkomplex OCR, den ich extra behandeln werde.

Um nicht falsch verstanden zu werden: Die Existenz von Messy Data ist völlig nachvollziehbar, aber der Wunsch damit direkt weiterarbeiten zu wollen ist es nicht.
Tidy Data bedeutet ganz grob: Ein Entitätstyp pro Tabelle, Datensätze in Zeilen, Attribute in Spalten, in jeder Zelle nur maximal ein Wert. Für die Datenbanker: So knapp vor Erste Normalform. Das habe ich mir nicht ausgedacht sondern diese Klassifikation kommt aus der Wissenschaft, wo man mit Daten erst dann feine Analysen machen kann wenn man sie etwas in Form gebracht hat.

Ein Beispiel dazu: Das ist so eine Excel-Mappe mit Rechnungen, jeweils nach Jahren und Fachbereichen einzelne Tabellen darin. Das ist für Menschen schön übersichtlich, wenn man einen Roboter drauf ansetzen will gibt’s zwei Möglichkeiten: Entweder der Roboter wird so programmiert dass er mit dem Kram zurechtkommt oder wir bringen die Daten vorher in eine saubere Form. Das bedeutet in diesem Fall eine Tabelle (wir haben einen Entitätstyp Rechnung) und Fachbereich und Jahr sind einfach weitere Attribute (also Spalten) in der großen Tabelle. Sofern letzteres nicht redundant ist, weil eh ein Datum als Attribut drin steht.

Was RPA angeht ist es nun so, dass meiner Ansicht nach die Grenze zwischen Messy Data und Tidy Data die Queue sein sollte. Das heißt also dort, wo der Arbeitsvorrat für den Prozess definiert wird. Die Queue ist ohnehin so ein unterschätztes Merkmal von RPA, aber dazu an anderer Stelle mehr. Damit ist sichergestellt dass der Prozess sauber lesbar bleibt und sich konzentriert um die Applikationen kümmern kann, die automatisiert werden sollen. Wenn man anfängt im Prozess zur Laufzeit auch noch die Daten aus den meist menschgemachten Vorprozessen auseinanderfusseln zu müssen dann wird der Code an dieser Stelle hässlich. Und das bedeutet schlecht wartbar und fehleranfällig.

Üblicherweise verwendet man dazu für einen Roboter eine Aufteilung in einen Loader und einen Worker (bei UIPath heißen die Dispatcher und Performer, ist aber das selbe). In dem Loader sorgt man dafür das die ganzen in den Prozess eingehenden Datenmengen in eine saubere Form (also Tidy Data) gebracht werden. Der direkte Ansatz ist dazu dass man also genau genommen zwei Roboter macht, einen um die Daten bereitzustellen, sowie einen weiteren der Arbeit erledigt. Wenn dann viel zu tun ist skaliert das auch viel besser, aber auch dazu kommen wir noch.

Dass der Worker-Teil der RPA-Lösung mit einer RPA-Software implementiert werden muss steht sicher außer Frage. Der Loader-Teil allerdings lässt sich meist besser mit Big-Data-Werkzeugen umsetzen, die virtuos mit unterschiedlichen Datenquellen umzugehen gelernt haben wie beispielsweise Python mit Pandas. Egal woher die Daten kommen, Pandas macht daraus Dataframes und sie lassen sich dann mergen, melten, slicen oder was auch immer erforderlich ist.

Vor 30 Jahren sagte mein Informatikprof in der Vorlesung: „Sie können auch mit einem Aschenbecher einen Nagel in die Wand schlagen, aber sollten dies nicht als den richtigen Weg propagieren.“ Daher an dieser Stelle noch einmal der Hinweis darüber nachzudenken ob die RPA-Lösung für den Loader das richtige Werkzeug ist. Die Stärke von RPA-Lösungen ist die Interaktion mit dem Zielsystem, nicht die Analyse und Konvertierung von Daten.

Die Aufteilung in Loader und Worker ist sogar dann sinnvoll, wenn das Quell- und Zielsystem der Automatisierung identisch ist, und beide Teile mit der RPA-Lösung implementiert werden sollen, wie man es oft bei Projekten im Umfeld von SAP hat. Ein Team kann den Loader programmieren, der den Arbeitsvorrat mit allen benötigten Attributen auch aus mehreren Transaktionen zusammen sammelt und in die Queue schreibt. Ein anderes kümmert sich darum, die Daten aus der Queue mit einem Worker abzuarbeiten. Das kann auch durch unterschiedliche Teams mit spezieller Expertise für die jeweilige Umgebung und sogar in zeitgleichen Sprints erfolgen.

Um auf Pandas zurück zu kommen: Eine gute RPA-Lösung bietet an, die gewünschten Transaktionen über eine REST-API in die Queue zu schreiben. Damit kann man Python verwenden um die Daten in Form zu bringen und dann auch gleich ohne den Umweg über CSV oder andere Exporte für den Worker in die Queue zu pumpen. Was nebenbei auch noch den Vorteil hat damit den Worker nur bei Bedarf triggern zu können.

Abschließend zusammengefasst kann man sagen, dass ein RPA-Prozess nie versuchen sollte mit Messy Data direkt loszurennen. Es sollte immer ein Schritt vorgesehen werden der daraus Tidy Data macht. Außerdem ist es sinnvoll das Ergebnis, also die hier erzeugten aufgeräumen Daten dem Auftraggeber vorzulegen, um sicherzustellen, dass es sich dabei um die Daten handelt die der Roboter verarbeiten soll.

RPA-Kompendium: Einsichten eines Informatikers

Die letzten Jahre habe ich mich bei einem DAX-Konzern intensiv mit RPA beschäftigt. RPA ist die Abkürzung für Robotics Process Automation und gemeint sind damit Roboter in Form von Software die bei anderen Programmen auf Knöpfe drücken und dabei die Arbeit in Form von Prozessen (vulgo: Klickarbeit) leisten die sonst ein Mensch machen würde. Das Ziel ist dabei repetitive Abläufe zur automatisieren um so mehr Raum für anspruchsvollere Tätigkeit zu geben.

Dafür gibt es verschiedene Produkte auf dem Markt zu Preisen von mehrere Kiloeuro pro Jahr, wie UIPath, Blue Prism oder Automation Anywhere, aber auch kostenloses Zeug wie OpenRPA und Pakete für Programmiersprachen wie Python. Mein persönlicher Favorit für den Business-Einsatz ist UIPath, da die typischen Probleme im geschäftlichen Alltag von zickigen Applikationen bis zur Governance aus meiner Einschätzung am besten abgebacken werden.

RPA ist dabei etwas mehr als nur andere Programme zu skripten, es ist ein ganzheitliches Konzept um Geschäftsprozesse in einem Unternehmen zu automatisieren. Wer hier nur den Teil betrachtet bei dem die RPA mit anderen Programmen interagiert sucht nur nach Ähnlichkeiten aber verkennt die Unterschiede.

Es ist eben nicht RPA wenn man mit VBA oder Python einfach nur Klickarbeit automatisiert, dies kann ein Teil davon sein, viel wichtiger ist aber dass die Prozesse dokumentiert werden, wartbare und beherrschbare Lösungen entstehen, das Ganze auch noch den Anforderungen an Datenschutz, Datensicherheit und Compliance genügt, und nicht zuletzt dass man jederzeit gegenüber den Fachabteilungen auskunftsfähig ist was der Roboter denn gerade so macht.

Außerdem ist es wichtig dass Prozesse im Unternehmen erkannt, analysiert und optimiert werden. Wenn der Roboter einfach nur genau das machen soll was vorher per Hand gemacht wurde dann wird das Projekt mit ziemlicher Sicherheit scheitern. Der sogenannte Business Analyst (früher sagte man Systemanalytiker dazu) muss wie ein Roboter denken können und die technischen Möglichkeiten genau kennen.

Setzt man hier die Personen mit den falschen Skills ein bedeutet dies nach hinten raus Mehrarbeit und unzufriedene Fachabteilungen. Es reicht für den Business Analyst eben nicht aus nur den Ist-Prozess zu dokumentieren, auch wenn dies allein schon in einigen Abteilungen eine reife Leistung sein kann.

In den letzten Jahren habe ich einige grundsätzliche Erkenntnisse bei der Architektur von RPA-Lösungen gewinnen können. Dazu beigetragen hat auch mein monatlich veranstaltetes Meetup der RPA-Developer in Berlin.

Dabei geht es nicht um bestimmte Produkte, vielmehr geht es mir um grundsätzliche Einsichten eines Informatikers zum Thema, die ich in dieser Serie von Artikeln in meinem verstaubten Blog teilen möchte. Vielleicht wird mal ein Buch draus.

SQL-Daten konvertieren

Für alles mögliche verwende ich seit einige Zeit Serendipity. Das ist eigentlich ein Blog, aber ich verwende es mehr als CMS (Content Management System). Damit stelle ich ganz unterschiedliche Themen online, von den Notizen aus dem Geoinformatik-Studium bis zu POI in Berlin.

Wobei ich letztere gar nicht selbst eingebe, sondern über ein kleines PHP-Programm aus einer XAPI-Abfrage der OSM-Datenbank konvertieren lassen. Die meisten kennen nur die Karte von OpenStreetMap, aber da sind ja auch POI (Points Of Interest, Orte von Interesse) drin. Und da sind wir auch schon beim Thema SQL-Konvertierung.

Das war nicht schon immer so, dass ich alles mögliche mit S9y (wie die Software in Kurzform heißt) gemacht habe. Früher hatte ich auch mal eine Terminkalender-Software in Verwendung, deren Daten ich schon vor einiger Zeit mit ein paar SQL-Befehlen aus der mySQL-Datenbank-Tabelle in das Blog konvertiert habe.

Gestern war es mal wieder soweit. Das Update des FAQ-Systems phpMyFAQ ging schief und es tat sich gar nichts mehr. Wieder zurück zur alten Version, alles schick, nur das Update wollte nicht. Also schnell beschlossen: Die Geocaching-FAQ wird nun auch auf S9y umgestellt. Da weiß ich zumindest mittlerweile, wo welcher Knopf ist an dem ich drehen muss wenn mal was nicht will.

Ein Aufgabenstellung, die man öfter mal hat. Die Daten von einem System (hier wars nun eben zufällig phpMyFAQ) sollen in ein anderes (bei mir zumindest zur Zeit immer S9y) konvertiert werden - es gibt aber keinen fertigen Konverter.

Die Konvertierung von Daten auf dem SQL-Server ist dabei ziemlich einfach, wenn man sich die Datenbanken in den beiden Systemen anguckt. Und unter der Voraussetzung, dass bei beiden Systemen das Encoding richtig eingestellt ist, also ISO-Latin oder UTF8. Das ist dann der Fall, wenn man die Inhalte in den Tabellen einwandfrei lesen kann, sprich: Die Umlaute stimmen.

Für alle die es interessiert, gehe ich hier den Ablauf mal durch, der als Beispiel für alle Konvertierungen dieser Art dienen kann.

insert into serendipity_entries (id, title, body, extended, author, timestamp) SELECT id, keywords as title, thema as body, content as extended, author, links_check_date as timestamp FROM phpmyfaq_faqdata


Man fängt am besten hinter dem Select an zu lesen. Die Einträge aus der FAQ werden dazu ausgewertet, alle Felder die in dem Blog benötigt werden werden mit einem Alias ausgewählt, wie er in dem Blog heissen soll. Dort werden sie dann auch mit der Einfügeabfrage reingeschrieben.

insert into serendipity_authors (realname, username, email) select author as realname, author as username, email from phpmyfaq_faqdata group by email


Hier wird eine Benutzertabelle aufgebaut. Die brauche ich in den Blog zwar nicht, aber so kann man das machen. Einloggen können die sich mangels Passwort schon nicht. Die User-ID bekommen die Benutzer im Blog durch das Autoincrement, Benutzer gabs in der FAQ nicht, man konnte mit Name und E-Mail seinen Beitrag dort abliefern.

insert into serendipity_category (categoryid, category_name, category_description) SELECT id as categoryid, name as category_name, description as category_description FROM phpmyfaq_faqcategories


Die Kategorien aus der FAQ werden dann so 1:1 in das Blog konvertiert - sehr unspektakulär.

insert into serendipity_entrycat (categoryid, entryid) SELECT category_id as categoryid, record_id as entry_id FROM phpmyfaq_faqcategoryrelations


Bei wohl allen Systemen dieser Art gibts dann eine n:m-Relation zwischen Artikeln und Kategorien. Das kann auch so direkt konvertiert werden. Die Felder heißen nur unterschiedlich, aber dafür kann man ja den passenden Alias hinter "as" verwenden.

update serendipity_entries set authorid=1
update serendipity_entries set exflag=1
UPDATE serendipity_entries SET isdraft = 'false'


Damit die Beiträge auch angezeigt werden, müssen noch ein paar Felder in dem Blog gesetzt werden, die beim Füllen der Tabelle nicht berücksichtigt wurden. Hätte man auch gleich machen können, aber dann wäre die Einfügeabfrage etwas unübersichtlicher geworden.

insert into serendipity_comments (entry_id, author, email, body, timestamp) SELECT id as entry_id, usr as author, email, comment as body, datum as timestamp FROM phpmyfaq_faqcomments


Auch die Kommentar aus der FAQ sollen als Kommentare im Blog verwendet werden. Kein Problem, die Felder gibts in beiden Systemen. Sogar die Timestamps sind auf beiden Systemen Unix-Sekunden, falls das nicht so ist kann man schon beim Select die Timestamp-Funktion vom SQL verwenden um andere Datumsangaben zu konvertieren.

update serendipity_comments set type="NORMAL"
update serendipity_comments set status="approved"


Damit die Kommentare auch korrekt angezeigt werden, müssen nur noch ein paar Attribute korrigiert werden. Das wars dann auch schon.

So eine Sammlung von Abfragen kann man dann immer wieder verwenden, wenn man sie einmal erstellt und getestet hat, um Daten von einem System in ein anderes zu konvertieren. Wer lange genug mit Computern zu tun hat, wird wissen warum: Der Zeitpunkt, von einem System auf ein anderes zu wechseln wird immer kommen, die Frage ist nicht ob, sondern wann.

Pocklington's Mantra

Dr. Jackie Pocklington ist amerikanischer Staatsbürger und lehrt seit 2000 als Professor für Wirtschaftsenglisch und technisches Englisch an der Beuth Hochschule für Technik in Berlin.

Von ihm kommt Pocklington's Mantra für Präsentationen: "Announce, click and wait!" Mit dieser Technik kann man ohne großen Aufwand jede Präsentation aufwerten, wenn man den Ablauf der Folien genau kennt.

Ein deutliches Beispiel: Auf einer Folie soll ein Diagramm gezeigt werden, auf dem man irgendeinen Sachverhalt erkennen kann. In jeder Durchschnittspräsentation wird eine Folie gezeigt, dann erklärt der Vortragende sofort, was zu sehen ist. Allerdings ist in die frische Folie hinein vorgetragen die Aufmerksamkeit des Publikums stark reduziert. da es damit beschäftigt ist sich auf dem Diagramm zu orientieren.

Besser ist jedoch eine Ankündigung wie: "Damit kommen wir zur Analyse der ... ich habe dazu ein Diagramm vorbereitet, in dem man die ... in Abhängigkeit von ... sehen kann." Klick. Diagramm ist da. Fünf Sekunden Pause für die Zuschauer. Erst jetzt kommt die Erläuterung hinterher.

Anderes Beispiel: "Mein Vortrag gliedert sich in drei Teile." Klick. Folie mit Agenda erscheint. Warten. Die Zuschauer müssen alles gelesen haben können. Erst jetzt wird ausführlich erläutert in welche Teile der Vortrag gegliedert wurde.

Let's get ready to Mumble

Selten hat mich ein Stückchen Software so begeistert wie Mumble. An sich ist ist es nichts Spektakuläres mehr, über das Internet miteinander zu sprechen. Seit Skype kennt wohl jeder die Möglichkeit, ein Headset aufzusetzen und damit zu telefonieren.

Seit einiger Zeit hab ich nun abends auch so ein Ding auf. Ich telefoniere aber nicht, sondern ich benutze eine Konferenz-Software, die den Eindruck vermittelt, man säße in einem Konferenzraum (oder nennen wir es Stammtisch oder was auch immer) und spräche miteinander. Das ganze hat etwas von einer Runde auf einem Funkkanal, die Gesprächspartner sind aber nicht zufällig, sondern von ähnlicher Interessenslage, in meinem Fall gehts um Geocaching.

Erfunden wurde die Mumbelei eigentlich für Spieler, die sich durch dreidimensionale Labyrinthe hetzen um ihre Cybergegner zu zermetzeln. Da sollen vergleichbare Lösungen wie Teamspeak den Nachteil einer schlechteren Verständlichkeit und vor allem einer längeren Laufzeit (Latenz) gehabt haben - Sekundenbruchteile, die wohl über virtuelles Leben und Tod entscheiden können.

So stressige Spielchen sind zwar nichts für mich, aber ich habe mir vor zwei Monaten für kleines Geld auch einen Mumble-Server gemietet, auf dem abendlich nun die Geocacher live die aktuellen Geocaching-Themen durchzugehen. Soweit dazu was ich damit mache, nun mal lieber zur Technik.

Man kann sich einen Client für den Mumble-Server für verschiedene Systeme (Windows, Mac, Linix) kostenlos herunterladen wie es bei Open Source üblich ist. Der verbindet sich über einen TCP-Port (64738, C64-Veteranen werden sich erinnern!) mit einem Mumble-Server. So ähnlich wie man es vom IRC kennt, es sind daher keine speziellen Verrenkungen auf der Firewall erforderlich, allerdings ist die ganze Kommunikation SSL-verschlüsselt.

Man kann dann sein Headset für sprachgesteuerten Betrieb mit einem Assistenten konfigurieren. Das braucht man aber nicht, wenn das Headset funktioniert (Stecker, Treiber, Einstellung), was für die meisten das größte Problem darstellt, kann man sofort mitmachen. Die Taste um zu sprechen ist frei wählbar und ein kleines rotes Icon zeigt wenn man "on air" ist.

Das Feature der Sprachausgabe kann man übrigens auch abschalten, besonders URLs die man mal während der Konferenz kurz durchreicht (auch das geht, wird bei Messengern wie ICQ ja auch gern gemacht) hören sich vorgelesen doch sehr merkwürdig an.

Wenn man keinen eigenen Server hat kann man einen der Server wählen, die der Client in einer Liste so anbietet. Auf jeden Fall müssen sich Benutzer, die miteinander sprechen wollen dem selben Server verbunden sein und sich auf dem gleichen Kanal befinden. Wer Linux-Kenntnisse und einen Root-Server hat wird sich vielleicht auch den Mumble-Server, der übrigens Murmur heißt selbst schnell installieren können.

Was mich besonders begeistert am Mumble ist die Sprachqualität, die eindeutig besser als das ist, was man vom ISDN her kennt. Interessanterweise funktioniert das sogar dann in dieser Qualität, wenn jemand ein Modem benutzt! Das liegt an dem verwendeten Speex-Codec, der obwohl frei verfügbar eine beachtliche Qualität bringt.
tweetbackcheck