Communardo Software GmbH, Kleiststraße 10 a, D-01129 Dresden

Anbindung des OpenBenno Mailarchivs an ein Active Directory

OpenBenno ist eine unter GPL lizen­zierte E‑Mail Archivierungslösung. Damit ist es mög­lich, die gesetz­li­chen Anforderungen zur Archivierung elek­tro­ni­scher Kommunikation umzu­set­zen. Soll diese Software im Unternehmen ein­ge­setzt wer­den, ist zumeist eine Anbindung an ein vor­han­de­nes Nutzerrepository via LDAP not­wen­dig. Dieser Artikel beschreibt die not­wen­dige Konfiguration der Anbindung an CAS und das Active Directory. Die zusätz­lich not­wen­dige Library, deren Sourcen und eine Beispielkonfiguration kön­nen am Ende des Artikels her­un­ter­ge­la­den werden.

Beschreibung der Konfiguration

Zur Authentifikation und Autorisation benutzt OpenBenno das Spring Security (ehe­mals Acegi) Framework. Dieses ermög­licht die Einbindung der Anwendung in eine Vielzahl von Wirkumgebungen. Die Authentifikation sollte im kon­kre­ten Fall über die Single-Sign-On-Lösung CAS erfol­gen. Die Auflösung der Nutzerberechtigungen wird über die LDAP-Schnittstellt des Active Directorys erfolgen.

Die initiale Einbindung des CAS-Workflows wird von einem EntryPoint ermög­licht, der eine Weiterleitung zur CAS-Login-Seite vornimmt:

<http entry-point-ref="casProcessingFilterEntryPoint">
   <intercept-url pattern="/login.html*" filters="none"/>
   <intercept-url pattern="/images/**" filters="none"/>

   <!-- adjust this role for your needs. "User" is a group, in that (in this case) -->
   <!-- everybody is a member, who should have access to the mail archive. -->
   <intercept-url pattern="/**" access="ROLE_USER"/>

   <form-login login-page='/login.html'/>
   <logout invalidate-session="true" logout-success-url="/login.html" />
</http>

<beans:bean id="casProcessingFilterEntryPoint" class="org.springframework.security.ui.cas.CasProcessingFilterEntryPoint">
   <beans:property name="loginUrl" value="https://www.mycompany.de/cas/login"/>
   <beans:property name="serviceProperties" ref="serviceProperties"/>
</beans:bean>

<beans:bean id="serviceProperties" class="org.springframework.security.ui.cas.ServiceProperties">
   <beans:property name="service" value="http://www.mycompany.de/bennosearch/j_spring_cas_security_check"/>
   <beans:property name="sendRenew" value="false"/>
</beans:bean>

Die Rollendefinition ROLE_USER muss dabei so ange­passt wer­den, dass dort eine Gruppe refe­ren­ziert wird, der alle Nutzer ange­hö­ren, die Zugriff auf das Mailarchiv erhal­ten sol­len. An der Bean casProcessingFilterEntryPoint muss dabei die Login-URL des CAS defi­niert wer­den. In den serviceProperties muss die URL defi­niert wer­den, auf die das CAS bei erfolg­rei­chem Login wei­ter­lei­tet. Wichtig ist dabei die Angabe der spe­zi­el­len URL (/j_spring_cas_security_check), auf wel­che ein spe­zi­el­ler CAS-Filter ange­setzt wird:

<authentication-manager alias="authenticationManagerAlias"/>

<beans:bean id="casProcessingFilter" class="org.springframework.security.ui.cas.CasProcessingFilter">
   <custom-filter after="CAS_PROCESSING_FILTER"/>
   <beans:property name="authenticationManager" ref="authenticationManagerAlias"/>
   <beans:property name="defaultTargetUrl" value="/"/>
   <beans:property name="filterProcessesUrl" value="/j_spring_cas_security_check"/>
</beans:bean>

Die Validierung des CAS-Tickets wird spä­ter von einem custom-authentication-provider durch­ge­führt. Dieser benö­tigt die Basis-URL des CAS:

<beans:bean id="casAuthenticationProvider" class="org.springframework.security.providers.cas.CasAuthenticationProvider">
   <custom-authentication-provider/>
   <beans:property name="userDetailsService" ref="userDetailsService"/>
   <beans:property name="serviceProperties" ref="serviceProperties"/>
   <beans:property name="ticketValidator">
      <beans:bean class="org.jasig.cas.client.validation.Cas20ServiceTicketValidator">
         <beans:constructor-arg index="0" value="https://www.mycompany.de/cas/"/>
      </beans:bean>
   </beans:property>
   <beans:property name="key" value="ticket"/>
</beans:bean>

Bei erfolg­rei­cher Authentifizierung wer­den über den refe­ren­zier­ten userDetailsService die Rollen des Nutzers nach­ge­la­den, wel­che spä­ter ent­schei­den, ob das Mailarchiv über­haupt zugäng­lich ist, und wel­che E‑Mail-Adressen durch­sucht wer­den kön­nen. Dabei wird auf das Active Directory zugegriffen.

