webentwicklung-frage-antwort-db.com.de

Wie erstelle ich REST URLs ohne Verben?

Ich kämpfe darum, herauszufinden, wie man erholsame URLs erstellt. Ich bin alle für den erholsamen Ansatz, URLs mit Nomen und nicht mit Verben zu verwenden, und verstehe nicht, wie man das macht.

Wir schaffen einen Service, um einen Finanzrechner zu implementieren. Der Rechner verwendet eine Reihe von Parametern, die wir über eine CSV-Datei hochladen. Die Anwendungsfälle umfassen:

  1. Laden Sie neue Parameter hoch
  2. Holen Sie sich die neuesten Parameter
  3. Parameter für ein bestimmtes Geschäftsdatum abrufen
  4. Aktivieren Sie einen Parametersatz
  5. Überprüfen Sie eine Reihe von Parametern

Ich gehe davon aus, dass die folgenden URL-Typen hilfreich sind:

/parameters
/parameters/12-23-2009

Sie können die ersten drei Anwendungsfälle erreichen mit:

  1. POST, bei dem Sie die Parameterdatei in die Post-Anfrage aufnehmen
  2. GET der ersten URL
  3. GET der zweiten URL

Aber wie macht man den 4. und 5. Anwendungsfall ohne Verb? Würdest du keine URLs brauchen wie:

/parameters/ID/activate
/parameters/ID/validate

??

278
Marcus Leon

Vielleicht so etwas wie:

PUT /parameters/activation HTTP/1.1
Content-Type: application/json; encoding=UTF-8
Content-Length: 18

{ "active": true }
71
yfeldblum

Allgemeine Grundsätze für ein gutes URI-Design:

  • Don't Verwenden Sie Abfrageparameter, um den Status zu ändern
  • Don't Verwenden Sie gemischte Pfade, wenn Sie helfen können; Kleinbuchstaben sind am besten
  • Don't verwende implementierungsspezifische Erweiterungen in deinen URIs (.php, .py, .pl, etc.)
  • Don't fallen in RPC mit Ihren URIs
  • Do Beschränken Sie Ihren URI-Bereich so weit wie möglich
  • Do Pfadsegmente kurz halten
  • Do entweder /resource Oder /resource/ Bevorzugen; Erstellen Sie 301 Weiterleitungen von denen, die Sie nicht verwenden
  • Do Abfrageparameter für die Unterauswahl einer Ressource verwenden; d.h. Paginierung, Suchanfragen
  • Do Verschieben von Inhalten aus dem URI, die sich in einem HTTP-Header oder einem Body befinden sollten

(Hinweis: Ich habe nicht "RESTful URI-Design" gesagt. URIs sind in REST im Wesentlichen undurchsichtig.)

Allgemeine Grundsätze für die Auswahl der HTTP-Methode:

  • Don't benutze jemals GET, um den Zustand zu ändern; Auf diese Weise kann der Googlebot Ihren Tag ruinieren
  • Don't Verwenden Sie PUT, es sei denn, Sie aktualisieren eine gesamte Ressource
  • Don't Verwenden Sie PUT, es sei denn, Sie können auch legitimerweise ein GET für denselben URI ausführen
  • Don't Verwenden Sie POST, um Informationen abzurufen, die langlebig sind oder die möglicherweise im Cache gespeichert werden können
  • Don't Führe eine Operation aus, die nicht idempotent mit PUT ist
  • Do benutze GET so oft wie möglich
  • Do Verwenden Sie im Zweifelsfall POST anstelle von PUT
  • Do Verwenden Sie POST, wenn Sie etwas tun müssen, das sich wie RPC anfühlt
  • Do Verwenden Sie PUT für Klassen von Ressourcen, die größer oder hierarchisch sind
  • Do Verwenden Sie DELETE anstelle von POST, um Ressourcen zu entfernen
  • Do Verwenden Sie GET für Berechnungen, es sei denn, Ihre Eingabe ist umfangreich. Verwenden Sie in diesem Fall POST

