Inhaltsverzeichnis

Enhanced Client or Proxy (ECP)

Die ECP-Schnittstelle eines IdP ist für die Kommunikation mit nicht-browserbasierten Clients da. Das grundlegende Konzept ist im Shibboleth Wiki dokumentiert. ECP ist im Shibboleth-IdP standardmäßig aktiv.

Achten Sie darauf, dass das ECP-SSO-Binding des IdPs in den DFN-AAI-Metadaten angegeben ist. Fehlt es, finden ECP-Clients den IdP nicht, wenn Sie sich anmelden wollen.

400

Zum Testen eignet sich das vom CILogon Projekt bereitgestellte Testscript 'testecp.sh'.

Schutz mit Basic-Auth nötig

Viele Sync&Share-Clients kommen mit der ECP-Variante des Shibboleth IdP leider nicht zurecht. Der ECP-Endpunkt muss für diese Clients noch explizit mit Basic-Auth geschützt werden. Dies kann mithilfe von Apache oder Tomcat gemacht werden - einfacher ist die Apache-Variante.

Entweder: ECP-Endpunkt mit Apache Basic-Auth schützen

Authentifizierung per LDAP im Apache aktivieren:

root@idp:~# a2enmod authnz_ldap
root@idp:~# systemctl reload apache2
/etc/apache2/sites-available/idp.hochschule-XY.de.conf
#
# - Definition des LDAP-Server-Root-CA-Zertifikates außerhalb der VirtualHost-Direktive
# - hier am Beispiel der DFN-PKI, bitte anpassen
# - Abweichende Einträge in /etc/ldap/ldap.conf überschreiben diesen Eintrag.
#
LDAPTrustedGlobalCert CA_BASE64 /etc/ssl/certs/T-TeleSec_GlobalRoot_Class_2.pem
 
<VirtualHost *:443>
  ServerName              idp.hochschule-XY.de:443
  ...
  # ECP-Config für Sync&Share-Clients
  <Location /idp/profile/SAML2/SOAP/ECP>
    AuthType Basic
    AuthName "idp.hochschule-XY.de - ECP profile"
    AuthBasicProvider ldap
    AuthLDAPURL "ldaps://ldap.hochschule-XY.de/ou=people,dc=hochschule-xy,dc=de?uid?sub"
    AuthLDAPBindDN "cn=idp,cn=systemusers,dc=hochschule-xy,dc=de"
    AuthLDAPBindPassword "geheim007"
    Require valid-user
  </Location>
</VirtualHost>

Oder: ECP-Endpunkt mit Tomcat Basic-Auth schützen

FIXME prüfen!

Wir empfehlen, die ECP-Schnittstelle über den Webserver zu schützen, wenn dies in Ihrer Umgebung möglich ist.

Zunächst aktivieren Sie folgende Blöcke in ./edit-webapp/WEB-INF/web.xml:

./edit-webapp/WEB-INF/web.xml
    ...
    <!--
    Uncomment to use container managed authentication. The new servlet spec (3.1)
    supports "**" as a wildcard syntax to avoid role usage, which is normally desirable.
    Older containers usually support "*" when proprietary options are used (e.g., Jetty
    requires setting the Strict property on the SecurityManager.)
    -->
    <security-constraint>
        <display-name>Web Login Service</display-name>
        <web-resource-collection>
            <web-resource-name>user authentication</web-resource-name>
            <url-pattern>/Authn/RemoteUser</url-pattern>
            <url-pattern>/profile/SAML2/SOAP/ECP</url-pattern>
            <http-method>POST</http-method>·
        </web-resource-collection>
        <auth-constraint>
            <role-name>**</role-name>
        </auth-constraint>
        <user-data-constraint>
            <transport-guarantee>CONFIDENTIAL</transport-guarantee>·
        </user-data-constraint>
    </security-constraint>
 
    <!-- Uncomment if you want BASIC auth managed by the container. -->
    <login-config>
        <auth-method>BASIC</auth-method>
        <realm-name>Web Login Service</realm-name>
    </login-config>
    ...

Passen Sie das Context Fragment in der Tomcat-Konfiguration an. Das sieht dann ungefähr so aus (appName, Pfade etc. ggf. anpassen):

/etc/tomcat9/Catalina/localhost/idp.xml
<Context docBase="/opt/shibboleth-idp/war/idp.war"
         privileged="true"
         antiResourceLocking="false"
         unpackWAR="true"
         swallowOutput="true">
  <Realm className="org.apache.catalina.realm.JAASRealm" appName="ShibUserPassAuth"/>
