73

Ich baue eine Webanwendung mit einer Services-Schicht. Die Services-Schicht wird mit einem RESTful-Design erstellt. Wir sind der Meinung, dass wir in Zukunft möglicherweise andere Anwendungen (iPhone, Android usw.) erstellen werden, die dieselbe Servicesbene wie die Webanwendung verwenden. Meine Frage ist dies - wie implementiere ich Login? Ich glaube, ich habe Schwierigkeiten, von einem traditionelleren verbbasierten Design zu einem ressourcenbasierten Design überzugehen. Wenn ich das mit SOAP erstellen würde, hätte ich wahrscheinlich eine Methode namens Login. In REST sollte ich eine Ressource haben. Ich habe Schwierigkeiten zu verstehen, wie ich meine URI für einen Login erstellen soll. Sollte es so etwas wie diese:Wie implementiere ich Login in einem RESTful Web Service?

http://myservice/ {username} p = {Kennwort}

EDIT: Die Front-End-Web-Anwendung, die traditionelle ASP.NET-Framework zur Authentifizierung verwendet. Irgendwann im Authentifizierungsprozess muss ich die angegebenen Anmeldeinformationen überprüfen. In einer herkömmlichen Webanwendung würde ich eine Datenbanksuche durchführen. Aber in diesem Szenario rufe ich einen Dienst auf, anstatt eine Datenbanksuche durchzuführen. Daher benötige ich etwas im Service, das die angegebenen Anmeldeinformationen überprüft. Zusätzlich zur Validierung der angegebenen Zugangsdaten benötige ich wahrscheinlich auch Informationen über den Benutzer, nachdem er erfolgreich authentifiziert wurde - Dinge wie sein vollständiger Name, seine ID usw. Ich hoffe, dass dies die Frage klarer macht.

Oder denke ich nicht über den richtigen Weg nach? Ich habe das Gefühl, dass ich Schwierigkeiten habe, meine Frage korrekt zu beschreiben.

Corey

Antwort

55

Wie S.Lott bereits erwähnt, haben wir ein zwei hier gefaltet Dinge: Login und Authentifizierung out-of-scope

Authentifizierung hier ist, wie dies breit diskutiert wird, und es gibt gemeinsame Vereinbarung. Was benötigen wir jedoch für einen Client, um sich erfolgreich gegen einen RESTful-Webdienst zu authentifizieren? Richtig, irgendeine Art von Token, nennen wir es Access-Token.

Client) Also, alles, was ich brauche, ist ein Access-Token, aber wie bekomme ich so RESTvoll?
Server) Warum nicht einfach erstellen?
Client) Wie kommt?
Server) Für mich ist ein Access-Token nichts anderes als eine Ressource. Daher erstelle ich eine für Sie als Gegenleistung für Ihren Benutzernamen und Ihr Passwort.

Somit könnte der Server die Ressourcen-URL "/ accesstokens" anbieten, um den Benutzernamen und das Passwort an die neu erstellte Ressource "/ accesstokens/{accesstoken}" zu senden. Alternativ Sie ein Dokument senden Sie das Zugriffstoken und a href mit der Ressource-Link enthält:

 
<access-token 
    id="{access token id goes here; e.g. GUID}" 
    href="/accesstokens/{id}" 
/> 

Die meisten wahrscheinlich, Sie eigentlich gar nicht zu schaffen, den Zugang-Token als subresource und demzufolge auch nicht sein href in der Antwort.
Wenn Sie dies jedoch tun, könnte der Client den Link in seinem Namen generieren oder nicht? Nein!
Denken Sie daran, dass REST-konforme Webdienste Ressourcen so miteinander verknüpfen, dass der Client selbst navigieren kann, ohne dass Ressourcenlinks generiert werden müssen.

Die letzte Frage, die Sie wahrscheinlich haben, ist, wenn Sie den Benutzernamen und das Passwort als ein HTML-Formular oder als ein Dokument, z. XML oder JSON - es hängt davon ab ... :-)

+3

Nicht perfekt nach REST, aber einfach und messbar besser als andere. Plus mit guter Laune geteilt. –

+1

Patrick, schlägst du dasselbe vor wie diese Antwort? http://StackOverflow.com/a/1135995/14731 – Gili

+0

Ist 403 korrekter Statuscode, wenn Benutzername und/oder Passwort nicht übereinstimmen? – sevteen

-4

Ich habe vor dem gleichen Problem konfrontiert. Login kann nicht gut auf Ressourcen-basiertes Design übertragen werden.

So wie ich es in der Regel handhaben ist durch Login-Ressource mit und vorbei Benutzernamen und Passwort auf der Parameter-String, im Grunde tun

GET auf http://myservice/login?u= {username} & p = {Kennwort}

Die Antwort ist eine Art Session oder Auth-String, die dann zur Validierung an andere APIs übergeben werden kann.

