Citrix ADC als Identity Provider (IdP) für SAML Authentifizierung

Im folgenden Beitrag möchte ich beispielhaft zwei Webseiten (SAML Service Provider (SP)) über meinen Citrix ADC/Netscaler 13.0 (SAML Identity Provider (IdP))anmelden lassen und ein SSO (Single Sign-On), bzw. ein SLO (Single Log-Out) für die beiden SPs implementieren:

  • Wer sich an einer der beiden Seiten angemeldet hat, wird beim Login auf der zweiten Seite seamless angemeldet und zur Webseite zurückgeleitet.
  • Wer sich an einer der beiden Seiten abgemeldet hat, wird von der zweiten Seite automatisch mit abgemeldet.

Die Konfiguration dazu nehme ich per CLI vor, unter den Überschriften findet ihr allerdings auch jeweils die Web GUI Optionen dazu.

Für meine Konfiguration nehme ich folgende Beispiele zur Demonstration:

IdP URL:                             https://login.company.net
IdP SAML SSO URL:                    https://login.company.net/saml/login
IdP SAML SLO URL:                    https://login.company.net/cgi/tmlogout
SP1 URL:                             https://www.website0815.de
SP1 Assertion Consumer Service URL:  https://www.website0815.de/saml/sp/saml2acs.php
SP1 Logout URL:                      https://www.website0815.de/saml/sp/saml2logout.php
SP2 URL:                             https://www.website4711.de
SP1 Assertion Consumer Service URL:  https://www.website4711.de/saml/sp/saml2acs.php
SP2 Logout URL:                      https://www.website4711.de/saml/sp/saml2logout.php

Das für die Login Page benötigte SSL Zertifikat habe ich mir vorab besorgt und inkl. CA Zertifikaten importiert. Die Signing Zertifikate der Service Provider wurden vorab von diesen geliefert und ebenfalls importiert. Das eigene SAML Signing Zertifikat habe ich self-signed auf dem Netscaler erstellt. Im NetScaler sind die Zertifikate wie folgt benannt:

IdP Public Zertifikat:              SSL.Cert_company.net  ->  es empfiehlt sich ein Wildcard Zertifikat oder ein Zertifikat mit allen DNS-Namen im SAN, die über den NetScaler verfügbar gemacht werden (also nicht nur login....)
IdP SAML Signing Zertifikat:        SSL.Cert_login.company.net_SAML
SP1 SAML Signing Zertifikat:        SSL.Cert_www.website0815.de_SAML
SP2 SAML Signing Zertifikat:        SSL.Cert_www.website4711.de_SAML
SAML IdP Konfiguration

LDAP Server Policy

Security / AAA – Application Traffic / Policies / Authentication / Basic / LDAP

Als ersten Schritt benötige ich natürlich eine interne Authentifizierungsquelle, also einen Server mit Benutzerdaten. Im folgenden Beispiel verwende ich dazu einen regulären LDAP Server, also kein Active Directory. Dementsprechend sind die Attribute, die ich aus meiner Authentifizierungsquelle auslese, in ihrer Benennung LDAP-konform. Wird ein Active Directory per LDAP ausgelesen, sind die Attribute entsprechend nach Microsoft-Konvention anzupassen.

Mein interner LDAP(S) Server hat beispielhaft folgende Eigenschaften:

IP-Adresse:                  192.168.1.11
LDAP User Base OU:           OU=user,DC=authentication,DC=source
LDAP Binding User Name:      nsbinduser
LDAP Binding User Passwort:  H1ghSecur3P@ss
LDAP Protokoll/Port:         LDAPS / TCP636

Daraus erstelle ich mir folgende LDAP Server Action und Authentication Policy:

