GraphQL und REST als Hybrid-API: Wann beide Protokolle nebeneinander sinnvoll sind
AI generated
{ }
GET
REST · GraphQL · API-Architektur
GraphQL und REST als Hybrid-API
Wann sich eine Kombination aus beiden Protokollen lohnt, statt komplett zu migrieren

Die Diskussion um GraphQL und REST wird oft als Entweder-oder geführt, dabei schließen sich beide Protokolle in der Praxis nicht aus. REST bleibt für einfache CRUD-Ressourcen und Webhooks die pragmatische Wahl, GraphQL spielt seine Stärken bei komplexen, aggregierenden Leseoperationen im Frontend aus. Dieser Artikel zeigt, wie eine hybride Architektur mit gemeinsamer Backend-Logik konkret aussieht, was sie an Team- und Tooling-Aufwand kostet und wann sich die zusätzliche Komplexität schlicht nicht lohnt.

15 Min. Lesezeit GraphQL · REST Hybrid-Architektur

1. Warum die Wahl selten ein Entweder-oder ist

Die Diskussion um GraphQL und REST wird in vielen Teams als Grundsatzentscheidung geführt, bei der ein Protokoll das andere vollständig ablösen soll. In der Praxis zeigt sich jedoch regelmäßig, dass diese Entweder-oder-Haltung an den tatsächlichen Anforderungen vorbeigeht, weil beide Protokolle für unterschiedliche Zugriffsmuster unterschiedlich gut geeignet sind. Ein Team, das GraphQL ausschließlich einführt, um ein bestehendes REST-Backend zu ersetzen, überträgt oft Probleme, die REST gar nicht hatte, in eine neue, komplexere Schicht.

Sinnvoller ist es, GraphQL dort einzusetzen, wo es seine Stärken tatsächlich ausspielt, und REST dort zu belassen, wo es bereits gut funktioniert. Diese hybride Denkweise verlangt zwar eine bewusste Architekturentscheidung und etwas mehr Abstimmungsaufwand im Team, vermeidet aber die Kosten einer kompletten Migration, deren Nutzen in vielen Projekten den Aufwand gar nicht rechtfertigt. Der Rest dieses Artikels beschreibt, wie eine solche Aufteilung in der Praxis aussieht und wo ihre Grenzen liegen.

2. Typische Aufteilung: REST für CRUD, GraphQL für aggregierende Leseoperationen

Eine bewährte Aufteilung ordnet REST die einfachen CRUD-Ressourcen zu, also das Anlegen, Lesen, Aktualisieren und Löschen einzelner, klar abgegrenzter Entitäten wie Bestellungen, Kunden oder Produkte. Für diese Operationen bietet REST mit seinen etablierten HTTP-Methoden, Statuscodes und der einfachen Testbarkeit über curl oder Postman einen unmittelbaren Vorteil, ohne dass ein zusätzliches Abfrageschema notwendig wäre. Auch Webhooks, also ausgehende Benachrichtigungen an externe Systeme bei Ereignissen, passen strukturell besser zu REST, weil sie im Kern einfache, einzelne POST-Requests mit einem festen Payload-Format sind.

GraphQL entfaltet seinen Vorteil dagegen bei komplexen, aggregierenden Leseoperationen im Frontend, bei denen eine einzelne Ansicht Daten aus mehreren, tief verschachtelten Ressourcen benötigt. Eine Produktdetailseite, die gleichzeitig Preisdaten, Lagerbestand, Bewertungen und verwandte Produkte anzeigen soll, würde mit REST mehrere separate Requests erfordern oder einen speziell zugeschnittenen Endpunkt, während GraphQL genau diese Kombination in einer einzigen Anfrage erlaubt. Für Frontend-Teams, die häufig neue Ansichten mit wechselnden Datenkombinationen bauen, reduziert das den Abstimmungsaufwand mit dem Backend-Team spürbar.

3. Gemeinsame Backend-Logik hinter beiden Schnittstellen

Damit die Einführung von GraphQL neben REST nicht zu doppelt gepflegter Geschäftslogik führt, sollte die eigentliche Domänenlogik in einer gemeinsamen Service-Schicht liegen, auf die sowohl REST-Controller als auch GraphQL-Resolver zugreifen. In einer Symfony-Anwendung bedeutet das konkret, dass ein Anwendungsfall wie das Abrufen einer Bestellung als eigenständiger Service implementiert wird, der weder von der HTTP-Schicht noch vom GraphQL-Schema abhängt.

