Inhaltsverzeichnis

MFA mit fudiscr und wahlweise Password/SPNEGO als erstem Faktor

(zurück zur fudiscr-Seite)

Wichtiger Hinweis

Die folgende Anleitung setzt voraus, dass Kerberos-Login bzw. SPNEGO gemäß der Anleitung im Shibboleth-Wiki als Extended Flow des Password Login Flows eingerichtet wurde.

SPNEGO als eigenständiger Flow

Damit authn/SPNEGO als unabhängiger, eigenständiger Flow angesprochen werden kann, muss zunächst die Referenz als Extended Flow in der authn/Password-Konfiguration entfernt oder zumindest auskommentiert werden:

./conf/authn/password-authn-config.xml
    <!--
    <bean id="shibboleth.authn.Password.ExtendedFlows" class="java.lang.String" c:_0="SPNEGO" />
    <util:list id="shibboleth.authn.Password.ExtendedFlowParameters">
        <value>_shib_idp_SPNEGO_enable_autologin</value>
    </util:list>
    -->

In ./conf/authn/authn-event-flow.xml müssen folgende Einträge ergänzt werden:

./conf/authn/authn-events-flow.xml
    <!-- ... -->
    <end-state id="SPNEGO" />
    <global-transitions>
        <transition on="SPNEGO" to="SPNEGO" />
        <transition on="#{!'proceed'.equals(currentEvent.id)}" to="InvalidEvent" />
    </global-transitions>
    <!-- ... -->

Weiterhin muss der SPNEGO-Button im Login-Template überarbeitet werden (mensch beachte die eventId). Gemeinsam mit dem Username/Password-Button sieht dies dann folgendermaßen aus:

./views/login.vm
    <!-- ... -->
    <div class="grid">
        <div class="grid-item">
          <button type="submit" name="_eventId_proceed"
             onClick="this.childNodes[0].nodeValue='#springMessageText("idp.login.pleasewait", "Logging in, please wait...")'">
             #springMessageText("idp.login.login", "Login")
          </button>
        </div>
        <div class="grid-item">
          <button type="submit" name="_eventId_SPNEGO">
             #springMessageText("idp.login.SPNEGO", "One-Click Kerberos Login")
          </button>
        </div>
    </div>
    <!-- ... -->

authn/SPNEGO erwartet als eigenständiger Flow, dass Autologin aktiviert ist (um es dann zu deaktivieren). Dies lässt sich über folgenden Parameter bewerkstelligen:

./conf/authn/authn.properties
idp.authn.SPNEGO.enforceRun = true


Spezifische fudiscr-MFA-Konfiguration

Zunächst in die entsprechende Transition Map definieren:

./conf/authn/mfa-authn-config.xml
    <!-- ... -->
    <util:map id="shibboleth.authn.MFA.TransitionMap">
        <entry key="">
            <bean parent="shibboleth.authn.MFA.Transition" p:nextFlow="authn/Password"/>
        </entry>
        <entry key="authn/Password">
            <bean parent="shibboleth.authn.MFA.Transition">
                <property name="nextFlowStrategyMap">
                    <map>
                        <entry key="SPNEGO" value="authn/SPNEGO" />
                        <entry key="proceed" value-ref="checkSecondFactor" />
                    </map>
                </property>
            </bean>
        </entry>
        <entry key="authn/SPNEGO">
            <bean parent="shibboleth.authn.MFA.Transition">
                <property name="nextFlowStrategyMap">
                    <map>
                        <entry key="InvalidCredentials" value="authn/Password" />
                        <entry key="proceed" value-ref="checkSecondFactor" />
                    </map>
                </property>
            </bean>
        </entry>
    </util:map>
    <!-- ... -->

Die Liste der supported Principals um den entsprechenden Kerberos-Eintrag erweitern:

./conf/authn/authn.properties
idp.authn.MFA.supportedPrincipals = \
    saml2/urn:oasis:names:tc:SAML:2.0:ac:classes:InternetProtocol, \
    saml2/urn:oasis:names:tc:SAML:2.0:ac:classes:PasswordProtectedTransport, \
    saml2/urn:oasis:names:tc:SAML:2.0:ac:classes:Password, \
    saml2/urn:oasis:names:tc:SAML:2.0:ac:classes:Kerberos, \
    saml2/urn:de:zedat:fudis:SAML:2.0:ac:classes:CR

Falls für die weitere Verarbeitung im IdP die User Id ohne Realm benötigt wird (entsprechende Transformationen in der c14n-Config vorausgesetzt), gilt es zu verhindern, dass der MFA-Flow mit zwei unterschiedlichen Usernames bzw. „Username Principals“ arbeitet - einmal mit, einmal ohne Realm. Daher muss fudiscr daran gehindert werden, die User Id aus der Authentisierung mit dem zweiten Faktor weiter zu verarbeiten:

./conf/authn/fudiscr.properties
fudiscr.result_with_username_principal=shibboleth.Conditions.FALSE

Sowie in ./conf/c14n/subject-c14n.xml in der Liste der PostLoginSubjectCanonicalizationFlows nach <ref bean=„c14n/simple“ /> die Referenz <ref bean=„c14n/fudiscr“ /> einfügen:

./conf/c14n/subject-c14n.xml
    <!-- ... -->
    <util:list id="shibboleth.PostLoginSubjectCanonicalizationFlows">
        <!-- was auch immer sonst hier steht -->
        <ref bean="c14n/x500" />
        <ref bean="c14n/simple" />
        <ref bean="c14n/fudiscr" />
    </util:list>
    <!-- ... -->

Analog zu idp.authn.Password.reuseCondition sollte auch die Condition für idp.authn.SPNEGO.reuseCondition gesetzt werden, also z.B.

./conf/authn/authn.properties
idp.authn.MFA.reuseCondition=shibboleth.Conditions.FALSE
idp.authn.Password.reuseCondition=shibboleth.Conditions.TRUE
idp.authn.SPNEGO.reuseCondition=shibboleth.Conditions.TRUE
idp.authn.fudiscr.reuseCondition=shibboleth.Conditions.FALSE