Allgemeine Prinzipien des Web Service Designs mit HTTP:

  • Don't Fügen Sie Metadaten in den Hauptteil einer Antwort ein, die sich in einem Header befinden soll
  • Don't Versetzen Sie Metadaten in eine separate Ressource, es sei denn, dies würde einen erheblichen Overhead verursachen
  • Do Verwenden Sie den entsprechenden Statuscode
    • 201 Created Nach dem Erstellen einer Ressource; resource muss zum Zeitpunkt des Absendens der Antwort vorhanden sein
    • 202 Accepted Nach erfolgreicher Ausführung eines Vorgangs oder asynchroner Erstellung einer Ressource
    • 400 Bad Request Wenn jemand eine Operation mit Daten ausführt, die eindeutig gefälscht sind; Für Ihre Anwendung könnte dies ein Validierungsfehler sein. In der Regel 500 für nicht abgefangene Ausnahmen reservieren
    • 401 Unauthorized, Wenn jemand auf Ihre API zugreift, ohne einen erforderlichen Authorization -Header anzugeben, oder wenn die Anmeldeinformationen in Authorization ungültig sind; Verwenden Sie diesen Antwortcode nicht, wenn Sie keine Anmeldeinformationen über einen Authorization -Header erwarten.
    • 403 Forbidden, Wenn jemand auf eine Weise auf Ihre API zugreift, die böswillig sein könnte oder wenn er nicht autorisiert ist
    • 405 Method Not Allowed, Wenn jemand POST verwendet, wenn er PUT usw. Hätte verwenden sollen
    • 413 Request Entity Too Large, Wenn jemand versucht, Ihnen eine unzulässig große Datei zu senden
    • 418 I'm a teapotbeim Kaffeebrühen mit einer Teekanne
  • Do Verwenden Sie Caching-Header, wann immer Sie können
    • ETag -Header eignen sich gut, wenn Sie eine Ressource leicht auf einen Hash-Wert reduzieren können
    • Last-Modified Sollte Ihnen anzeigen, dass es eine gute Idee ist, den Zeitstempel der Ressourcenaktualisierung einzuhalten
    • Cache-Control Und Expires sollten sinnvolle Werte erhalten
  • Do alles, was Sie können, um Caching-Header in einer Anfrage zu berücksichtigen (If-None-Modified, If-Modified-Since)
  • Do Redirects verwenden, wenn sie sinnvoll sind, aber diese sollten für einen Webdienst selten sein

In Bezug auf Ihre spezielle Frage sollte POST für # 4 und # 5 verwendet werden. Diese Vorgänge fallen unter die oben genannte "RPC-ähnliche" Richtlinie. Denken Sie für # 5 daran, dass POST nicht unbedingt Content-Type: application/x-www-form-urlencoded Verwenden muss. Dies kann genauso gut eine JSON- oder CSV-Nutzlast sein.

984
Bob Aman

Wann immer es so aussieht, als ob Sie ein neues Verb benötigen, denken Sie daran, dieses Verb stattdessen in ein Substantiv umzuwandeln. Verwandeln Sie beispielsweise "Aktivieren" in "Aktivierung" und "Validieren" in "Validierung".

Aber nur nach dem, was Sie geschrieben haben, würde ich sagen, dass Ihre Anwendung viel größere Probleme hat.

Jedes Mal, wenn eine Ressource namens "Parameter" vorgeschlagen wird, sollte sie in den Köpfen aller Projektteammitglieder rote Fahnen setzen. 'parameter' kann buchstäblich auf jede Ressource angewendet werden. es ist nicht spezifisch genug.

Was genau repräsentiert ein 'Parameter'? Wahrscheinlich eine Reihe von verschiedenen Dingen, denen jeweils eine separate Ressource gewidmet sein sollte.

Ein anderer Weg, dies zu erreichen: Wenn Sie Ihre Anwendung mit Endbenutzern besprechen (die vermutlich wenig über Programmierung wissen), welche Wörter verwenden sie selbst wiederholt?

Das sind die Wörter, um die Sie Ihre Anwendung herum entwerfen sollten.

Wenn Sie diese Konvertierung noch nicht mit potenziellen Nutzern durchgeführt haben - stoppen Sie jetzt alles und schreiben Sie erst dann eine weitere Codezeile! Nur dann hat Ihr Team eine Vorstellung davon, was aufgebaut werden muss.

Ich weiß nichts über Finanzsoftware, aber wenn ich raten müsste, würde ich sagen, dass einige der Ressourcen mit Namen wie "Bericht", "Zahlung", "Überweisung" und "Währung" versehen sind.

Es gibt eine Reihe guter Bücher über diesen Teil des Software-Designprozesses. Zwei, die ich empfehlen kann, sind Domain Driven Design und Analysis Patterns .

18
Rich Apodaca

Das Design Ihrer URLs hat nichts damit zu tun, ob Ihre Anwendung REST-fähig ist oder nicht. Der Ausdruck "RESTful URLs" ist daher Unsinn.

Ich denke, Sie sollten etwas mehr darüber lesen, was REST eigentlich ist. REST behandelt die URLs als undurchsichtig und weiß daher nicht, was in ihnen enthalten ist. ob es Verben oder Substantive gibt oder was auch immer. Vielleicht möchten Sie Ihre URLs immer noch entwerfen, aber es geht um die Benutzeroberfläche, nicht um REST.

