Individualisierte Touch Points im Web mit Single Page-Anwendungen

Der Digitalisierungstrend umfasst, neben der klassischen Automatisierung durch Software, vor allem auch die Bereitstellung von zielgruppengerechten, digitalen Touch Points, idealerweise in Form von Web-Anwendungen.
Diese Web-Anwendungen sollen für Kunden, Partner und weitere Interessengruppen pro Kanal nicht nur individuelle Funktionen anbieten sondern die Funktionalität auch in attraktiver Art und Weise präsentieren. Eine herausragende Usability soll die Bedürfnisse der Zielgruppen möglichst gut erfüllen damit die Kanäle effektiv genutzt werden und gleichzeitig das Branding unterstützt wird.

Was ist eine Single Page (Web) Application?

Für die Entwicklung solcher Web-Anwendungen hat sich in letzter Zeit ein Ansatz namens «Single Page (Web) Application» (SPA) verbreitet. Wie der Name sagt, besteht der Ansatz einer SPA darin, dass auf einer klassische Webseite eine komplette Web-Anwendung eingebettet ist, welche nach dem Laden der Seite im Internet Browser des Anwenders ausgeführt wird. Um solche Single Page Applications zu entwickeln, haben sich mehrere Frameworks etabliert, darunter AngularJS, das von Google stammt. Das «JS» im Namen steht dabei für JavaScript – eine standardisierte Programmiersprache, die von allen gängigen Browsern unterstützt wird und neben HTML und CSS das Fundament für SPA legt. Im Unterschied zu früheren Ansätzen wie z.B. das ehemals populäre Flash benötigen SPA auf Basis von JavaScript keine Browser Extensions.

Wann macht eine Single Page Application Sinn?

Der Clou einer Single Page Application liegt darin, dass die Anwendung im Hintergrund, also für den Anwender nicht direkt sichtbar, mit Server-Systemen kommuniziert, um Daten auszutauschen oder Services aufzurufen. Der Vorteil davon liegt in einer stark verbesserten User Experience, indem Interaktionen flüssig und ohne ständiges Laden von neuen Seiten erfolgen, das Verhalten also dem einer lokal installierten Desktop-Anwendung entspricht.

Single Page Applications setzen natürlich voraus, dass auf Server-Seite geeignete Schnittstellen («API») vorhanden sind, d.h. eine SPA muss im Zusammenspiel mit den Backend-Systemen entwickelt werden.

Ein möglicher Nachteil von Single Page Web Applications liegt darin, dass die Such­maschinen­optimierung erschwert wird, da die Indexierung der Suchmaschinen auf (einzelnen) Seiten mit eindeutigen URLs basiert. Je nach Relevanz von SEO im konkreten Anwendungsfall müssen unter Umständen zusätzliche technische Massnahmen (wie z.B. «Prerendering») vorgesehen werden, um diese Problematik zu lösen. Gut zu wissen ist, dass Google und die anderen Suchmaschinen ständig Verbesserungen hinsichtlich SEO von SPA vornehmen, wobei Google auch AngularJS beeinflussen kann.

Beispiel: eCommerce MyAccount als Single Page App mit AngularJS

Für Tailored-Fits, ein Startup im Umfeld der additiven Fertigung, das auf Basis von 3D-Fuss-Scans massgeschneiderte Sohlen und Schuhe produziert, haben wir ein individuelles eCommerce-System entwickelt. Dieses beinhaltet Touch Points sowohl für die Tailored-Fits-Partner als auch für die Endkunden. Weitere Details können in der Referenz nachgelesen werden. Die Endkunden erhalten mit ihrer ersten Bestellung ein Login für das Portal von Tailored-Fits und können in ihrem Konto («My Account») die Entstehung ihres massgeschneiderten Produkts direkt mitverfolgen, inklusive einer 3D-Vorschau des zu produzierenden Produkts. Im «My Account» werden auch die typischen Use Cases unterstützt mit Update des eigenen Profils und allem, was dazu gehört, sowie der kompletten Bestellhistorie. Im nächsten Schritt ist auch vorgesehen, dass Kunden mit den vorhandenen Fuss-Scans in ihrem Konto direkt neue Bestellungen aufgeben können.

Das gesamte «My Account» wurde auf Basis von AngularJS umgesetzt. Besondere Herausforderungen waren dabei die Integration der SPA in das CMS sowie die durchgängige Mehrsprachigkeit. Besondere Beachtung galt auch der strikten Zugriffskontrolle auf das «My Account», da mit dem dort zugänglichen persönlichen Fuss-Scan recht sensible Informationen hinterlegt sind.