<beans:bean id="contextSource" class="org.springframework.security.ldap.DefaultSpringSecurityContextSource">
   <beans:constructor-arg value="ldap://ldap.mycompany.de:3268/dc=mycompany,dc=de"/>
   <beans:property name="userDn" value="cn=publicLogin,cn=Users"/>
   <beans:property name="password" value="publicLoginPassword"/>
</beans:bean>

<beans:bean id="userDetailsService" class="org.springframework.security.userdetails.ldap.LdapUserDetailsService">
   <beans:constructor-arg index="0" ref="userSearch"/>
   <beans:constructor-arg index="1" ref="authoritiesPopulator"/>
</beans:bean>

<beans:bean id="userSearch" class="org.springframework.security.ldap.search.FilterBasedLdapUserSearch">
   <beans:constructor-arg index="0" value="CN=Users"/>
   <beans:constructor-arg index="1" value="(&amp;(sAMAccountName={0})(objectClass=user))"/>
   <beans:constructor-arg index="2" ref="contextSource"/>
</beans:bean>

Die Bean contextSource defi­niert die URL des LDAPs und den zu ver­wen­den­den Basispfad. Weiterhin müs­sen ein öffent­li­cher Nutzer und Passwort für einen erfolg­rei­chen Bind ange­ge­ben wer­den. Die Bean userSearch defi­niert einen Filter zum Auffinden des ein­ge­logg­ten Nutzers, wobei {0} ein Platzhalter für das ein­ge­ge­bene Login ist. Für den refe­ren­zier­ten authoritiesPopulator muss jedoch eine spe­zi­elle Komponente für OpenBenno ver­wen­det werden:

<beans:bean id="authoritiesPopulator" class="de.communardo.openbenno.OpenBennoLdapAuthoritiesPopulator">
   <beans:constructor-arg ref="contextSource"/>
   <beans:constructor-arg value=""/>
   <beans:property name="groupRoleAttribute" value="cn"/>
   <beans:property name="groupSearchFilter" value="(&amp;(member={0})(objectClass=group))"/>
   <beans:property name="rolePrefix" value="ROLE_"/>
   <beans:property name="searchSubtree" value="true"/>
   <beans:property name="convertToUpperCase" value="false"/>
   <beans:property name="mailRoleAttribute" value="mail"/>
</beans:bean>

Dieser authoritiesPopulator ist eine Ableitung vom stan­dard­mä­ßi­gen DefaultLdapAuthoritiesPopulator, der damit um eine Funktion erwei­tert wurde. Es wird nicht nur die Menge an zuge­wie­se­nen Nutzergruppen (aus dem Active Directory) in Rollenbezeichnungen für Spring Security über­führt, son­dern zusätz­lich die E‑Mail-Adresse des Nutzers als spe­zi­elle Rolle mit dem Präfix ROLE_MAIL_ bereit­ge­stellt.

Im kon­kre­ten Fall bezeich­net das Attribut mail des authen­ti­fi­zier­ten Nutzers die jewei­lige E‑Mail-Adresse. Über die Property mailRoleAttribute kann die­ser Wert ange­passt wer­den. Optional kann über die Property roleMailPrefix der Präfix (stan­dard­mä­ßig ROLE_MAIL_) ange­passt wer­den. Für die aktu­elle Version von OpenBenno ist dies jedoch nicht notwendig.

Der OpenBennoLdapAuthoritiesPopulator über­schreibt die getAdditionalRoles-Methode und ent­nimmt ledig­lich das Mail-Attribut aus dem LDAP-Nutzer und stellt diese, zusam­men mit dem Präfix, als neue Authority bereit:

protected Set getAdditionalRoles(DirContextOperations user, String username) {

   String mailAddress = user.getStringAttribute(mailRoleAttribute);
   String role = roleMailPrefix + mailAddress.toLowerCase();
   Set result = new HashSet();
   result.add(new GrantedAuthorityImpl(role));
   return result;
}

Die gesamte Klasse kann im Quellcode und als gepak­tes JAR her­un­ter­ge­la­den werden.

Bereits im ers­ten Codeabschnitt wurde das Logout-Verhalten definiert:

<logout invalidate-session="true" logout-success-url="/login.html" />

Damit wird erreicht, dass nach einem Klick auf den Logout-Button zur Login-Seite gesprun­gen und die Session inva­li­diert wird. Um sich auf der dann gezeig­ten Login-Seite erneut ein­log­gen zu kön­nen, muss LDAP noch für den direk­ten Login kon­fi­gu­riert wer­den. Dies ist durch die Registrierung eines custom-authentication-providers mög­lich:

<beans:bean id="ldapProvider" class="org.springframework.security.providers.ldap.LdapAuthenticationProvider">
   <custom-authentication-provider/>
   <beans:constructor-arg ref="ldapBindAuthenticator" />
   <beans:constructor-arg ref="authoritiesPopulator"/>
</beans:bean>

<beans:bean id="ldapBindAuthenticator" class="org.springframework.security.providers.ldap.authenticator.BindAuthenticator">
   <beans:constructor-arg ref="contextSource"/>
   <beans:property name="userSearch" ref="userSearch" />
