Arbeiten mit SSL in Web-API
Mehrere gängige Authentifizierungsschemas sind über einfaches HTTP nicht sicher. Insbesondere senden die einfache Authentifizierung und Formularauthentifizierung unverschlüsselte Anmeldeinformationen. Um sicher zu sein, müssen diese Authentifizierungsverfahren SSL verwenden. Darüber hinaus können SSL-Clientzertifikate zum Authentifizieren von Clients verwendet werden.
Aktivieren von SSL auf dem Server
So richten Sie SSL in IIS 7 oder höher ein:
- Ein Zertifikat erstellen oder abrufen. Zum Testen können Sie ein selbstsigniertes Zertifikat erstellen.
- Fügen Sie eine HTTPS-Bindung hinzu.
Ausführliche Informationen finden Sie unter Einrichten von SSL für IIS 7.
Für lokale Tests können Sie SSL in IIS Express in Visual Studio aktivieren. Setzen Sie im Fenster Eigenschaften SSL aktiviert auf True. Beachten Sie den Wert SSL-URL-; verwenden Sie diese URL zum Testen von HTTPS-Verbindungen.
SSL-Verschlüsselung in einem Web-API-Controller erzwingen
Wenn Sie über eine HTTPS- und eine HTTP-Bindung verfügen, können Clients weiterhin HTTP für den Zugriff auf die Website verwenden. Möglicherweise können Sie zulassen, dass einige Ressourcen über HTTP verfügbar sind, während andere Ressourcen SSL erfordern. Verwenden Sie in diesem Fall einen Aktionsfilter, um SSL für die geschützten Ressourcen zu benötigen. Der folgende Code zeigt einen Web-API-Authentifizierungsfilter, der auf SSL überprüft:
public class RequireHttpsAttribute : AuthorizationFilterAttribute
{
public override void OnAuthorization(HttpActionContext actionContext)
{
if (actionContext.Request.RequestUri.Scheme != Uri.UriSchemeHttps)
{
actionContext.Response = new HttpResponseMessage(System.Net.HttpStatusCode.Forbidden)
{
ReasonPhrase = "HTTPS Required"
};
}
else
{
base.OnAuthorization(actionContext);
}
}
}
Fügen Sie diesen Filter zu allen Web-API-Aktionen hinzu, die SSL erfordern:
public class ValuesController : ApiController
{
[RequireHttps]
public HttpResponseMessage Get() { ... }
}
SSL-Clientzertifikate
SSL stellt die Authentifizierung mithilfe von Public Key-Infrastrukturzertifikaten bereit. Der Server muss ein Zertifikat bereitstellen, das den Server für den Client authentifiziert. Es ist weniger üblich, dass der Client ein Zertifikat für den Server bereitstellt, aber dies ist eine Option für die Authentifizierung von Clients. Um Clientzertifikate mit SSL zu verwenden, benötigen Sie eine Möglichkeit, signierte Zertifikate an Ihre Benutzer zu verteilen. Bei vielen Anwendungstypen ist dies nicht eine gute Benutzererfahrung, aber in einigen Umgebungen (z. B. Enterprise) kann es machbar sein.
Vorteile | Benachteiligungen |
---|---|
- Zertifikatsnachweise sind stärker als Benutzername/Passwort. - SSL bietet einen vollständigen sicheren Kanal mit Authentifizierung, Nachrichtenintegrität und Nachrichtenverschlüsselung. | – Sie müssen PKI-Zertifikate abrufen und verwalten. – Die Clientplattform muss SSL-Clientzertifikate unterstützen. |
Um IIS so zu konfigurieren, dass Clientzertifikate akzeptiert werden, öffnen Sie den IIS-Manager, und führen Sie die folgenden Schritte aus:
Klicken Sie in der Strukturansicht auf den Standortknoten.
Doppelklicken Sie im mittleren Bereich auf die Funktion SSL-Einstellungen.
Wählen Sie unter Client-Zertifikate, eine der folgenden Optionen:
- Akzeptieren: IIS akzeptiert ein Zertifikat vom Client, verlangt aber keins.
- Erfordern: Erfordert ein Client-Zertifikat. (Um diese Option zu aktivieren, müssen Sie auch "SSL erforderlich" auswählen.)
Sie können diese Optionen auch in der ApplicationHost.config Datei festlegen:
<system.webServer>
<security>
<access sslFlags="Ssl, SslNegotiateCert" />
<!-- To require a client cert: -->
<!-- <access sslFlags="Ssl, SslRequireCert" /> -->
</security>
</system.webServer>
Das SslNegotiateCert--Flag bedeutet, dass IIS ein Zertifikat vom Client akzeptiert, aber keines erfordert (entspricht der Option "Annehmen" im IIS-Manager). Um ein Zertifikat zu benötigen, legen Sie das SslRequireCert Flag fest. Zum Testen können Sie diese Optionen auch in IIS Express in der lokalen Datei "applicationhost.Config" festlegen, die sich in "Documents\IISExpress\config" befindet.
Erstellen eines Clientzertifikats zum Testen
Zu Testzwecken können Sie MakeCert.exe verwenden, um ein Clientzertifikat zu erstellen. Erstellen Sie zunächst eine Test-Root-Autorität:
makecert.exe -n "CN=Development CA" -r -sv TempCA.pvk TempCA.cer
Makecert fordert Sie auf, ein Kennwort für den privaten Schlüssel einzugeben.
Fügen Sie dann das Zertifikat wie folgt zum Speicher „Vertrauenswürdige Stammzertifizierungsstellen“ des Test-Servers hinzu:
- Öffnen Sie MMC.
- Wählen Sie unter Datei, Snap-In hinzufügen/entfernen.
- Wählen Sie unter Verfügbare Snap-Ins, die Option Zertifikate, und klicken Sie dann auf Hinzufügen.
- Wählen Sie Computerkonto.
- Wählen Sie Lokaler Computer und schließen Sie den Assistenten ab.
- Erweitern Sie im Navigationsbereich den Knoten „Vertrauenswürdige Stammzertifizierungsstellen“.
- Zeigen Sie im Menü Aktion auf Alle Aufgaben, und klicken Sie dann auf Importieren um den Assistenten für den Zertifikatsimport zu starten.
- Suchen Sie nach der Zertifikatsdatei TempCA.cer.
- Klicken Sie auf Öffnen, dann auf Weiter und schließen Sie den Assistenten ab. (Sie werden aufgefordert, das Kennwort erneut einzugeben.)
Erstellen Sie nun ein Clientzertifikat, das vom ersten Zertifikat signiert ist:
makecert.exe -pe -ss My -sr CurrentUser -a sha1 -sky exchange -n "CN=name"
-eku 1.3.6.1.5.5.7.3.2 -sk SignedByCA -ic TempCA.cer -iv TempCA.pvk
Verwenden von Clientzertifikaten in der Web-API
Auf der Serverseite können Sie das Client-Zertifikat abrufen, indem Sie GetClientCertificate in der Anforderungsnachricht aufrufen. Die Methode gibt NULL zurück, wenn kein Clientzertifikat vorhanden ist. Andernfalls gibt es eine X509Certificate2 Instanz zurück. Verwenden Sie dieses Objekt, um Informationen aus dem Zertifikat abzurufen, z. B. den Aussteller und den Betreff. Anschließend können Sie diese Informationen für die Authentifizierung und/oder Autorisierung verwenden.
X509Certificate2 cert = Request.GetClientCertificate();
string issuer = cert.Issuer;
string subject = cert.Subject;