maesn
Produkt-Feature

Customisation Handling für alles außerhalb des Modells, weiter innerhalb Ihrer Anbindung

Echte Installationen tragen Dinge, die ein gemeinsames Schema nicht fassen kann. Raw Data liefert die unveränderte Nutzlast neben der normalisierten, Authenticated Passthrough ruft jeden nativen Endpunkt direkt auf, und beide lassen Basis-URL, Zugangsdaten und Mandantenkennungen auf Maesns Seite.

Außerhalb des Modellstrotzdem erreichbar
Ein Feld außerhalb des ModellsrawData
Ein nativer EndpunktpassThrough
Ein eigener ObjekttyppassThrough
maesn hält Sie authentifiziert
Zwei dokumentierte Schalter
GET  /contacts?rawData=true
POST /accounting/passThrough
Diese Software-Teams vertrauen uns
HubSpotTipaltiPaywiseRallyQredNordhealthFindityFintoClockinHEROHolviLanes & PlanesAgicapHubSpotTipaltiPaywiseRallyQredNordhealthFindityFintoClockinHEROHolviLanes & PlanesAgicap
Das Konzept

Was ist Customisation Handling

Ein Common Data Model ist eine Schnittmenge. Es trägt, was Systeme wirklich teilen, und genau das lässt ein Rechnungsobjekt über alle hinweg funktionieren, es kann deshalb nicht tragen, was nur die Installation eines Kunden hat. Das ist keine Lücke im Modell, das ist seine Definition. Jede ernsthafte Anbindung erreicht diesen Moment trotzdem: ein Feld, das jemand vor Jahren ergänzt hat und von dem ein Report abhängt, ein Objekttyp, den der Hersteller nie standardisiert hat, ein nativer Aufruf, der etwas tut, das kein vereinheitlichter Endpunkt bietet.

Customisation Handling ist die Antwort auf diesen Moment, und es gibt genau zwei dokumentierte Mechanismen. Raw Data liest mehr, als das Modell zurückgibt, in der Doku beschrieben als Zugriff auf Daten, die die vereinheitlichten Antworten nicht abdecken. Authenticated Passthrough macht Aufrufe, die die Unified API nicht macht, beschrieben als Aufruf von System-Endpunkten, auch wenn sie nicht ausdrücklich umgesetzt sind. Das eine weitet die Antwort, das andere die Fläche.

Beide sind Notausgänge, und ein Notausgang wird danach beurteilt, was er Sie nachbauen lässt. Diese zwei nehmen die Normalisierung weg und sonst nichts: Die Authentifizierung, die Basis-URL und die Kennungen, die den gemeinten Mandanten benennen, bleiben, wo sie waren. Für ein Feld das Common Data Model zu verlassen heißt deshalb nicht, Maesn zu verlassen, und das Modell bleibt für alles andere in derselben Codebasis der Standardweg.

Das Problem

Der übliche Notausgang wirft Sie auf null zurück

Die meisten Anbindungsebenen bieten einen Weg an sich vorbei. Die Frage ist der Preis, denn sobald Sie den vereinheitlichten Endpunkt verlassen, gehören vier Dinge meist wieder Ihnen.

Die Basis-URL
je Systemje Versionje Installation
Die Zugangsdaten
OAuth-RefreshToken-Speicherungeine zweite Anmeldung
Die Mandantenkennung
realmIdcompanyIdenvironmentName
Das Protokoll
RESTGraphQLSOAP-Umschläge

Keines dieser vier ist für sich schwer. Zusammen sind sie eine zweite Anbindung neben der ersten, und es ist die, die niemand dokumentiert. Die Basis-URL wechselt je System und manchmal je Installation, sie kann also keine Konstante sein. Die Mandantenkennung hat in jedem System einen anderen Namen und eine andere Quelle: eine Realm-ID bei QuickBooks, einen Umgebungsnamen bei Business Central. Und das Protokoll ist nicht einmal immer REST: Manche Systeme antworten in GraphQL, andere sprechen weiterhin SOAP, und beide brauchen Formen, die ein REST-Client nicht erzeugt.

Die Zugangsdaten sind der Posten, der am kleinsten aussieht und am meisten kostet. Sie gehören dem Kunden, und die Access- und Refresh-Token hinter einer Maesn-Verbindung sind für Sie nicht auslesbar, ein Aufruf auf eigene Faust braucht also eine eigene Autorisierung. Derselbe Kunde klickt ein zweites Mal auf Verbinden, meldet sich bei einem System an, das er schon verbunden hat, und unterhält von da an zwei Verbindungen dorthin, eine davon wegen eines einzigen Endpunkts. Diese Token zu speichern und zu erneuern liegt dann ebenfalls bei Ihnen, und das ist die Hälfte dieser Kosten, die üblicherweise genannt wird.