add authentication ldapAction AAA.Auth.LDAP.Srv_authentication.source -serverIP 192.168.1.11 -serverPort 636 -secType SSL -ldapBase "OU=users,DC=authentication,DC=source" -ldapBindDn "CN=nsbinduser,OU=admin,DC=authentication,DC=source" -ldapBindDnPassword H1ghSecur3P@ss -ldapLoginName mail -groupAttrName memberOf -subAttributeName cn -passwdChange ENABLED -Attribute1 sn -Attribute2 givenName -Attribute3 mail -Attribute4 street -Attribute5 postalCode -Attribute6 streetAddress -Attribute7 co -Attribute8 telephoneNumber
add authentication Policy AAA.Auth.Pol_LDAP_authentication.source -rule true -action AAA.Auth.LDAP.Srv_authentication.source

Insgesamt lese ich mit dieser LDAP Server-Policy aus meinem LDAPS Server neben den Credentials acht weitere Attribute aus, die ich später in meiner SAML IdP Konfiguration weiterverwenden kann (z.B. in Form der Attribute, die mit dem SAML-Token an den Service Provider mit übergeben werden). Zudem aktiviere ich die Möglichkeit, das Passwort der LDAP User zu ändern.

SAML IDP Profile

Security / AAA – Application Traffic / Policies / Authentication / Advanced / SAML IDP

In den Profilen werden primär folgende Punkte definiert:

  • wer mit wem und wie?
  • was?

SAML IDP Profile haben eine Menge konfiguierbarer Parameter, teils Pflicht, teils optional:

add authentication samlIdPProfile <Name> [-samlSPCertName <String> [-encryptAssertion (ON|OFF) [-keyTransportAlg (RSA-V1_5|RSA_OAEP)]]] [-samlIdPCertName <String>] [-assertionConsumerServiceURL <URL>] [-sendPassword (ON|OFF)] [-samlIssuerName <String>] [-rejectUnsignedRequests (ON|OFF)] [-signatureAlg (RSA-SHA1|RSA-SHA256)] [-digestMethod (SHA1|SHA256)] [-audience <String>] [-NameIDFormat (Unspecified|emailAddress|X509SubjectName|WindowsDomainQualifiedName|kerberos|entity|persistent|transient)] [-NameIDExpr <String>] [-encryptionAlgorithm (DES3|AES128|AES192|AES256)] [-samlBinding (REDIRECT|POST|ARTIFACT)] [-skewTime <Minuten>] [-serviceProviderID <String>] [-signAssertion (NONE|ASSERTION|RESPONSE|BOTH)] [-SPLogoutUrl <String>] [-logoutBinding (REDIRECT|POST)] [-Attribute1 <String> -Attribute1Expr <String> [-Attribute1FriendlyName <String>] [-Attribute1Format (URI|Basic)]] [-Attribute2 <String> -Attribute2Expr <String> [-Attribute2FriendlyName <String>] [-Attribute2Format (URI|Basic)]] [-Attribute3 <String> -Attribute3Expr <String> [-Attribute3FriendlyName <String>] [-Attribute3Format (URI|Basic)]] [-Attribute4 <String> -Attribute4Expr <String> [-Attribute4FriendlyName <String>] [-Attribute4Format (URI|Basic)]] [-Attribute5 <String> -Attribute5Expr <String> [-Attribute5FriendlyName <String>] [-Attribute5Format (URI|Basic)]] [-Attribute6 <String> -Attribute6Expr <String> [-Attribute6FriendlyName <String>] [-Attribute6Format (URI|Basic)]] [-Attribute7 <String> -Attribute7Expr <String> [-Attribute7FriendlyName <String>] [-Attribute7Format (URI|Basic)]] [-Attribute8 <String> -Attribute8Expr <String> [-Attribute8FriendlyName <String>] [-Attribute8Format (URI|Basic )]] [-Attribute9 <String> -Attribute9Expr <String> [-Attribute9FriendlyName <String>] [-Attribute9Format (URI|Basic)]] [-Attribute10 <String> -Attribute10Expr <String> [-Attribute10FriendlyName <String>] [-Attribute10Format (URI|Basic)]] [-Attribute11 <String> -Attribute11Expr <String> [-Attribute11FriendlyName <String>] [-Attribute11Format (URI|Basic)]] [-Attribute12 <String> -Attribute12Expr <String> [-Attribute12FriendlyName <String>] [-Attribute12Format (URI|Basic)]] [-Attribute13 <String> -Attribute13Expr <String> [-Attribute13FriendlyName <String>] [-Attribute13Format (URI|Basic)]] [-Attribute14 <String> -Attribute14Expr <String> [-Attribute14FriendlyName <String>] [-Attribute14Format (URI|Basic)]] [-Attribute15 <String> -Attribute15Expr <String> [-Attribute15FriendlyName <String>] [-Attribute15Format (URI|Basic)]] [-Attribute16 <String> -Attribute16Expr <String> [-Attribute16FriendlyName <String>] [-Attribute16Format (URI|Basic)]]

