2017-03-23 4 views
2

Ich versuche, eine Web-API 2-Methode aufzurufen, die Auth von einer Konsolenanwendung benötigt, die auf meinem Desktop ausgeführt wird, wo ich die Berechtigung habe, aber 401 Unathorized. Ich weiß, dass ich eine Autorisierung habe, weil es funktioniert, wenn ich den gleichen Anruf von einem Webbrowser aus mache. So kann ein Browser meine Standard-Login-ID/PW an die API senden, aber der WebClient von .NET kann nicht? Das scheint verrückt. Es muss einen Weg geben, dies zu tun, ohne meine ID/Pw in die Konsolen-App einzugeben.Verwenden von Standardanmeldeinformationen zum Aufrufen von API in der Konsolenanwendung

Das Folgende ist, was ich in einer Konsolen-App verwende und es funktioniert nicht.

Dies verwendet Windows Auth als Intranet-Zeug.

Dies löst eine Ausnahme aus "Der Remote-Server hat einen Fehler zurückgegeben: (401) Nicht autorisiert."

using(var c = new WebClient()) 
{ 
    c.UseDefaultCredentials = true; 
    string value = c.DownloadString("http://localhost:62659/api/Store/GetData"); 
} 

Ich versuchte auch, die unten, und wenn ich die Maus über DefaultNetworkCredentials der Benutzername/pw leere Strings sind. Warum kann .NET das nicht herausfinden?

using(var c = new WebClient()) 
      { 
       var creds = new CredentialCache(); 
       var uri = new Uri("http://localhost:62659/api/Store/GetData"); 
       creds.Add(uri, "ntlm", System.Net.CredentialCache.DefaultNetworkCredentials); 
       c.Credentials = creds; 
       string value = c.DownloadString(uri); 
      } 
+0

Erhalten Sie eine Ausnahme oder Fehlerinformationen, die Sie teilen könnten? – gmiley

+0

Fiddler2 zeigt Ihnen die Anmeldeinformationen, die mit der get-Anforderung übergeben wurden. – samosaris

+0

Ich verwende [Postman] (https://www.getpostman.com/), um diese Art von Problemen zu beheben. – jomsk1e

Antwort

1

Es ist wahrscheinlich, dass Sie nicht Ihre Anmeldeinformationen innerhalb Windows Credential Manager gespeichert haben. Sie können darauf über Control Panel > Credential Manager zugreifen. Von dort können Sie alle erforderlichen Anmeldeinformationen hinzufügen. CredentialCache.DefaultCredentials und CredentialCache.DefaultNetworkCredentials enthält die Anmeldeinformationen des aktuell angemeldeten oder impersonierten Benutzers. Wenn für das, zu dem Sie eine Verbindung herstellen, andere Anmeldeinformationen erforderlich sind, funktionieren diese nicht. Sie müssen diese Anmeldeinformationen dem Berechtigungsnachweis-Manager in Windows hinzufügen.

Der Grund, warum Sie in Chrome eine Verbindung herstellen, ist, dass Chrome Anmeldeinformationen in sich speichert, die Sie speichern möchten.

Anmeldeinformationen, die als funktionale IDs verwendet werden, können so eingestellt werden, dass sie niemals ablaufen, oder sie müssen zu einer Liste von monatlichen/jährlichen Wartungselementen hinzugefügt werden, um das Kennwort für diese Konten zu aktualisieren.

Sie möchten auch schlechte Login-Informationen in Ihrer Anwendung behandeln. Wenn dies eine automatisierte Aufgabe ist, lassen Sie sie per E-Mail oder anderweitig benachrichtigen, dass die Anmeldeinformationen aktualisiert werden müssen.

Wenn ein Benutzer das ausführt, können Sie den aktuellen Benutzer einfach auffordern, ein neues Kennwort anzugeben, mit dem Sie die gespeicherten Anmeldeinformationen dann aktualisieren können.

Eine andere Option wäre, den Benutzer, der die Anwendung ausführt, als Benutzer am empfangenden Ende mit denselben Anmeldeinformationen zu definieren. Auf diese Weise ist der gesamte Prozess an die Benutzer gebunden, die die Anwendung ausführen werden.

+0

Das ist eine große Enttäuschung. In einer Corp-Umgebung, in der Apps von einem Batch-Server ausgeführt werden, werden Admins dies nicht beibehalten wollen, wenn sie die Batch-ID/pw ändern (was wir nicht wissen, wenn wir Jobs in einem Planungssystem erstellen). Großer Mist. – user441521

+0

@ user441521 - Ich erwähnte ein wenig darüber, nachdem ich Ihren Kommentar oben gesehen habe. Ein anderer Ansatz wäre, dies in Ihre Anwendung zu schreiben. Wenn der Berechtigungsnachweis aufgrund von schlechten Anmeldeinformationen fehlschlägt, können Sie ihn per E-Mail oder auf andere Weise benachrichtigen, dass die Anmeldeinformationen aktualisiert werden müssen. – gmiley

+0

@ user441521 - Ich habe meine Antwort erweitert, um hoffentlich einige Alternativen zu bieten. – gmiley

0

Die Verwendung von DefaultCredentials sollte funktionieren, Windows Auth von der Konsolenanwendung zu verwenden. Solange Sie den entsprechenden Berechtigungs-Header haben, nach dem Ihre Web-API sucht. Gleiches gilt für meinen Kommentar. Ich empfehle, den api-Aufruf mit Postman zu testen, damit Sie Fehler beheben und überprüfen können, was Ihnen fehlt.

In Bezug auf die Anmeldeinformationen als leer, ist dies möglicherweise, weil Sie DefaultNetworkCredentials verwenden.

Try this:

using(var c = new WebClient()) 
{ 
    var uri = new Uri("http://localhost:62659/api/Store/GetData"); 
    c.Credentials = System.Net.CredentialCache.DefaultCredentials; 
    string value = c.DownloadString(uri); 
} 

Wenn Sie NetworkCredential verwenden möchten, sollten Sie Netzwerkanmeldeinformationen wie so werden Eingabe:

c.Credentials = new NetworkCredential(username, password, domain); 

Ich habe diese Art von Konsole-Anwendung und verwendet es als Service und Ich kann dir sagen, dass das funktionieren sollte. Sie sollten nur Fehler beheben und Bit für Bit das eigentliche Problem bekommen.

+0

Was ist der Unterschied zwischen NetworkCredential und DefaultCredentials? Ich meine meine ID, die wäre DefaultCredentials, denke ich, ist eine AD-ID im Netzwerk. Leider erlaubt mir der Ort nicht, Postbote zu führen. Ich versuche Geiger, aber ich sehe den Verkehr nicht, aber ich benutze den Geiger nicht so sehr, also bin ich es wahrscheinlich. Versuchen. Und Ihre Web-API war Web API 2 mit Authorize-Tag auf Controllern und mit Windows-Authentifizierung? – user441521

+0

Fiddler zeigt dies nicht an, wenn es von der Konsolen-App kommt. – user441521

+0

@ user441521 - 'DefaultNetworkCredentials' ist vom Typ 'NetworkCredential', der die tatsächlich verwendete Klasse ist. 'DefaultCredentials' gibt Objekte des Typs 'ICredentials' zurück, jedoch liefert die' GetCredential() 'Funktion auf' DefaultCredentials' ein Objekt vom Typ 'NetworkCredential'. Unabhängig davon, welche Sie verwenden, arbeiten Sie tatsächlich mit 'NetworkCredential'-Instanzen, die die ICredentials-Schnittstelle implementieren. – gmiley

Verwandte Themen