Kommen wir jedoch zu Ihrer Frage: Die letzten beiden Fälle sind nicht REST-konform und passen nicht in ein ruhiges Schema. Das könnten Sie RPC nennen. Wenn Sie REST ernst meinen, müssen Sie die Funktionsweise Ihrer Anwendung von Grund auf überdenken. Entweder das oder REST und mache deine App einfach als RPC-App.

Hrmmm vielleicht nicht.

Die Idee dabei ist, dass Sie alles als Ressource behandeln müssen. Sobald ein Parametersatz eine URL hat, auf die Sie verweisen können, fügen Sie einfach Folgendes hinzu:

GET [parametersurl]/validationresults

POST [paramatersurl]
body: {command:"activate"}

Aber auch dieses aktivierende Ding ist RPC, nicht REST.

11
Breton

Die Aktivierungs- und Validierungsanforderungen sind Situationen, in denen Sie versuchen, den Status einer Ressource zu ändern. Es ist nicht anders, als wenn eine Bestellung "abgeschlossen" oder eine andere Anfrage "übermittelt" wird. Es gibt zahlreiche Möglichkeiten, diese Art der Zustandsänderung zu modellieren. Ich finde jedoch, dass dies häufig funktioniert, indem Sie Sammlungsressourcen für Ressourcen desselben Zustands erstellen und dann die Ressource zwischen den Sammlungen verschieben, um den Zustand zu beeinflussen.

z.B. Erstellen Sie einige Ressourcen wie

/ActiveParameters
/ValidatedParameters

Wenn Sie einen Parametersatz aktivieren möchten, fügen Sie diesen der ActiveParameters-Auflistung hinzu. Sie können den Parametersatz entweder als Entitätskörper oder wie folgt als Abfrageparameter eine URL übergeben:

POST /ActiveParameters?parameter=/Parameters/{Id}

Dasselbe kann mit den/ValidatedParameters durchgeführt werden. Wenn die Parameter nicht gültig sind, kann der Server "Bad Request" an die Anforderung zurückgeben, um die Parameter zur Sammlung validierter Parameter hinzuzufügen.

6
Darrel Miller

Ich würde die folgenden Meta-Ressourcen und Methoden vorschlagen.

Parameter aktivieren und/oder validieren:

> PUT /parameters/<id>/meta HTTP/1.1
> Host: example.com
> Content-Type: application/json
> Connection: close
>
> {'active': true, 'require-valid': true}
>
< HTTP/1.1 200 OK
< Connection: close
<

Überprüfen Sie, ob die Parameter aktiv und gültig sind:

> GET /parameters/<id>/meta HTTP/1.1
> Host: example.com
> Connection: close
>
< HTTP/1.1 200 OK
< Content-Type: application/json
< Connection: close
<
< {
<     'active': true,
<     'require-valid': true,
<     'valid': {'status': false, 'reason': '...'}
< }
<
1

In einer REST Umgebung ist jede URL eine eindeutige Ressource. Was sind Ihre Ressourcen? Ein Finanzrechner hat wirklich keine offensichtlichen Ressourcen. Sie müssen sich mit den Parametern befassen, die Sie aufrufen, und diese abrufen B. ein Tilgungskalender für ein Darlehen eine Ressource dar. Die URL für den Kalender kann Startdatum, Laufzeit (in Monaten oder Jahren), Zeitraum (bei Zinserhöhung), Zinssatz und Anfangsprinzip enthalten Mit all diesen Werten haben Sie einen bestimmten Zahlungskalender:

http://example.com/amort_cal/2009-10-20/30yrsfixed/monthly/5.00/200000

Jetzt weiß ich nicht, was Sie berechnen, aber Ihr Konzept einer Parameterliste klingt nicht RESTful. Wie schon jemand gesagt hat, klingen Ihre obigen Anforderungen eher nach XMLRPC. Wenn Sie nach REST suchen, benötigen Sie Substantive. Berechnungen sind keine Substantive, sondern Verben, die auf Substantive einwirken. Sie müssen es umdrehen, um die Substantive aus Ihren Kalkulationen zu ziehen.

0
jmucchiello

Edit: In der Tat hätte der URI verhindert, dass GET Anfragen idempotent blieben.


Für die Validierung würde jedoch die Verwendung von HTTP-Statuscodes zur Benachrichtigung über die Gültigkeit einer Anforderung (zum Erstellen eines neuen oder Ändern eines vorhandenen 'Parameters') zu einem Restful-Modell passen.

Melde dich mit einem 400 Bad Request Statuscode, wenn die übermittelten Daten ungültig sind und die Anforderung vor der erneuten Übermittlung geändert werden muss ( HTTP/1.1 Statuscodes ).

Dies hängt jedoch von der Validierung zum Zeitpunkt der Einreichung ab, anstatt sie wie in Ihrem Anwendungsfall aufzuschieben. Die anderen Antworten haben passende Lösungen für dieses Szenario.

0
Derek Mortimer