Dieses Muster verhindert, dass Validierungsregeln, Berechtigungsprüfungen oder Berechnungslogik zweimal implementiert werden und in der Folge auseinanderlaufen. Der REST-Controller und der GraphQL-Resolver werden dadurch zu dünnen Adapterschichten, die lediglich zwischen dem jeweiligen Protokollformat und der gemeinsamen Domänenschicht übersetzen, was auch das Testen erheblich vereinfacht, weil die eigentliche Logik unabhängig vom Transportprotokoll getestet werden kann.


<?php
declare(strict_types=1);

namespace App\Order\Application;

final class GetOrderService
{
    public function __construct(
        private readonly OrderRepositoryInterface $orderRepository,
    ) {
    }

    /**
     * Lädt eine Bestellung anhand ihrer ID.
     * Wird sowohl vom REST Controller als auch vom GraphQL Resolver genutzt.
     */
    public function execute(string $orderId): Order
    {
        $order = $this->orderRepository->findById($orderId);

        if ($order === null) {
            throw new OrderNotFoundException($orderId);
        }

        return $order;
    }
}

// REST Controller (dünner Adapter)
final class OrderController
{
    public function __construct(private readonly GetOrderService $getOrderService)
    {
    }

    public function show(string $orderId): JsonResponse
    {
        $order = $this->getOrderService->execute($orderId);

        return new JsonResponse(OrderNormalizer::normalize($order));
    }
}

// GraphQL Resolver (dünner Adapter, gleiche Service Schicht)
final class OrderResolver
{
    public function __construct(private readonly GetOrderService $getOrderService)
    {
    }

    public function resolveOrder(string $orderId): Order
    {
        return $this->getOrderService->execute($orderId);
    }
}

4. Team- und Tooling-Kosten einer Zwei-Protokoll-Strategie

Der Preis einer Zwei-Protokoll-Strategie zeigt sich selten sofort, sondern erst über die Zeit im laufenden Betrieb. Zwei Schnittstellen bedeuten zwei Sätze an Dokumentation, die synchron gehalten werden müssen, zwei unterschiedliche Testansätze (Contract-Tests für REST, Schema-Validierung und Query-Tests für GraphQL) und zwei Monitoring-Strategien, weil sich Fehlerraten und Latenzen bei GraphQL nicht mehr sauber pro Endpunkt, sondern pro Feld oder Resolver messen lassen.

Auch das Team selbst muss beide Denkweisen beherrschen: REST-Ressourcenmodellierung folgt anderen Prinzipien als GraphQL-Schema-Design mit Typen, Interfaces und Resolvern, und nicht jeder Entwickler bringt beides gleich gut mit. Kleinere Teams unterschätzen häufig, wie viel zusätzliche Abstimmung nötig ist, um zu entscheiden, welche neue Anforderung über welches Protokoll umgesetzt wird, bevor sich diese Entscheidung als Team-Konvention etabliert hat.

5. Caching-Verhalten: HTTP-Caching versus Query-spezifisches Caching

REST profitiert direkt von HTTP-Caching-Mechanismen wie ETag, Last-Modified und Cache-Control-Headern, die von Browsern, CDNs und Reverse-Proxys wie Varnish ohne zusätzliche Konfiguration verstanden werden. Ein GET-Request auf eine Produktressource lässt sich dadurch mit vergleichsweise geringem Aufwand cachen, weil die URL selbst eindeutig identifiziert, welche Ressource gemeint ist.

GraphQL erschwert dieses Muster strukturell, weil praktisch alle Anfragen über denselben Endpunkt per POST laufen und der eigentliche Inhalt der Anfrage im Request-Body steckt, den HTTP-Caches standardmäßig nicht auswerten. Caching muss deshalb entweder auf Anwendungsebene mit einem Persisted-Queries-Mechanismus oder einem GraphQL-spezifischen Cache wie Apollo Server Cache-Control-Direktiven nachgebaut werden, was zusätzliche Infrastruktur und zusätzliches Know-how im Team voraussetzt.

6. Versionierung und Schema-Evolution im Vergleich

