Zum Beispiel habe ich Entitäten: Client, Bericht. Der Client verfügt möglicherweise über viele Berichte, und ich denke, der Endpunkt für eine einzelne Berichtsverwaltung sollte wie folgt verschachtelt sein:
/clients/{client_id}/reports/{report_id}
Wie für alle Berichte eines Clients wird der Enpoint erwartet:
/clients/{client_id}/reports
Aber wie sollte ein Endpunkt aussehen, um alle Berichte aller Clients zu erhalten, damit die API konsistent und gut gestaltet bleibt?
Meine Ansätze:
- (Ich habe es in einer Google-API gesehen) Verwenden Sie stattdessen "-" und analysieren Sie es als "alle":
/clients/-/reports
Dadurch wird das Endpunktformat beibehalten, es sieht jedoch etwas ungewöhnlich aus. Es kann kein RFC gefunden werden, das dies vorschlägt.
- Erstellen Sie einen separaten Endpunkt nur für alle Berichte:
/reports
Aber um Kundenberichte zu erhalten, ist es immer noch:
/clients/{client_id}/reports
- Refactor-Endpunkte, um "Client" nicht zu einem übergeordneten Element, sondern nur zu einem Filterparameter zu machen:
/reports?client={client_id}
- Berichte eines Kunden
/reports
- Berichte aller Kunden
Wenn Sie einen neuen Endpunkt zum Posten eines Berichts für einen bestimmten Client hinzufügen, sieht dieser möglicherweise hässlich aus, da es sich um eine POST-Anforderung mit einem Parameter in der URL handelt.
Gibt es noch andere Ideenvorschläge?
quelle
Antworten:
Denken Sie vor allem daran, dass es keine goldenen Regeln für die Modellierung von RESTful-APIs gibt. Wir haben nur Best Practices und Konventionen. Abgesehen davon lautet die wahrscheinliche Antwort - wie üblich - diejenige, die Ihren Anforderungen am besten entspricht, und in diesem Fall diejenige, die Ihr Modell am besten ausdrückt.
Überprüfen Sie also die drei Optionen anhand der Ausdruckskraft.
# 1 Die "-" Notation
Das ist eine gute Idee. Es erlaubt uns, die Bedingung auszudrücken, zu der alles
reports
gehörtclients
. Es beschränkt die "Abfrage" auf einen bestimmten Satz von Berichten (die sich innerhalb derclients
Grenze befinden).Der Begriff der Hierarchie (Zugehörigkeit) wird ständig beibehalten. Wenn er
reports
also an verschiedenen Orten gefunden werden kann, ist diese Notation eine große Sache. Zum Beispiel:/clients/-/reports
/departments/-/reports
/employees/-/reports
Zum Abrufen aller verfügbaren Berichte im System bietet das Beibehalten der Hierarchie jedoch keinen wertvollen Vorteil gegenüber der nächsten Option.
# 2 Verschiedene URIs
Wenn wir zum Zeitpunkt des Abrufs aller verfügbaren Berichte keine Grenzen / Kontexte / Hierarchien ausdrücken müssen, erscheint mir dieser Ansatz vernünftiger.
Die neue URI (
/reports
) lässt auch die Möglichkeit einer Berichtsverwaltung offen . Wir müssen es jedoch nicht vollständig RESTful unterstützen, wenn wir es nicht für notwendig halten. Zum Beispiel haben Sie angegebenMake a separate endpoint just for all the reports
. Das ist in Ordnung, Sie müssen nurGET
einige Filter zum Abfragen implementieren und vielleicht ist es soweit.Beachten Sie, dass Sie dies immer noch tun können
/reports?client={client_id}
. Es ist in Ordnung, unterschiedliche URI für dieselbe Ressource zu haben. Einige Artikel, die ich gelesen habe, würden diese Robustheit nennen .# 3 Hierarchie umkehren
Ich habe das Gefühl, dass dieser Ansatz nicht Ihren Erwartungen entspricht. Außerdem denke ich, dass es Sie irgendwann zum Startpunkt bringen wird.
Schlussfolgerungen
Beachten Sie, dass sich Nr. 1 und Nr. 2 nicht gegenseitig ausschließen. Wir können beides umsetzen. In Anbetracht der tatsächlichen Situation und gemäß den Prämissen des OP würde ich nur # 2 implementieren.
1: Es ist äquivalent zu,
/clients/-/reports
denke ichquelle
Die API-Entwurfsmuster von Google schlagen vor, in diesem Szenario '-' zu verwenden.
Quelle:
https://cloud.google.com/apis/design/design_patterns#list_sub-collections
quelle
/client/{client_id}/report/{report_id}
und/clients/report/{report_id}
/reports
?/clients...
und/reports
.