In meinem Beispiel definiere ich hier einerseits, dass das Email-Attribut als Benutzername verwendet wird und dass im SAML Token noch die Attribute Nachname, Vorname, Email-Adresse und Gruppenmitgliedschaften übermittelt werden.

add authentication samlIdPProfile AAA.Auth.SamlIdp.Prof_www.website0815.de -samlSPCertName SSL.Cert_www.website0815.de_SAML -samlIdPCertName SSL.Cert_login.company.net_SAML -assertionConsumerServiceURL "https://www.website0815.de/saml/sp/saml2acs.php" -samlIssuerName login.company.net -serviceProviderID www.website0815.de -signatureAlg RSA-SHA256 -digestMethod SHA256 -SPLogoutUrl "https://www.website0815.de/saml/sp/saml2logout.php" -NameIDFormat emailAddress -Attribute1 lastname -Attribute1Expr "AAA.USER.ATTRIBUTE(1)" -Attribute1Format URI -Attribute2 firstname -Attribute2Expr "AAA.USER.ATTRIBUTE(2)" -Attribute2Format URI -Attribute3 mail -Attribute3Expr "AAA.USER.ATTRIBUTE(3)" -Attribute3Format URI -Attribute4 groups -Attribute4Expr AAA.USER.GROUPS -Attribute4Format URI
add authentication samlIdPProfile AAA.Auth.SamlIdp.Prof_www.website4711.de -samlSPCertName SSL.Cert_www.website4711.de_SAML -samlIdPCertName SSL.Cert_login.company.net_SAML -assertionConsumerServiceURL "https://www.website4711.de/saml/sp/saml2acs.php" -samlIssuerName login.company.net -serviceProviderID www.website4711.de -signatureAlg RSA-SHA256 -digestMethod SHA256 -SPLogoutUrl "https://www.website4711.de/saml/sp/saml2logout.php" -NameIDFormat emailAddress -Attribute1 lastname -Attribute1Expr "AAA.USER.ATTRIBUTE(1)" -Attribute1Format URI -Attribute2 firstname -Attribute2Expr "AAA.USER.ATTRIBUTE(2)" -Attribute2Format URI -Attribute3 mail -Attribute3Expr "AAA.USER.ATTRIBUTE(3)" -Attribute3Format URI -Attribute4 groups -Attribute4Expr AAA.USER.GROUPS -Attribute4Format URI

Anmerkung zu den Attribut-Parametern:

  • AAA.USER.ATTRIBUTE(1) = Attribute1 aus AAA.Auth.LDAP.Srv_authentication.source = Nachname
  • AAA.USER.ATTRIBUTE(2) = Attribute2 aus AAA.Auth.LDAP.Srv_authentication.source = Vorname
  • AAA.USER.ATTRIBUTE(3) = Attribute3 aus AAA.Auth.LDAP.Srv_authentication.source = Email-Adresse
  • AAA.USER.GROUPS = MemberOf aus AAA.Auth.LDAP.Srv_authentication.source = Gruppenmitgliedschaft

