2016-11-06 2 views
7

Nehmen wir an, ich möchte eine RESTful-Schnittstelle erstellen, und ich möchte mit foo s basierend auf ihren IDs arbeiten. Nichts Neues hier:Best Practices für die Rückgabe der Repräsentation der Ressource, die auch eine Sammlung ist

  • GET /api/foo1 gibt eine Darstellung (zum Beispiel JSON verwendet wird) von foo1.
  • DELETE /api/foo1 löscht foo1.

usw.

Nun lassen Sie mich Ihnen sagen, dass ein „foo“ ist eine Sammlung Typ Sache. Deshalb möchte ich in der Lage sein, eine „Bar“ zu einem „foo“ hinzuzufügen:

  • PUT /api/foo1/bar3 fügt bar3 zu foo1.
  • GET /api/foo1/bar3 gibt eine Darstellung foo1 zurück.
  • DELETE /api/foo1/bar3 entfernt bar3 von foo1.
  • DELETE /api/foo1 löscht foo1 insgesamt.

Jetzt bleibt die Frage: Was macht GET /api/foo1? Gibt es einfach eine Darstellung von foo1 zurück, wie ich ursprünglich in dieser Frage angenommen habe? Oder gibt es eine Liste von Bars zurück? Oder gibt es eine Darstellung von foo1 zurück, die sowohl eine Beschreibung von foo1 als auch enthält eine Liste aller enthaltenen Bars?

Oder sollte GET /api/foo1 lediglich eine Darstellung foo1 zurück, wie ich zu Beginn angenommen, und erfordern eine PROPFIND Anfrage der Stäbe innerhalb foo1 (der Ansatz von WebDAV genommen) zur Liste? Aber, um konsistent zu sein, müsste ich nicht alle meine anderen listenartigen Funktionen auf PROPFIND ändern, was direkt all jenen Tausenden von RESTful-Tutorials widerspricht, die sagen, GET /api/foo1 zu verwenden, um den Inhalt aufzulisten?

Antwort

2

Die Semantik von WebDAV wurde nie wirklich mit den Idiomen von RESTful-Schnittstellen in Einklang gebracht.

Theoretisch sollte GET eine Repräsentation eines Status einer Ressource abrufen und PROPFIND sollte verwendet werden, um die Mitglieder einer Sammlung abzurufen.

So sollten Sie dies tun:

  • GET/api/foo1/- kehrt Zustand foo1 nur
  • PROPFIND/api/foo1/- gibt die Mitglieder der foo1

meisten Front-End-Devs würden ausflippen, wenn Sie ihnen sagen würden, PROPFIND zu verwenden, obwohl es vollständig in Browser-js-Implementierungen unterstützt wird.

Ich persönlich benutze ein webdav/json Gateway, wo Anfragen verwenden RESTful Idiome gemacht, aber zu meiner webdav Implementierung geroutet

Zum Beispiel würde ich dies tun:

GET /api/foo1/_PROPFIND?fields=name,fooProp1,fooProp2 

Und das würde zurückkehren

[ 
{ name : "bar1", fooProp1: "..", fooProp2 : ".."}, 
{ name : "bar2", fooProp1: "..", fooProp2 : ".."} 
] 

Ein Vorteil dieses Ansatzes ist, dass der Client die zurückgegebenen JSON-Eigenschaften steuern kann. Das ist gut, weil eine Rich-API viele Eigenschaften hat, aber in den meisten Situationen brauchen die Clients nicht alle.

1

Die Routen und ihre Operationen in RESTfull API wurden vollständig von den Entwicklern entwickelt. Es ist der Entwickler, der entscheidet, was zurückgegeben werden soll, wenn er eine bestimmte Route anfragt, z. B. GET /api/foo1.

Und der Entwickler sollte jede Route einschließlich /api/foo1/bar entwerfen. Es gibt keine spezielle Regel, was eine bestimmte Route tun sollte. Wenn Ihre API ein Open-Source-Projekt ist, erstellen Sie eine saubere und klare Dokumentation aller Routen.

Verschwenden Sie keine Zeit mit Nachdenken über die Strategien der alten Schule.

3

Nach einigem Nachdenken, denke ich, die beste konzeptionelle Erklärung aus einer REST-Perspektive ist, dass normalerweise das "Ding" nicht dasselbe ist wie seine "Sammlung". Während also in der WebDAV-Welt eine directory/ dasselbe ist, das ihre Dateien enthält, könnte ich in der RESTful-Welt einen separaten directory/files/-Unterpfad für die enthaltenen Dateien haben. Auf diese Weise kann ich Verzeichnisse getrennt von den Dateien, die halten, manipulieren.

Betrachten Sie eine RESTful API für eine Farm, die Ställe enthält. Der Endpunkt könnte eine Liste von Ställen zurückgeben, von denen einer farm/api/barns/bigredbarn wäre. Naiv würde ich denken, dass das Abrufen von farm/api/barns/bigredbarn/ mir eine Liste von Tieren in der Scheune zur Verfügung stellen würde, was diese Frage ausgelöst hat.

Aber wirklich die Tiere in der Scheune sind nur ein Aspekt der Big Red Barn. Es könnte enthalten Fahrzeuge und Heu:

  • farm/api/barns/bigredbarn/animals/
  • farm/api/barns/bigredbarn/vehicles/
  • farm/api/barns/bigredbarn/haybales/

Mit diesem Ansatz das Dilemma ich nicht entstehen konfrontiert.

+0

Ich mag Ihren Ansatz. In der Tat ist es das gleiche Verhalten, das wirklich orientierten Sprachen implementieren Objekt für Array oder eine Liste Objekte: Array-Objekt Eigenschaften: Länge, Abmessungen, nur lesbar Array Methode GetValue - Liefert eine Element Liste Objekteigenschaften: Kopf, Aktuelle List-Methode GetEnumerator - gibt ein Objekt zurück, das wiederum Elemente zurückgibt –

Verwandte Themen