Die MyAccount-SPA interagiert über ein REST-basiertes API mit dem eCommerce-Portal, welches auf Basis von Laravel, einem modernen Application Framework auf Basis von PHP, entwickelt wurde. API-Aufrufe via REST werden durch AngularJS besonders unterstützt, so dass der nötige Code dafür schlank und elegant ausfällt.

Beispiel: Der «Login Service» in Form eines AngularJS-Service:

authModule.factory('LoginService', ['API_DEFAULT', 'MYACCOUNT_DEFAULT', '$log', '$rootScope', '$http', 'AuthService', '$q', function (API_DEFAULT, MYACCOUNT_DEFAULT, $log, $rootScope, $http, AuthService, $q) {

    var loginServiceInstance = {
        login: function (iEmail, iPwd) {
            $log.debug('LoginService::login>> email, pwd ', iEmail, iPwd);
            var deferred = $q.defer();

            $http.post(API_DEFAULT.api_endpoint + "customers/login", {
                email: iEmail,
                password: iPwd
            })
                .then(function (result) {
                    var data = result.data.data;

                    var customer = {
                        ID: data.customer_id,
                        token: data.token,
                        name: data.firstname + ' ' + data.lastname
                     };
                    $log.debug("LoginService>>got customer:", customer);
                    if (customer.token) {
                        AuthService.saveUser(customer);
                        // Cookie for CMS
                         rightNow = new Date();
                        $rootScope.username = AuthService.getUserName();
                        deferred.resolve(true);
                    } else {
                        AuthService.clearUser();
                        deferred.resolve(false);
                    }

                })
                .catch(function (reason) {
                    $log.error(reason);
                    deferred.resolve(false);
                })
                .finally(function () {
                    // Gets executed no matter what
                 });

            return deferred.promise;
        },

        logout: function () {
            AuthService.clearUser();
            $rootScope.username = null;
            return true;
        }
    };

    return loginServiceInstance;
}]);

Die Integration der MyAccount-App in das CMS – in diesem Fall WordPress – wurde über ein entsprechendes Child Theme sowie ein spezifisches Seiten-Template gelöst. Damit wird erreicht, dass die AngularJS-App nur dann geladen wird, wenn ein Website-Besucher die MyAccount-Seite aufruft, und gleichzeitig über ein gemeinsames Cookie die aktuelle Sprache an die SPA weiter gegeben werden kann. Damit wird auch ein Sprachwechsel während der Ausführung der Anwendung ermöglicht. Als weiteres Feature wird auf allen CMS-Seiten angezeigt, ob man im «My Account» eingeloggt ist, und zwar indem dynamisch der eigene Name eingeblendet wird statt des «My Account»-Links. Auch dies wird im Child Theme in Kombination mit einem weiteren Cookie gelöst.

Eine Herausforderung für Single Page Apps ist das korrekte Verhalten beim Navigieren mittels Browser Buttons. Da die Anwender im Falle einer SPA immer auf derselben Seite bleiben, passt das klassische Vor- und Zurück-Navigieren, das man vom Browser her gewohnt ist, nicht ins Konzept. Damit man dadurch nicht den in der Anwendung vorgesehenen Ablauf durcheinander bringt oder bewusst umgehen kann, muss der Flow in der Anwendung strikt kontrolliert werden. Dazu gibt es in AngularJS eine Extension namens UI-Router, mit der die nötigen Schritte im Ablauf gesteuert werden können.
Folgender Ausschnitt zeigt beispielhaft, wie States und Sub-States deklarativ definiert und mit dem jeweiligen Controller, der die Logik steuert, verknüpft werden können (vgl. «myaccount» mit Profile, Orders und OrderDetails):

Beispiel: Deklarative Definition von States und Sub-States und Steuerung und Verknüpfung der Logik mit dem jeweiligen Controller

