REST-APIs: Benutzerdefinierte HTTP-Header im Vergleich zu URL-Parametern

96

Wann verwenden Sie benutzerdefinierte HTTP-Header im Anforderungsteil einer REST-API?

Beispiel:

Würden Sie jemals verwenden

GET /orders/view 
(custom HTTP header) CLIENT_ID: 23

anstatt

GET /orders/view/client_id/23 or 
GET /orders/view/?client_id=23
Vasile Cotovanu
quelle

Antworten:

122

Die URL gibt die Ressource selbst an. Ein "Client" ist eine Ressource, auf die reagiert werden kann. Sie sollte daher Teil der Basis-URL sein : /orders/view/client/23.

Parameter sind genau das, um den Zugriff auf die Ressource zu parametrisieren. Dies kommt insbesondere bei Beiträgen und Suchen ins Spiel : /orders/find?q=blahblah&sort=foo. Es gibt eine feine Linie zwischen Parametern und Unterressourcen : /orders/view/client/23/active versus /orders/view/client/23?show=active. Ich empfehle den Subressourcenstil und die Reserveparameter für Suchvorgänge.

Da jeder Endpunkt eine Statusübertragung darstellt (um die Mnemonik zu entstellen), sollten benutzerdefinierte Header nur für Dinge verwendet werden, die nicht den Namen der Ressource (die URL), den Status der Ressource (den Body) oder Parameter direkt betreffen Auswirkungen auf die Ressource (Parameter). Damit bleiben echte Metadaten über die Anforderung von benutzerdefinierten Headern.

HTTP bietet eine sehr große Auswahl an Headern, die fast alles abdecken, was Sie benötigen. Ich habe gesehen, dass benutzerdefinierte Header in einer System-zu-System-Anforderung angezeigt werden, die im Auftrag eines Benutzers ausgeführt wird. Das Proxysystem überprüft den Benutzer, fügt " X-User: userid" zu den Headern hinzu und verwendet die Systemanmeldeinformationen, um den Endpunkt zu erreichen. Das empfangende System überprüft, ob die Systemanmeldeinformationen berechtigt sind, im Namen des Benutzers zu handeln, und überprüft dann, ob der Benutzer berechtigt ist, die Aktion auszuführen.

Nialscorva
quelle
Vielen Dank für eine so umfassende Antwort! Würden Sie den X-User weiterhin für eine mobile API verwenden, bei der das Risiko eines bösen Proxys (der den Header entfernt) immer noch hoch ist?
Vasile Cotovanu
1
Nein, die von mir erwähnte Verwendung von X-User erfolgt in System-zu-System-Verbindungen, bei denen das System im Auftrag eines Dritten handelt. Beispielsweise spricht Benutzer U mit Server A. Server A präsentiert Server B Anmeldeinformationen mit einem X-User-Header mit der Meldung "Verwenden Sie meine Anmeldeinformationen, um zu überprüfen, ob ich berechtigt bin, diese Aktion im Namen von Benutzer U auszuführen." Dies tritt in serviceorientierten Architekturen auf, und normalerweise verwenden Sie HTTPS. Eine mobile Plattform sollte fast immer der Benutzer selbst sein und die entsprechenden Anmeldeinformationen der ersten Person für die Transaktion verwenden.
Nialscorva
7
Der dritte Absatz ist eine der informativsten Antworten, die ich auf SO gelesen habe ;-)
Alistair77
1
@ Nialscorva Tolle Erklärung! Was ist, wenn der Benutzer über einen autorisierten Container (wie meine mobile App) mit meiner API interagieren soll? Was ich jetzt mache, ist, dass meine mobile App nicht berechtigt ist, eine Aktion alleine auszuführen, und auch nicht der Endbenutzer. Beide Anmeldeinformationen müssen vorhanden sein, wenn der Benutzer bereit ist, eine Aktion auszuführen.
Bolbol
6