SAML IDP Policies

Security / AAA – Application Traffic / Policies / Authentication / Advanced / SAML IDP

Mit zwei SAML IdP Policies bestimme ich nun Regeln, bei denen das SAML IdP Profil angewendet wird. Beide Policies müssen mit der Expression true definiert werden.

add authentication samlIdPPolicy AAA.Auth.SamlIdp.Pol_www.website0815.de -rule true -action AAA.Auth.SamlIdp.Prof_www.website0815.de
add authentication samlIdPPolicy AAA.Auth.SamlIdp.Pol_www.website4711.de -rule true -action AAA.Auth.SamlIdp.Prof_www.website4711.de
Authentication Login Page

Da SAML ein Web-basiertes Anmeldeprotokoll ist, benötigt man logischerweise eine Webseite mit Anmeldefunktion. Im NetScaler lässt sich dies auf mehrere Arten bewerkstelligen, zwei davon findet ihr hier:

  • Authentication Virtual Server (addressable)
  • Authentication Virtual Server (non-addressable) mit vorgeschaltetem Content Switching Virtual Server (addressable) (oder alternativ mit Load Balancing Virtual Server)

Es gibt natürlich noch mehr Möglichkeiten und Kombinationen, auf die gehe ich jetzt aber auch nicht im Detail ein. Was der Unterschied zwischen addressable und non-addressable Servern an sich ist, erkläre ich in diesem Beitrag jetzt nicht extra, das sollte klar sein, wenn man NetScaler administriert. Deshalb hier nur kurz eine Erklärung, warum ein Content Switching Virtual Server nützlich sein kann:

  • In großen Unternehmen eher kein Thema, bei kleinen Firmen und Privatpersonen schon: die IP-Adressen! Durch den vorgelagerten Content Switching Virtual Server lassen sich über eine (öffentliche) IP mehrere Server und Serverarten veröffentlichen. Möchte man z.B. einen Authentication Virtual Server und einen Gateway Virtual Server über eine IP und über einen Port bereitstellen, ist der Weg über den Content Switching Virtual Server die beste Option, dies zu realisieren.

Option 1: Authentication Virtual Server (addressable)

Authentication Virtual Server

Security / AAA – Application Traffic / Virtual Servers

add authentication vserver AAA.vSrv_login.company.net SSL 192.168.1.111 443
bind ssl vserver AAA.vSrv_login.company.net -certkeyName SSL.Cert_company.net
bind authentication vserver AAA.vSrv_login.company.net -policy AAA.Auth.Pol_LDAP_authentication.source -priority 100 -gotoPriorityExpression NEXT
bind authentication vserver AAA.vSrv_login.company.net -policy AAA.Auth.SamlIdp.Pol_www.website0815.de -priority 100 -gotoPriorityExpression NEXT
bind authentication vserver AAA.vSrv_login.company.net -policy AAA.Auth.SamlIdp.Pol_www.website4711.de -priority 110 -gotoPriorityExpression NEXT

Option 2: Authentication Virtual Server (non-addressable) mit vorgeschaltetem Content Switching Virtual Server (addressable)

Authentication Virtual Server

Security / AAA – Application Traffic / Virtual Servers

Wie bei Option 1 konfiguriere ich auch bei Option 2 einen AuthenticationVirtual Server. Im Gegensatz zu Option 1 ist der Server jetzt jedoch non-addressable, d.h. ich konfiguriere 0.0.0.0 als IP Adresse ohne Port. Die restlichen Einstellungen können aus Option 1 übernommen werden.