</Context>

Geben Sie Tomcat den Pfad zur JAAS login.config als Startparameter mit:

/etc/default/tomcat9
JAVA_OPTS=" ... -Djava.security.auth.login.config=file:/opt/shibboleth-idp/login.config ..."

Legen Sie die Datei ./login.config an:

/opt/shibboleth-idp/login.config
ShibUserPassAuth {
   org.ldaptive.jaas.LdapLoginModule required
      ldapUrl="..."
      ssl="true"
      bindDn="..."
      bindCredential="..."
      baseDn="..."
      userFilter="uid={user}"
      logCredentials="false"
   ;
};

Starten Sie Tomcat neu.

Schutz vor Brute-Force

Da dieser Endpunkt weltweit erreichbar sein muss, können hier auch Brute-Force-Passwort-Angriffe auftreten. Diesen sollten ebenfalls mithilfe von fail2ban begegnet werden, siehe die fail2ban-Seite in diesem Wiki.

Funktionstest

Um die grundsätzliche Funktionalität zu testen, kann einer der aus der Shibboleth-Community bereitgestellten Clients verwendet werden, siehe die Contributions-Seite im Shibboleth Wiki. Das folgende Beispiel bezieht sich auf ecp.sh:

Zunächst die Dokumentation in den ersten Zeilen des Skripts durchlesen und unter ecp_endpoints einen Alias für den zu testenden IdP setzen, z.B.

["Campus01"]="https://idp.example.org/idp/profile/SAML2/SOAP/ECP"

Dann kann der Client mit einem beliebigen (Test-)User (hier: „tester“) verwendet werden:

user@idp:~# ./ecp.sh -d Campus01 https://testsp3.aai.dfn.de/ecp-test/index.txt tester

Beim danach erscheinenden Passwort-Prompt das Passwort des (Test-)Users eingeben. Wenn alles funktioniert, wird im Anschluss an den Debug-Output ein „ok“ zurückgegeben.

ECP einschränken auf einzelne SPs

Aus unserer Sicht ist es nicht nötig, die ECP-Unterstützung auf einzelne SPs einzuschränken. Der Vollständigkeit halber sei hier jedoch gezeigt, wie das geht: Sie müssten in /opt/shibboleth-idp/conf/relying-party.xml im Abschnitt DefaultRelyingParty die Referenz auf das Bean SAML2.ECP auskommentieren. Weiter unten fügen Sie in der Liste der RelyingPartyOverrides eine Konfiguration für die gewünschten SPs hinzu.

Mit diesem Beispiel erlauben Sie den Zugriff auf die ECP-Schnittstelle nur für bwIDM-SPs:

/opt/shibboleth-idp/conf/relying-party.xml
<bean id="shibboleth.DefaultRelyingParty" parent="RelyingParty">
  <property name="profileConfigurations">
    <list>
        <bean parent="Shibboleth.SSO" 
              p:postAuthenticationFlows="#{{'terms-of-use', 'attribute-release'}}"
              p:includeAttributeStatement="true" />
          <ref bean="SAML1.AttributeQuery" />
          <ref bean="SAML1.ArtifactResolution" />
          <bean parent="SAML2.SSO"
                p:nameIDFormatPrecedence="urn:oasis:names:tc:SAML:2.0:nameid-format:transient" 
                p:postAuthenticationFlows="#{{'terms-of-use', 'attribute-release'}}" />
          <ref bean="SAML2.Logout" />
          <ref bean="SAML2.ArtifactResolution" />
    </list>
  </property>
</bean>
 
<util:list id="shibboleth.RelyingPartyOverrides">
 
 <bean parent="RelyingPartyByTag">
   <constructor-arg name="candidates">
     <list>
        <bean parent="TagCandidate" c:name="http://macedir.org/entity-category"
              p:values="http://aai.dfn.de/category/bwidm-member"/>
     </list>
   </constructor-arg>
   <property name="profileConfigurations">
     <list>
        <ref bean="SAML2.ECP" />
        <ref bean="SAML2.AttributeQuery" />
        <bean parent="SAML2.SSO" 
              p:postAuthenticationFlows="#{{'terms-of-use', 'attribute-release'}}"
              p:nameIDFormatPrecedence="#{{'urn:oasis:names:tc:SAML:2.0:nameid-format:persistent', 'urn:oasis:names:tc:SAML:2.0:nameid-format:transient'}}"
                   />
        <ref bean="SAML2.Logout" />
        <ref bean="SAML2.ArtifactResolution" />
     </list>
   </property>
 </bean>
 
</util:list>