Die nützliche Frage ist deshalb nicht, ob es einen Weg um die Abstraktion herum gibt. Sie lautet, welche Teile davon Sie behalten, wenn Sie einen nutzen, und welchen einen Teil Sie bewusst aufgeben.

Raw Data

Die volle Nutzlast, neben der normalisierten

Ein Query-Parameter an einer GET-Anfrage. Das vereinheitlichte Objekt kommt weiterhin an, und der Satz, wie das System ihn lieferte, kommt daneben an.

Eine Antwort auf GET /contacts?rawData=true
data

Das normalisierte Objekt, auf jedem System gleich.

"id":"123"
"name":"John Doe"
"email":"test@email.com"
rawData

Der Satz, wie das System ihn lieferte, unverändert.

"id":"123"
"name":"John Doe"
"email":"test@email.com"
"extraField":"extra data"

rawData=true zu setzen schaltet die Antwort nicht in einen anderen Modus, es ergänzt sie. Ihr bestehender Code liest data genau wie bisher, und das eine Feld, das Ihnen fehlte, steht daneben in rawData. Das ist der Unterschied zwischen einem Notausgang und einer Abzweigung: Es muss nichts umgeschrieben werden, um zu sehen, was das System tatsächlich gesagt hat.

Das macht es zugleich zu einem Werkzeug fürs Debuggen, dem Einsatz, den niemand einplant und am Ende jeder braucht. Sieht ein Wert in Ihrem Produkt falsch aus, sagen Ihnen beide Hälften derselben Antwort nebeneinander sofort, ob das Quellsystem ihn so gesendet hat oder ob er sich unterwegs geändert hat. Ohne das wird aus derselben Frage ein Supportticket und eine Vermutung.

Es steht auf allen GET-Endpunkten und für alle Zielsysteme bereit, und das heißt auch, dass es sich mit allem verträgt, was diese Endpunkte sonst tun. Weil es dieselbe Anfrage ist, gelten weiterhin dasselbe Filtern, Sortieren und Blättern, Sie können also nach den Änderungen des letzten Tages fragen und bekommen die unveränderte Nutzlast für genau diese Datensätze.

Authenticated Passthrough

Ein Endpunkt, was das System auch spricht

Passthrough ist ein POST /accounting/passThrough mit drei Dingen: dem relativen path, der method und, beim Schreiben, dem body. Alle fünf Methoden sind unterstützt, ein natives Lesen, Anlegen, Ändern oder Löschen ist also derselbe Aufruf mit anderem Verb. Es gibt keine eigenen Zugangsdaten, keinen eigenen Host und keinen zweiten Client einzurichten.

Sehenswert ist, was bei Systemen passiert, die kein REST sprechen. Ein GraphQL-System nimmt gar keinen Pfad, und Ihre Query reist im Rumpf. Ein SOAP-System nimmt ebenfalls keinen Pfad, und Sie senden den Rumpfinhalt base64-kodiert, den Maesn dann in den Umschlag legt, den dieses System erwartet. Drei Transportwelten, von Ihrem Platz aus eine Anfrage.

Was das System spricht
RESTFelder im RumpfPfad + Methode
GraphQLbody.querygar kein Pfad
SOAPbody.xmlbase64, nur Rumpf

Bei SOAP senden Sie nur den Inhalt des body-Elements; der Umschlag, das Access-Token und der Mandantencode werden darum gelegt.

ein passThrough-Aufruf
Was Sie senden
POST /accounting/passThrough

Ein Endpunkt, zwei Header und ein relativer Pfad. Die Transportunterschiede bleiben auf Maesns Seite des Aufrufs.

Das arbeitende Wort im Namen der Funktion ist authenticated. Der Kunde hat sein System einmal über Unified Authentication verbunden, und diese Verbindung trägt auch einen nativen Aufruf. Sie senden Ihre zwei Maesn-Header; das eigene Token des Zielsystems, das Access-Token in einem SOAP-Umschlag und die Kennungen, die ihm den gemeinten Mandanten nennen, kommen auf dieser Seite des Aufrufs dazu.

Das ist der Teil, den ein außen gebauter Aufruf nicht borgen kann. Die Token sind für Sie nicht auslesbar, Ihr eigener Endpunkt braucht also eine eigene Autorisierung, und der Kunde meldet sich ein zweites Mal an, um ein System zu erreichen, das er schon verbunden hat. Passthrough ist der Notausgang, der nie danach fragt: eine Zustimmung, eine Verbindung, und der native Aufruf reist darauf.

Der Tausch

Sie geben die Form auf, nicht die Verbindung

Eine native Antwort kommt in der eigenen Form des Systems an, mit seinen Feldnamen, und die Abbildung dafür liegt bei Ihnen. Alles unterhalb der Form bleibt, wo es war.