REST-APIs werden traditionell über URL-Präfixe oder Header versioniert, etwa /v1/orders und /v2/orders, wenn sich das Ressourcenformat inkompatibel ändert. Diese Versionierung ist explizit sichtbar, erfordert aber, dass alte Versionen parallel gepflegt werden, solange noch Konsumenten darauf zugreifen.

GraphQL verfolgt bewusst einen anderen Ansatz: Statt expliziter Versionen wird das Schema evolutionär erweitert, neue Felder kommen hinzu, veraltete Felder werden mit einem @deprecated-Hinweis markiert, aber nicht sofort entfernt. Das funktioniert gut, solange Breaking Changes tatsächlich vermieden werden, verlangt aber Disziplin bei der Schema-Pflege, weil sich veraltete Felder in der Praxis oft länger halten, als ursprünglich geplant war.

7. Sicherheitsaspekte: Rate-Limiting und Query-Komplexität

Bei REST lässt sich Rate-Limiting vergleichsweise einfach pro Endpunkt und HTTP-Methode konfigurieren, weil jede Ressource und jede Operation eine eigene, klar identifizierbare URL hat. Ein API-Gateway kann dadurch granular steuern, wie oft ein Client bestimmte Operationen aufrufen darf.

GraphQL braucht hier einen anderen Schutzmechanismus, weil eine einzelne Anfrage durch tiefe Verschachtelung theoretisch beliebig teuer für das Backend werden kann, selbst wenn sie technisch nur ein einziger Request ist. Üblich sind deshalb Query-Complexity-Analysen, die jeder Anfrage vor der Ausführung einen Kostenwert zuweisen, und eine maximale Verschachtelungstiefe, die im Schema oder in der Middleware durchgesetzt wird, um übermäßig teure Anfragen von vornherein abzulehnen.

8. Wann sich die zusätzliche Komplexität nicht lohnt

Nicht jedes Projekt profitiert von einer Hybrid-Strategie. Bei einer überschaubaren Domäne mit wenigen, klar abgegrenzten Ressourcen und einem einzigen Frontend-Team, das die API konsumiert, rechtfertigt der Zusatzaufwand einer zweiten Schnittstelle in den meisten Fällen den Nutzen nicht. Der zusätzliche Betriebs-, Test- und Dokumentationsaufwand für GraphQL lohnt sich vor allem dann, wenn tatsächlich mehrere Frontend-Teams mit unterschiedlichen, sich häufig ändernden Datenanforderungen gegen dieselbe API arbeiten.

Auch kleine Teams ohne dedizierte Erfahrung mit GraphQL-Schema-Design sollten die Einführung kritisch hinterfragen, denn ein schlecht entworfenes GraphQL-Schema mit N+1-Problemen und fehlender Query-Complexity-Kontrolle kann mehr Probleme verursachen, als es löst. In solchen Fällen ist ein gut modelliertes REST-API mit gezielten, auf die Frontend-Bedürfnisse zugeschnittenen Aggregations-Endpunkten häufig die pragmatischere und wartungsärmere Lösung.

9. Entscheidungshilfe für die eigene Architektur

Die folgende Tabelle fasst die zentralen Entscheidungskriterien zusammen, um im konkreten Projekt schneller abzuwägen, ob und in welchem Umfang sich eine Hybrid-Strategie aus REST und GraphQL lohnt.

Kriterium REST GraphQL Empfehlung
Ressourcen-Caching Einfach über HTTP-Header Erfordert zusätzliche Infrastruktur REST für stark gecachte Leseressourcen
Aggregierende Leseabfragen Mehrere Requests nötig Eine Anfrage für verschachtelte Daten GraphQL für komplexe Frontend-Views
Webhooks und Events Natives Muster Unüblich, kein Standard REST für ausgehende Benachrichtigungen
Schutz vor teuren Anfragen Pro Endpunkt/Rate-Limit Query-Complexity-Analyse nötig Zusätzlichen Aufwand bei GraphQL einplanen
Team-Einarbeitung Breit bekannt Eigenes Schema-Denken nötig GraphQL nur bei tatsächlichem Bedarf einführen

Mironsoft

OpenAPI-Design, Symfony-APIs und API-Sicherheit

APIs, die externe Teams ohne Rückfragen integrieren können?

Wir prüfen bestehende REST-APIs auf inkonsistente Fehlerformate, fehlende OpenAPI-Dokumentation und Sicherheitslücken und bauen daraus eine API, die klar dokumentiert, versioniert und gegen Missbrauch abgesichert ist.