Eine Alternative zu GET auf der Login-Ressource tun, ist ein POST, REST-Puristen werden mich jetzt wahrscheinlich nicht mögen :), und übergibt die Glaubwürdigkeit im Körper. Die Antwort wäre die gleiche.

+11

Passwort folgen? Klartext Passwort?Als Abfragezeichenfolge? Hast du das wirklich gemeint, oder meinst du eine Zusammenfassung des Passwortes? –

+0

Danke. Das macht Sinn. Hier ist eine Follow-up-Frage - für eine große Anwendung würden Sie einen großen RESTful-Service für alles erstellen oder Dinge in verschiedene Dienste aufteilen? Ich dachte an einen Dienst nur für die Authentifizierung und dann verschiedene Dienste für die verschiedenen Module meiner Anwendung. Gibt es irgendwelche Gründe, warum Sie es auf die eine oder andere Weise tun würden oder nicht? –

+2

S. Lott: Es hängt davon ab, was Sie versuchen zu tun. Natürlich, wenn Sie eine Verdauung machen können, dann auf alle Fälle. Manchmal ist ein Digest nicht möglich. Wenn Ihnen die einzige Möglichkeit offen steht, ein Klartext-Passwort zu senden, tun Sie das bitte über SSL. In diesem Fall ist es auch besser, einen POST anstatt GET zu verwenden, um zu verhindern, dass der Browser sich erinnert, was Sie gesendet haben. – Alex

22

Sie loggen sich nicht ein. Du "authentifizierst" dich. Welt der Differenz.

Sie haben viele Authentifizierungsalternativen.

HTTP Basic, Digest, NTLM and AWS S3 Authentication

  • HTTP Basic und Digest-Authentifizierung. Dies verwendet den Header HTTP_AUTHORIZATION. Das ist sehr nett, sehr einfach. Aber kann zu viel Verkehr führen.

  • Authentifizierung Benutzername/Signatur. Wird manchmal "ID and KEY" -Authentifizierung genannt. Dies kann eine Abfragezeichenfolge verwenden.

    ?username=this&signature=some-big-hex-digest

    Dies ist, was wie Amazon Einsatz bringt. Der Benutzername ist die "ID". Der "Schlüssel" ist ein Digest, ähnlich dem für die HTTP-Digest-Authentifizierung. Beide Seiten müssen sich darauf einigen, dass der Digest fortgesetzt wird.

  • Eine Art Cookie-basierte Authentifizierung. Beispielsweise kann OpenAM als ein Agent konfiguriert werden, um ein Cookie zu authentifizieren und bereitzustellen, das Ihr RESTful-Webserver dann verwenden kann. Der Client würde sich zuerst authentifizieren und dann den Cookie mit jeder RESTful-Anfrage bereitstellen.

+0