Was Sie nicht nachbauen müssen
Die Basis-URLMaesn speichert die Basis-URL jedes Systems und hängt Ihren relativen Pfad an. Sie senden /employees, keine vollständige URL.path
Die ZugangsdatenDer Aufruf trägt dieselben zwei Maesn-Header wie jede andere Anfrage, und das Token des Zielsystems kommt auf unserer Seite dazu.X-API-KEY
Die MandantenkennungWerte, an denen ein System den gemeinten Mandanten erkennt, werden bei der Authentifizierung hinterlegt, sodass ein QuickBooks-Realm oder eine weclapp-ID für Sie eingesetzt wird.realmId
Der SOAP-UmschlagSenden Sie den Rumpfinhalt base64-kodiert, und der Umschlag, das Access-Token und der Mandantencode werden darum gelegt.body.xml
Der GraphQL-EinstiegSysteme, die GraphQL sprechen, nehmen gar keinen Pfad: Die Query reist im Rumpf und erreicht trotzdem den richtigen Endpunkt.body.query

Hier genau zu sein nützt mehr, als Anpassung für umsonst zu versprechen. Was Sie aufgeben, wenn Sie den vereinheitlichten Endpunkt verlassen, ist die Normalisierung: eine Antwortform, ein Satz Feldnamen, ein Weg, jedes System zu lesen. Was Sie behalten, ist alles in der Tabelle darüber, und das ist der Teil, der am längsten zu bauen ist und nie aufhört, Pflege zu brauchen.

Zwei Dinge ändern sich ebenfalls nicht. Ein nativer Aufruf reist auf der eigenen Verbindung des Kunden, er kann also, was diese Verbindung kann, und nicht mehr. Und das eigene Rate-Limit des Zielsystems gilt weiterhin für diesen Verkehr, dieselben publizierten Limits, die Asynchronous Processing je System aufführt, ein Stapel nativer Aufrufe verbraucht also dasselbe Budget wie jede andere Anfrage.

Warum es zählt

Der Sonderfall ist kein zweites Projekt mehr

Selbst gebaut
  • Eine zweite Anbindung für die Sonderfälle
  • Basis-URLs und Token wieder je System
  • Mandantenkennungen von Hand durchreichen
  • SOAP und GraphQL getrennt behandeln
Mit Maesn
  • Ein Schalter für die volle Nutzlast
  • Ein Endpunkt für jeden nativen Aufruf
  • Die Authentifizierung bleibt Maesns Aufgabe
  • Jedes Protokoll hinter einer Anfrage

Integrationsprojekte gehen selten am Standardfall verloren. Sie gehen an dem einen Kunden verloren, dessen Setup nicht Standard ist, denn dort wird aus einer sauberen Abstraktion meist eine direkte Anbindung daneben, mit eigenen Zugangsdaten, eigenem Host und eigenen Fehlern. Bald gibt es je System zwei Anbindungen zu pflegen, und nur eine davon ist dokumentiert.

Mit einem Query-Parameter für die volle Nutzlast und einem Endpunkt für jeden nativen Aufruf bleibt die Ausnahme innerhalb derselben Anbindung. Ihr Kunde bekommt das Feld, nach dem er gefragt hat, und Sie verpflichten sich nicht zu einem parallelen Codepfad, um es zu liefern.

Es gibt einen zweiten Effekt, der in Ihrem eigenen Backlog auftaucht. Ohne Weg am Modell vorbei kommt jede ungewöhnliche Anforderung als Anfrage bei Ihnen an: dieses Feld ergänzen, jenes Objekt freigeben, dieses eine System anders unterstützen. Diese Anfragen sammeln sich schneller an, als sie gebaut werden können, und jede konkurriert mit der Roadmap. Wenn Kunden die Daten selbst erreichen, ist die Anfrage nicht mehr Ihre zu planen, und das ist mehr wert als die Funktion, die sie ersetzt. Eine Roadmap, die keine einmaligen Feldwünsche mehr aufnimmt, ist das Deutlichste, was Produkt- und Entwicklungsteams hier zurückbekommen.

FAQ Customisation Handling

Häufige Fragen

Was ist Authenticated Passthrough?

Ein einzelner Endpunkt, über den Sie ein Zielsystem direkt aufrufen, wenn der gewünschte Aufruf nicht Teil der Unified API ist. Sie senden einen POST an /accounting/passThrough mit dem relativen Pfad, der HTTP-Methode und, beim Schreiben, einem Rumpf. Die Anfrage wird mit Ihren Maesn-Keys authentifiziert und zum System durchgereicht, nichts im System bleibt Ihnen also verschlossen, nur weil Maesn es nicht vereinheitlicht hat.