</beans:bean>

Mithilfe der beschrie­be­nen Konfigurationsschritte ist die Anbindung von OpenBenno an CAS und LDAP (z.B. Active Directory) mög­lich. Um Ihr OpenBenno ent­spre­chend zu kon­fi­gu­rie­ren, fol­gen Sie bitte die­sen Schritten:

Installationsanweisungen

  1. Getestet für OpenBenno 1.0.7
  2. JAR und Beispiel-XML-Konfiguration herunterladen
  3. XML-Konfiguration ent­spre­chend Ihrer Wirkumgebung anpas­sen und umge­nen­nen (applicationContext-security.xml)
  4. Tomcat stop­pen
  5. JAR deployen
    • tomcat/webapps/bennosearch/WEB-INF/lib/
    • tomcat/webapps/bennosearch.war#/WEB-INF/lib/ (in das WAR der bennosearch-Anwendung)
  6. applicationContext-security.xml deployen
    • tomcat/webapps/bennosearch/WEB-INF/
    • tomcat/webapps/bennosearch.war#/WEB-INF/ (in das WAR der bennosearch-Anwendung)
  7. Tomcat star­ten

Download

Tipps

  • Wenn Sie OpenBenno nur an LDAP anbin­den wol­len, und dabei kein CAS ver­wen­det wer­den soll, kön­nen Sie die beschrie­bene XML-Konfiguration eben­falls benutz­ten. Es müs­sen nur die Bestandteile, die für CAS benö­tigt wer­den, weg­ge­las­sen wer­den (casProcessingFilterEntryPoint, serviceProperties, casProcessingFilter, casAuthenticationProvider, entry-point-ref="casProcessingFilterEntryPoint" und <authentication-manager alias="authenticationManagerAlias"/>).
  • Um bestimm­ten Nutzern geson­derte Leserechte für zusätz­li­che E‑Mail-Adressen zu geben, kön­nen bestimmte Gruppen im Active Directory ange­legt und zuge­wie­sen wer­den. So könnte für eine Support-E-Mail-Adresse support@mycompany.com gewollt sein, dass alle Mitarbeiter diese E‑Mail-Adresse eben­falls im Archiv betrach­ten kön­nen sol­len. Im Active Directory müsste dafür die Gruppe "MAIL_support@mycompany.com" ange­legt und den ent­spre­chen­den Mitarbeitern zuge­wie­sen werden.
19. November 2009
|||

Related Posts

Hi,
ich hätte gerne die Anbindung aus­pro­biert, lei­der las­sen sich das jar Archive und die XML-Konfig nicht downloaden.

Dank für diese Fehlermeldung! Wir haben das Problem beho­ben. Die Dateien las­sen sich nun wie­der herunterladen.

Vielen Dank,
werde dann mal Testen.

Hallo Niels!

Danke für deine Anleitung!
Sind deine Erweiterungen für Benno auch noch pas­send zur aktu­el­len Version 1.1.3?
Muss CAS spe­zi­ell von (http://www.jasig.org/node/579) her­un­ter­la­den und auf dem sel­ben System installieren?

Habe bis­her Probleme die AD-Integration hinzubekommen :-/
Unter /var/log/tomcat6/catalina.out erhalte ich sehr viele Fehler und die Seite http://HOST:8080/bennosearch/start/ lässt sich auch nicht mehr auf­ru­fen. Der Auszug aus dem Log würde hier den Rahmen sprengen.

Gibt es hier evtl. ein Versions-Problem oder sollte ich auf wei­tere Dinge achten?
Haben die Erweiterung andere User bereits pro­blem­los zum Laufen bekommen?

Danke Ralf

Nachtrag:

Sorry – eine Bitte: Wäre es mög­lich noch eine Beispiel-XML-Konfiguration OHNE CAS bereit zu stellen?

Danke für die Mühen! Ralf

Hallo Ralf,

wir haben es noch nicht mit die­ser Benno-Version getes­tet. Allerdings steht das Update auf der Agenda. Dann kann ich dazu mehr sagen und ggf. einen Patch bereit stellen.

Die Konfiguration ohne CAS ist oben unter "Tipps" beschrie­ben. Leider kann ich das momen­tan nicht noch ein­mal testen.

Viele Grüße,
Niels

Hallo Ralf,

wir haben heute das Benno auf die Version 1.1.3 aktua­li­siert. Dort funk­tio­niert die Anbindung auch. Lediglich tauch­ten zwi­schen­zeit­lich ClassNotFound Exceptions im Log auf, dass die Klasse org.springframework.security.providers.cas.CasAuthenticationProvider nicht gefun­den wurde.

Durch den Download der Lib spring-security-cas-client‑2.0.4.jar von [1] und Einpacken ins openbenno.war ließ sich das Problem jedoch schnell lösen. Vielleicht ist das bei dir das selbe Problem?

Viele Grüße,
Niels

1: http://www.docjar.com/jar_detail/spring-security-cas-client‑2.0.4.jar.html

Hallo,
super bei­trag, nur sind alle Download links des Artikels down. 🙁

Comments are closed.

Pin It on Pinterest