Benutzerdefinierte Header bieten folgende Vorteile:

  • Kann leicht von Netzwerk-Tools / Skripten gelesen werden (Authentifizierung, Metainfo, ...)
  • Hält URLs frei von Sicherheitsvorkehrungen (sicherer, nicht in Browser- / Proxy-Caches)
  • Hält URLs sauberer: Ermöglicht eine bessere Zwischenspeicherung von Ressourcen
Christophe Roussy
quelle
Sie können auch stillschweigend von Proxies entfernt / gefiltert werden
fusi
@fusi guter Punkt ... hier ist ein Thema dazu: stackoverflow.com/questions/20820572/…
Christophe Roussy
5

Ich würde einen benutzerdefinierten Header nur verwenden, wenn es keine andere Möglichkeit gibt, Informationen nach Standard oder Konvention weiterzugeben. Darren102 erklärt den typischen Weg, um diesen Wert zu übergeben. Ihre API wird viel benutzerfreundlicher, wenn Sie typische Musterverse mit benutzerdefinierten Headern verwenden. Das heißt nicht, dass Sie keinen Fall haben, um sie zu verwenden, nur dass sie der letzte Ausweg sein sollten und etwas, das nicht bereits von der HTTP-Spezifikation behandelt wird.

verklagen
quelle
Stimmen Sie voll und ganz zu ... erfinden Sie das Rad niemals neu, wenn es einen Standardweg gibt, um eine Aufgabe zu erfüllen.
Alessandro Santini
5

Wann verwenden Sie ... HTTP-Header im Anforderungsteil einer REST-API?

Authentifizierung: GUIDs, Basisauthentifizierung, benutzerdefinierte Token usw., z. B. Basisauthentifizierung mit einem Guid-Token für die REST-API anstelle von Benutzername / Kennwort

Wenn Sie an der Weitergabe von Token oder anderen authentifizierungsähnlichen Informationen zwischen Domänen beteiligt sind, die von PCI-DSS oder anderen Sicherheitsregeln abgedeckt werden, müssen Sie möglicherweise auch Parameter begraben, da in einigen Vorschriften Authentifizierungselemente ausdrücklich erforderlich sind, um sich von URLs fernzuhalten, die trivial wiedergegeben werden können (von Browserverläufe, Proxy-Protokolle usw.).

user3038458
quelle
1

Es gibt keinen Standard für REST, wie auch immer der akzeptierte Weg wäre

GET /orders/view/23

Wenn Sie die benutzerdefinierten Header und damit die 23 After View nicht verwenden, wird davon ausgegangen, dass es sich um die ID handelt. Daher hätten Sie eine Funktion, die die ID aufnimmt und daher genau diese Informationen erzeugt.

darren102
quelle
1

Ich würde keine benutzerdefinierten Header verwenden, da Sie nicht wissen, ob Proxys diese weitergeben. URL-basiert ist der richtige Weg.

GET / orders / view / client / 23

Antony Scott
quelle
1
Ich würde auch keine benutzerdefinierten Header empfehlen, aber defekte Proxys sind nicht der Grund. Wenn der Proxy defekt ist, sollte er repariert werden.
Julian Reschke
1

Auf jeden Fall OK:

GET /orders/view/client_id/23 or 
GET /orders/view/?client_id=23

Auch ok:

GET /orders/view/23 or 

Ich würde denken, das wäre auch in Ordnung:

POST /orders/view 
(custom HTTP header) CLIENT_ID: 23
paulsm4
quelle
Die REST-vollständige POST-Antwort sollte ein HTTP 303 sein, dessen Standortheader auf "/ orders / view / 23" gesetzt ist.
Rich Remer
0

Sie können benutzerdefinierte Header verwenden, um weitere Informationen zu einer teilweise verarbeiteten Anforderung aufzunehmen, da das Umhüllen keine bewährte Methode ist. Die Header sind sicher .

Anwar Husain
quelle