Was ist Raw Data?

Ein Query-Parameter. Hängen Sie rawData=true an eine GET-Anfrage, und die Antwort behält ihre gewohnte vereinheitlichte Form und trägt die unveränderte Nutzlast des Zielsystems daneben in einem rawData-Feld. Das funktioniert auf allen GET-Endpunkten und für alle Zielsysteme, ein Feld außerhalb des Modells zu erreichen heißt also nie, das Modell für diese Ressource aufzugeben.

Muss ich mich zwischen beiden entscheiden?

Nein, und sie beantworten verschiedene Fragen. Raw Data ist für Lesezugriffe, bei denen das vereinheitlichte Objekt das richtige ist, Sie aber etwas Zusätzliches brauchen, das mitkam. Passthrough ist für Aufrufe, die die Unified API gar nicht macht, sei es ein Endpunkt, ein Objekttyp oder ein Schreibvorgang, den das System auf eigene Weise erledigt.

Können wir Raw Data nutzen, um einen falschen Wert zu untersuchen?

Das ist einer seiner besseren Einsätze. Weil das vereinheitlichte Objekt und die unveränderte Nutzlast in derselben Antwort ankommen, vergleichen Sie beide direkt und sehen, ob eine Abweichung aus dem Quellsystem stammt oder aus der Normalisierung unterwegs. Damit wird aus einer Frage, die sonst ein Supportticket würde, etwas, das Sie mit einer Anfrage selbst beantworten.

Wie hilft uns das als Softwarehersteller, nicht nur unseren Kunden?

Es nimmt Anfragen aus Ihrem Backlog. Ohne Weg am Modell vorbei kommt jede ungewöhnliche Anforderung als Änderungswunsch bei Ihrem Team an: dieses Feld freigeben, jenes Objekt ergänzen, ein System anders behandeln. Die stapeln sich und konkurrieren mit Ihrer Roadmap. Wenn ein Kunde die Daten selbst erreicht, ist der Sonderfall nichts mehr, das Sie einplanen müssen.

Welche HTTP-Methoden unterstützt Passthrough?

GET, POST, PUT, PATCH und DELETE. Für POST, PUT und PATCH ist ein Rumpf nötig, und bei REST-Systemen gehen die Felder direkt in dieses Rumpfobjekt.

Brauche ich die vollständige URL des Zielsystems?

Nein. Sie senden den relativen Pfad, etwa /employees oder /units, und Maesn hängt ihn an die Basis-URL, die es für dieses System hinterlegt hat. Die Dokumentation führt diese Basis-URL je System auf, sodass Sie genau sehen, welchen Teil einer nativen URL Sie weglassen. Ohne den Interactive Authentication Flow erwarten manche Systeme zusätzlich environmentName oder companyId als Query-Parameter.

Was ist mit Systemen, die kein REST sprechen?

Sie laufen über denselben Endpunkt. GraphQL-Systeme nehmen gar keinen Pfad: Ihre Query geht als query-Feld in den Rumpf. SOAP-Systeme nehmen ebenfalls keinen Pfad: Sie senden den Inhalt des body-Elements als base64-kodiertes xml-Feld, und Maesn legt den Umschlag darum, samt Access-Token und Mandantencode.

Ist die Passthrough-Antwort normalisiert?

Nein, und das ist der ehrliche Tausch. Sie bekommen die eigene Antwort des Systems, in seiner Form, mit seinen Feldnamen, das Mapping liegt also bei Ihnen. Was Sie behalten, ist alles unterhalb der Form: ein Endpunkt, Ihre Maesn-Header, die hinterlegte Basis-URL, die Mandantenkennungen und das Protokoll-Drumherum.

Gibt es systemspezifische Eigenheiten, die ich kennen sollte?

Einige, und sie sind je System dokumentiert. BuchhaltungsButler nimmt auch beim Lesen nur POST-Anfragen an, mit dem Vorgang im Pfad. Moneybird erwartet den Pfad in einer Notation aus Ressource und Format. QuickBooks-Realm-IDs sowie die Kennungen von weclapp und Xentral werden bei der Authentifizierung des Kunden hinterlegt, Sie übergeben sie also nie selbst.

Gelten die Rate-Limits des Zielsystems weiterhin?

Ja. Ein nativer Aufruf über Passthrough ist weiterhin Verkehr, der bei diesem System ankommt, und seine eigenen Limits gelten dafür wie für jede andere Anfrage. Das publizierte Limit jedes verbundenen Systems ist dokumentiert, Sie können also abschätzen, wie viel davon ein Stapel nativer Aufrufe verbraucht.

Einmal bauen, auf der Unified API.

Sehen Sie, wie Customisation Handling für Ihre Integration funktioniert, oder steigen Sie in die technische Referenz ein.