add authentication vserver AAA.vSrv_login.company.net SSL 0.0.0.0
bind ssl vserver AAA.vSrv_login.company.net -certkeyName SSL.Cert_company.net
bind authentication vserver AAA.vSrv_login.company.net -policy AAA.Auth.Pol_LDAP_authentication.source -priority 100 -gotoPriorityExpression NEXT
bind authentication vserver AAA.vSrv_login.company.net -policy AAA.Auth.SamlIdp.Pol_www.website0815.de -priority 100 -gotoPriorityExpression NEXT
bind authentication vserver AAA.vSrv_login.company.net -policy AAA.Auth.SamlIdp.Pol_www.website4711.de -priority 110 -gotoPriorityExpression NEXT

Content Switching Action

Traffic Management / Content Switching / Actions

Nachdem der Authentication Virtual Server (non-addressable) konfiguriert ist, wird mit der Action nun definiert, dass dieser auch über einen Content Switching Virtual Server angesprochen werden kann.

add cs action CS.Act_login.company.net -targetVserver AAA.vSrv_login.company.net

Content Switching Policy

Traffic Management / Content Switching / Policies

Mit einer Content Switching Policy werden jetzt Regeln bestimmt, bei denen die Content Switching Action angewendet wird. In meinem Beispiel wird mit der Regel definiert, dass die Action Anwendung findet, wenn die aufgerufene URL den String login.company.net (also die URL meines SAML IdP) enthält.

add cs policy CS.Pol_login.company.net -rule "HTTP.REQ.URL.SET_TEXT_MODE(IGNORECASE).CONTAINS(\"login.company.net\")" -action CS.Act_login.company.net

Content Switching Virtual Server

Traffic Management / Content Switching / Virtual Server

Wie oben bereits geschrieben könnte der Content Switching Virtual Server für weitere Services verwendet werden. Dementsprechend benenne ich ihn jetzt auch nicht mehr nur im Hinblick auf die Login-Seite, sondern „allgemeiner“. Im Gegensatz zu Option 1 hält der Content Switching Virtual Server nun die erreichbare IP-Adresse und ist somit adressierbar.

add cs vserver CS.vSrv_company.net SSL 192.168.1.111 443 -cltTimeout 180 -persistenceType NONE
bind ssl vserver CS.vSrv_company.net -certkeyName SSL.Cert_company.net
bind cs vserver CS.vSrv_company.net -policyName CS.Pol_login.company.net -priority 100
Single Log-Out

Mit der vorangegangen Konfiguration wurde das SSO für die zwei Webseiten implementiert. Gleichzeitig hab ich bereits in den SAML IdP Policies die Logout Redirect URLs der Service Provider hinterlegt. Unsere IdP SLO URL müssen die Hoster der Webseiten natürlich wissen und in ihrer SAML SP Konfiguration entsprechend hinterlegen. Beim Netscaler lautet sie für AAA Virtual Server  https://<URL>/cgi/tmlogout.

Für das SLO ist seitens des Netscalers eigentlich keine zusätzliche Konfiguration mehr erforderlich. Der Netscaler schaut beim Logout eines Service Providers in der Konfiguration nach weiteren Service Providern und sendet sog. Back-Channel Logout Requests zu allen weiteren Service Providern, von denen der entsprechende User abgemeldet werden soll. Damit Back-Channel SLO funktioniert, müssen lediglich folgende Voraussetzungen erfüllt sein:

  • DNS: Der Netscaler muss den SLO Endpunkt FQDN zu seiner IP-Adress auflösen können.
  • Firewall: Die Netscaler SNIP muss die aufgelöste IP-Adresse erreichen können über den Port der SLO URL (i.d.R. HTTPS, also TCP/443)
  • Service Provider: Der SP muss die Back-Channel Logout Funktion unterstützen.

Quellen:
https://docs.citrix.com/en-us/citrix-adc/13/aaa-tm/saml-authentication/citrix-adc-saml-idp.html
https://support.citrix.com/article/CTX221631
https://support.citrix.com/article/CTX228135
https://support.citrix.com/article/CTX253927

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert

Diese Website verwendet Akismet, um Spam zu reduzieren. Erfahre mehr darüber, wie deine Kommentardaten verarbeitet werden.