API-Review

OpenAPI-Spezifikation, Fehlerformate und Statuscodes auf Konsistenz prüfen.

Symfony-Umsetzung

DTOs, Serializer und Validator für saubere, typsichere Request/Response-Modelle einsetzen.

Security-Audit

Rate-Limiting, Auth-Schemes und Input-Validierung gegen echte Angriffsflächen absichern.

10. Zusammenfassung

GraphQL und REST Hybrid: Das Wichtigste auf einen Blick

Kernidee

GraphQL und REST schließen sich nicht aus, sie decken unterschiedliche Zugriffsmuster ab und lassen sich hinter derselben Backend-Logik kombinieren.

Typische Aufteilung

REST für CRUD-Ressourcen und Webhooks, GraphQL für komplexe, aggregierende Leseoperationen im Frontend.

Größter Kostenfaktor

Doppelte Dokumentation, doppeltes Testing und ein Team, das beide Denkweisen gleichzeitig beherrschen muss.

Wann es sich nicht lohnt

Bei kleinen Domänen mit einem einzigen Frontend-Team ist ein gut modelliertes REST-API meist die einfachere Wahl.

11. FAQ: GraphQL und REST Hybrid: Das Wichtigste auf einen Blick

1Ersetzt GraphQL REST komplett?
Nein, in den meisten produktiven Setups ergänzen sich beide Protokolle. REST bleibt für einfache CRUD-Ressourcen und Webhooks sinnvoll, GraphQL übernimmt komplexe, aggregierende Leseoperationen im Frontend.
2Muss ich mein bestehendes REST-Backend für GraphQL umbauen?
Nicht grundsätzlich. Wenn die Geschäftslogik bereits in einer eigenen Service-Schicht liegt, kann ein GraphQL-Resolver diese Schicht direkt wiederverwenden, ohne die REST-Endpunkte zu verändern.
3Wie cache ich GraphQL-Antworten, wenn HTTP-Caching nicht funktioniert?
Üblich sind Persisted Queries, anwendungsseitiges Caching auf Feldebene oder ein GraphQL-spezifischer Cache-Layer wie Apollo Server Cache-Control. Diese Mechanismen ersetzen das fehlende native HTTP-Caching.
4Braucht GraphQL zwingend eine eigene Versionierung?
Nein, GraphQL setzt stattdessen auf schrittweise Schema-Evolution mit deprecated-Markierungen statt expliziter Versionsnummern. Das erfordert aber Disziplin, damit veraltete Felder nicht unbegrenzt bestehen bleiben.
5Wie schütze ich GraphQL vor teuren, tief verschachtelten Anfragen?
Mit einer Query-Complexity-Analyse, die jeder Anfrage vor der Ausführung einen Kostenwert zuweist, und einer maximalen Verschachtelungstiefe, die im Schema oder in der Middleware durchgesetzt wird.
6Lohnt sich GraphQL für ein kleines Team mit nur einer Frontend-Anwendung?
In den meisten Fällen nicht. Der zusätzliche Betriebs- und Lernaufwand rechtfertigt sich vor allem dann, wenn mehrere Frontend-Teams mit unterschiedlichen, sich häufig ändernden Datenanforderungen arbeiten.
7Kann ich Webhooks auch über GraphQL abbilden?
Technisch möglich über GraphQL-Subscriptions, aber unüblich. Webhooks sind im Kern einfache, einzelne POST-Requests, wofür REST das etabliertere und einfacher zu integrierende Muster bleibt.
8Wie vermeide ich doppelte Geschäftslogik zwischen REST und GraphQL?
Indem die eigentliche Domänenlogik in einer gemeinsamen Service-Schicht liegt, auf die sowohl REST-Controller als auch GraphQL-Resolver als dünne Adapter zugreifen.
9Erhöht ein Hybrid-Ansatz den Testaufwand?
Ja, spürbar. Es braucht sowohl Contract-Tests für die REST-Endpunkte als auch Schema- und Query-Tests für GraphQL, plus gemeinsame Tests für die zugrunde liegende Service-Schicht.
10Welches Team-Wissen ist für eine Hybrid-Strategie notwendig?
Das Team sollte sowohl REST-Ressourcenmodellierung als auch GraphQL-Schema-Design mit Typen und Resolvern beherrschen, sonst entstehen leicht inkonsistente oder schlecht performante Schnittstellen.