Reverse Routing in Polymer Apps


Thu 29 September 2016 Von André Justo

Wie Sie vielleicht wissen, haben wir vor Kurzem die erste Vorabversion der neuen Web UI vorgestellt, die mit Polymer erstellt wurde. Als wir mit der Entwicklung begannen, haben wir das Polymer Starter Kit als Ausgangspunkt unserer Anwendung verwendet. Momentan verwendet dieses Kit die aktuellen Routing-Elemente (app-route und app-location), um das Routing der Anwendung zu übernehmen. Zu Beginn der Entwicklung wurde diese Aufgabe noch an page.js übertragen, und diese Lösung nutzen wir weiterhin in unserer Anwendung.

Das Erstellen großer und inhaltsreicher Plattformen wie der Nuxeo Platform setzt die Einhaltung bewährter Praktiken voraus, um eine gute Nutzbarkeit bei der Verwendung einer Webanwendung zu erreichen. Heute konzentrieren wir uns auf die Erstellung von URLs.

URLs spielen eine große Rolle bei der Navigation von Anwendungen, da sie Benutzern ermöglichen, schnell zu einer bestimmten Seite zu navigieren, sie mit einem Kollegen zu teilen oder ein Lesezeichen als Referenz zu setzen. Das Bereitstellen von Links in einer Webanwendung ist normalerweise sehr einfach. Wir müssen lediglich ein Tag-Paar hinzufügen und sind fertig.

<a href="/home">Startseite</a>

Wir dürfen dabei nicht vergessen, dass wir mit Polymer und Web-Komponenten im Allgemeinen arbeiten, und diese darauf ausgelegt sind, Kapselung, Komposition und Trennung der Belange zu ermöglichen. Zudem kann jedes Element in völlig verschiedenen Apps oder Zusammenhängen mit eigenem Routing-Ansatz verwendet werden oder möglicherweise überhaupt keine Links erfordern.

Ein weiteres potentielles Problem in riesigen Anwendungen sind zu viele fest programmierte Links, die über verschiedene Stellen verteilt sind und Probleme bei der Wartung oder Refaktorierung bereiten können.

Vor diesem Hintergrund müssen wir die Elemente so gestalten, dass diese wissen, wie sie eine URL für eine bestimmte Route erzeugen. Dieser Prozess wird auch als Reverse Routing bezeichnet.

Die Lösung

Bevor wir zur Programmierung kommen, möchten wir darauf hinweisen, dass diese Lösung nicht von einer bestimmten Client-Routing-Bibliothek abhängig ist. In unseren Beispielen verwenden wir page.js, weil dies die Bibliothek ist, die wir momentan verwenden.

Beginnen wir damit, einige Beispiel-Routen für unsere Anwendung zu definieren:

 page('/home', function() {
   // home page route
 });

 page('/document/:id, function() {
   // route for a specific document
 });

 page('/admin/user-group-management/:type/:id, function() {
   // route to manage a user or a group
 });

Wie Sie sehen können, ist das Erstellen von Routen mit page.js relativ einfach: Sie müssen lediglich die Pfade, die vom Router verarbeitet werden, und bei Bedarf eine Callback-Funktion festlegen, die die gewünschten Aufgaben übernimmt - all dies ist bereits bekannt. Nachdem wir unsere Routes festgelegt haben, müssen wir lediglich ‚<a> Tags mit dem korrekten href-Attribut in unseren Elementen hinzufügen, um Links auf unsere Seiten zu erstellen. Während die Startseiten-Route ein-oder zweimal in einer Anwendung verwendet wird, erscheinen URLs zu Dokumenten oder Benutzern/Gruppen mehrmals in verschiedenen Elementen (Verzeichnissen, Suchen und so weiter) - und genau dann ist unsere Lösung hilfreich.

Wir haben ein Polymer-Verhalten mit dem Namen ‚Nuxeo.RoutingBehavior erstellt, das die funktionsartigen Eigenschaft ‚urlFor bereitstellt, die für die Erstellung einer URL für eine vorgegeben Route verwendet werden sollte.

Jedes Element mit diesem Verhalten kann jetzt passende URLs erstellen:

<a href$="[[urlFor('document', document.uid)]]">My document</a>

Bitte beachten Sie, dass wir unseren Routes Namen geben, und nicht die URL selbst fest programmieren. Dadurch bleiben unsere Elemente flexibel und wir können ihnen verschiedene URLs zuordnen, falls ein Element in unterschiedlichen Anwendungen verwendet wird. Beispielsweise könnte die URL für die Dokumentseite in Anwendung A ‚/my-document/:id lauten, während die URL in Anwendung B /document-page/:id lautet.

Werfen wir einen Blick darauf, was sich im Hintergrund abspielt: Die Funktion ‚urlFor zieht den Namen der Route und andere Parameter hinzu, um die URL zu erstellen.

Nuxeo.RoutingBehavior = {
  properties: {
    urlFor: {
      type: Function,
      notify: true,
      value: function() {
        return this.generateUrl;
      }
    }
  },

  generateUrl: function() {
    if (this.router) {
      var route = arguments[0];
      if (route.startsWith('/')) {
        return this.baseUrl + route;
      }
      if (!this.router[route]) {
        console.error('Could not generate a url for route ' + route);
        return;
      }
      var params = Array.prototype.slice.call(arguments, 1);
      return this.router[route].apply(this, params);
    }
  }
}

Bei näherer Betrachtung können Sie sehen, dass das Objekt ‚router mehrmals verwendet wurde. Dieses Objekt enthält unsere mit Namen versehenen Reverse Route Handler und seine Verwendung als Eigenschaft ermöglicht es, einfach einen benutzerdefinierten Router für Ihre Elemente festzulegen. Im Kontext einer Anwendung möchten wir, dass alle für die Route aktivierten Elemente die gleichen Routen teilen, damit wir mithilfe von Events eine Aktualisierung auslösen können, wenn unsere Routes (neu) definiert werden, wie wir dies mit unserem i18n helper gemacht haben. Oder wir fügen sie allen Polymer-Elementen mit folgendem Code hinzu:

Polymer.Base._addFeature({
  router: {
    home: function() {
      // returns url for homepage
      return page.url('/home');
    },
    document: function(id) {
      // returns url for a document page
  return page.url('/document/' + id);
    }
  }
});

Für jede in der Anwendung festgelegte Route müssen wir die Funktion (die im Router-Objekt gespeichert ist) implementieren, die für die Erstellung der URL dieser Route verantwortlich ist. Dies sollte alles kein Problem sein und ist langfristig nützlich, wenn Sie etwa einige der URLs Ihrer Anwendung nur leicht verändern müssen.

Das war's auch schon! page.js übernimmt das Routing in der Anwendung und mit Hilfe unseres Verhaltens können wir unseren Elementen Links entkoppelt hinzufügen.

Sehen Sie sich unseren Elemente-Katalog an, um mehr über die Elemente zu erfahren und uns Ihre Meinung darüber mitzuteilen!


Etikettiert: Polymer, How to, Nuxeo-Platform