$stateProvider
     .state('login', {
         url: '/login',
         templateUrl: '/my-account/app/views/login.html',
         controller: 'UserLoginController',
         data: {
             authRequired: false
         }
     })
    // ....

     .state('myaccount', {
         abstract: true,
         url: '/myAccount',
         template: '<div ui-view/>',
         data: {
             authRequired: true
         }
     })
     .state('myaccount.profile', {
         url: '/profile',
         templateUrl: '/my-account/app/views/myAccount.html',
         controller: 'AccountViewController'
     })
     .state('myaccount.orders', {
         url: '/orders',
         templateUrl: '/my-account/app/views/orderList.html',
         controller: 'OrderListController'
     })
     .state('myaccount.orderdetails', {
         url: '/orderDetails/:id',
         templateUrl: '/my-account/app/views/orderDetails.html',
         controller: 'OrderViewController'
     });
 $urlRouterProvider
     .otherwise('/login');

In dieselbe Kategorie wie das Navigieren fällt das komplette Neuladen der Seite (Shift-Refresh im Browser), das grundsätzlich jederzeit möglich ist. Wenn eine Anwenderin die Webseite mit der SPA neu lädt, während sie in der Anwendung drin ist, wird nicht nur die Seite neu geholt sondern auch die eingebettete SPA neu geladen und initialisiert. Um zu vermeiden, dass dabei der vorherige Stand verloren geht oder gar ein erneutes Login notwendig wird, wurde ein Mechanismus entwickelt, der unter Zuhilfenahme des Local Storage im Browser eine temporäre Session implementiert. Damit wird gesteuert, ob nach einem Reload der Seite ein Login nötig ist oder ob eine vorhandene, gültige Session wieder aufgenommen wird.

Single Page Apps entwickeln sich rasant weiter, sind aber keine Allzweckwaffe

Wie bei Software-Anwendungen generell müssen Single Page Apps regelmässig nachgezogen werden, um mit neuen Browser-Versionen und der verwendeten Frameworks Schritt zu halten zu können. Die Dynamik im Umfeld der JavaScript-Frameworks für Singe Page Apps ist besonders hoch, und sowohl Angular als auch dessen Konkurrenten entwickeln sich in grossen Schritten weiter. Leider fällt dieser Innovationsfreude regelmässig die Rückwärtskompatibilität zum Opfer. Upgrades auf neuere Major-Versionen bedingen Code-Anpassungen. Angular steht inzwischen bei Version 5 und 6 steht schon vor der Tür. Das «JS» ist aus dem Namen verschwunden, da man für die Zukunft auf TypeScript setzt, eine ausgereiftere Script Language, die nach JavaScript kompiliert wird.
Mit Version 5 unterstützt Angular neu sogenannte Progressive Web Apps (PWA). Dahinter versteckt sich nichts anderers als eine Single Page App, die mit der Situation umgehen kann, dass zeitweise keine Internet-Verbindung vorhanden ist, um Daten vom Server zu holen. Ein Beispiel dafür ist eine Support-Anwendung für einen Servicetechniker oder Lagermitarbeiter, die auch im Untergeschoss eines Gebäudes funktionieren muss. Ein anderes Beispiel ist eine eCommerce App, die unabhängig von der Netzverbindung das Browsen und, wie von Amazon umgesetzt, sogar einen Offliine-Checkout mit nachträglicher Validierung unterstützt. Die Voraussetzung dafür, eine SPA in eine PWA zu verwandeln, ist Caching. D.h. Daten werden vorab geladen, wenn eine Internet-Verbindung besteht, und zwischengespeichert. Sogenannte ServiceWorker, die man nach den jeweiligen Bedürfnissen konfigurieren kann, übernehmen dabei diese Aufgabe. Natürlich stösst man auch mit raffiniertem Caching an Grenzen, wenn Daten nachgeladen oder an den Server zur Ablage übermittelt werden müssen.
Auch wenn Single Page Apps zur Zeit im Trend liegen und spezifische Use Cases lösen, sind sie nicht in jedem Fall die ideale Lösung. SPA sind dort sinnvoll, wo den Benutzern vielschichtige Interaktionen mit einer erstklassigen User Experience zur Verfügung gestellt werden sollen. Die Implementation einer solchen Applikation setzt aber ein sorgfältiges Design und eine saubere Umsetzung voraus damit die oben aufgezeigten Aspekte wie Ablaufsteuerung, Mehrsprachigkeit, Sicherheit und Benutzerfreundlichkeit adressiert werden und die anvisierte Kundenzufriedenheit am Ende tatsächlich erreicht wird.

Weitere Infos zu Angular

Wer mehr erfahren möchte zu den technischen Aspekten von AngularJS, findet vertiefende Infos unter:

https://angularjs.org

https://angular.io

https://angular-university.io