Vielleicht muss ich meine Frage klären. Die Benutzer, die die Website besuchen, interagieren nicht direkt mit dem RESTful-Service. Sie werden mit der Webanwendung interagieren. Wenn ein Benutzer versucht, sich bei der Webanwendung anzumelden, ruft die Webanwendung den Webdienst auf (unter Verwendung von C# -Code). Dann wird der Code basierend auf der Antwort des Webdienstes diese entweder bei der Webanwendung anmelden oder nicht. Ist das sinnvoll? Ich bin mir nicht sicher, ob die vorgeschlagenen Authentifizierungsmethoden funktionieren, da der Browser des Benutzers nicht direkt mit dem Dienst interagiert. –

+0

@Corey Burnett: Korrekt. Benutzer können nicht mit einem RESTful-Webdienst interagieren. Richtig. Webanwendungen rufen Webdienste auf. Alle diese Methoden sind speziell so konzipiert, dass eine C# -Anwendung eine RESTful-Anforderung mit den richtigen Anmeldeinformationen erstellt und eine Antwort erhält. Ein REST-fähiger Webdienst verarbeitet nie "Anmeldung", da er keine Sitzungen hat. Es kann die Authentifizierung verarbeiten, indem es zustimmt, dass die Anfrage gültig ist. Wir haben eine "Dummy" -Anforderung, die nur mit einem "200 OK" antwortet, wenn die Anmeldeinformationen gut sind. –

+2

@ S.Lott @Corey Benutzer können absolut mit RESTful Systemen interagieren. Die meisten statischen HTML-Websites sind REST-konforme "Dienste". –

0

Seit ziemlich viel seit 2011 geändert hat ...

Wenn Sie ein 3rd-Party-Tool zur Verwendung offen sind, und leicht von REST abweichende leicht für die Web-UI, betrachten http://shiro.apache.org.

Shiro gibt Ihnen grundsätzlich einen Servlet-Filter, der sowohl für die Authentifizierung als auch für die Autorisierung vorgesehen ist. Sie können alle von @ S.Lott aufgelisteten Anmeldeverfahren verwenden, einschließlich einer einfachen formularbasierten Authentifizierung.

Filtern Sie die restlichen URLs, die eine Authentifizierung erfordern, und Shiro erledigt den Rest.

Ich benutze dies derzeit in meinem eigenen Projekt und es hat bis jetzt ziemlich gut für mich gearbeitet.

Hier ist etwas anderen Leute interessieren sein könnten. https://github.com/PE-INTERNATIONAL/shiro-jersey#readme

1

Große Frage, gut gestellt. Ich mag Patricks Antwort sehr.Ich benutze so etwas wie

-/users/{username}/loginsession

Mit POST und GET gehandhabt wird. So poste ich eine neue Login-Sitzung mit den Zugangsdaten und ich kann dann die aktuelle Sitzung als Ressource über das GET anzeigen.

Die Ressource ist eine Login-Sitzung, und das kann ein Zugriffstoken oder Auth-Code haben, Ablauf etc.

Seltsamer, mein MVC Anrufer muss sich ein Schlüssel/Träger-Token über einen Header präsentieren beweisen, dass Es hat das Recht, neue Anmeldesitzungen zu versuchen und zu erstellen, da die MVC-Site ein Client der API ist.

bearbeiten

denke ich einige andere Antworten und Kommentare hier sind die Lösung, das Problem mit einer Out-of-Band-Geheimnis geteilt und nur mit einem Header Authentifizierung. In vielen Situationen oder für Service-to-Service-Anrufe ist das kein Problem. Die andere Lösung besteht darin, ein Token, OAuth oder JWT oder anderes, fließen zu lassen, was bedeutet, dass die "Anmeldung" bereits durch einen anderen Prozess erfolgt ist, wahrscheinlich eine normale Login-Oberfläche in einem Browser, die auf einem Formular POST basiert.

Meine Antwort ist für den Dienst, der hinter dieser Benutzeroberfläche steht, vorausgesetzt, Sie möchten sich anmelden und die Benutzer- und Benutzerverwaltung in einem REST-Dienst und nicht im MVC-Code der Website platzieren. Es ist der Benutzer-Login-Dienst.

Es ermöglicht auch anderen Diensten, sich anzumelden und ein ablaufendes Token zu erhalten, anstatt einen vorinstallierten Schlüssel zu verwenden, sowie Testskripts in einem CLI oder Postman.

+2

Übergeben Sie das Token in einer Kopfzeile, ja. Übergeben Sie es als Teil der URL, nein. Die URL wird während der Verwendung von HTTPS verschlüsselt übertragen. Jedoch; Die URL wird auch im Browserverlauf und in Serverprotokollen gespeichert. Es gibt viele gute Gründe, die Übertragung sicherheitsrelevanter Daten in URL-Abfrageparametern zu vermeiden. – Craig

0

Das erste, was Sie über REST verstehen, ist, dass es sich um einen Token-basierten Ressourcenzugriff handelt. Im Gegensatz zu herkömmlichen Methoden wird der Zugriff basierend auf Token-Validierung gewährt. In einfachen Worten, wenn Sie ein richtiges Token haben, können Sie auf Ressourcen zugreifen. Jetzt gibt es viele andere Dinge für die Erstellung und Manipulation von Token.

Für Ihre erste Frage können Sie eine Restfull-API entwerfen. Zugangsdaten (Benutzername und Passwort) werden an Ihre Service-Schicht weitergegeben. Die Service-Schicht validiert diese Zugangsdaten und erteilt ein Token. Zugangsdaten können entweder ein einfacher Benutzername/Passwort sein oder SSL-Zertifikate. SSL-Zertifikate verwenden das OAUTH-Protokoll und sind sicherer.

Sie können Ihre URI wie folgt erstellen - URI für Token-Anfrage->http://myservice/some-directory/token? (Sie können Credentilals in diesem URI für Token übergeben)

Um dieses Token für den Ressourcenzugriff zu verwenden, können Sie dieses [Authorization: Bearer (Token)] zu Ihrem HTTP-Header hinzufügen.

Dieses Token kann vom Kunden für den Zugriff auf verschiedene Komponenten Ihrer Serviceschicht verwendet werden. Sie können auch den Ablaufzeitraum dieses Tokens ändern, um Missbrauch zu verhindern.

Für Ihre zweite Frage können Sie verschiedene Token für den Zugriff auf verschiedene Ressourcenkomponenten Ihrer Serviceebene gewähren. Dazu können Sie in Ihrem Token Ressourcenparameter und auf Basis dieses Feldes eine Großberechtigung angeben.

Sie können auch diese Links für mehr Information- http://www.codeproject.com/Articles/687647/Detailed-Tutorial-for-Building-ASP-NET-WebAPI-REST

http://www.vinaysahni.com/best-practices-for-a-pragmatic-restful-api

Verwandte Themen