diff --git a/mvn-build/src/docbkx/configuration.xml b/mvn-build/src/docbkx/configuration.xml index 9555a24f..9c5578f4 100644 --- a/mvn-build/src/docbkx/configuration.xml +++ b/mvn-build/src/docbkx/configuration.xml @@ -33,7 +33,18 @@ - Authentication + DirContext Authentication + + When DirContext instances are created to be used for performing + operations on an LDAP server these contexts often need to be authenticated. There are + different options for configuring this using Spring LDAP, described in this chapter. + + This section refers to authenticating contexts in the core functionality + of the ContextSource - to construct DirContext instances + for use by LdapTemplate. LDAP is commonly used for the sole purpose + of user authentication, and the ContextSource may be used for that as + well. This process is discussed in . + Authenticated contexts are created for both read-only and read-write operations by default. You specify @@ -43,7 +54,9 @@ The userDn needs to be the full - Distinguished Name (DN) of the user. + Distinguished Name (DN) of the user from the root of the LDAP tree, + regardless of whether a base LDAP path has been supplied to + the ContextSource. Some LDAP server setups allow anonymous read-only access. If you @@ -51,8 +64,49 @@ anonymousReadOnly property to true. + + Custom DirContext Authentication Processing + + The default authentication mechanism used in Spring LDAP is SIMPLE authentication. + This means that in the user DN (as specified to the userDn property) and + the credentials (as specified to the password) are set in + the Hashtable sent to the DirContext implementation constructor. + There are many occasions when this processing is not sufficient. For instance, + LDAP Servers are commonly set up to only accept communication on a secure TLS channel; + there might be a need to use the particular LDAP Proxy Auth mechanism, etc. + It is possible to specify an alternative authentication mechanism by supplying a + DirContextAuthenticationStrategy implementation to the ContextSource + in the configuration. + + TLS + + Spring LDAP provides two different configuration options for LDAP servers requiring TLS secure + channel communication: DefaultTlsDirContextAuthenticationStrategy and + ExternalTlsDirContextAuthenticationStrategy. Both these + implementations will negotiate a TLS channel on the target connection, but they differ in the actual authentication mechanism. + Whereas the DefaultTlsDirContextAuthenticationStrategy will apply SIMPLE authentication + on the secure channel (using the specified userDn and password), + the ExternalDirContextAuthenticationStrategy will use EXTERNAL SASL authentication, + applying a client certificate configured using system properties for authentication. + + Since different LDAP server implementations respond differently to explicit shutdown of the + TLS channel (some servers require the connection be shutdown gracefully; others do not support it), + the TLS DirContextAuthenticationStrategy implementations support specifying + the shutdown behavior using the shutdownTlsGracefully parameter. If this + property is set to false (the default), no explicit TLS shutdown will happen; + if it is true, Spring LDAP will try to shutdown the TLS channel gracefully + before closing the target context. + + When working with TLS connections you need to explicitly turn off + the native LDAP Pooling functionality by setting the pooled property to false, + particularly if shutdownTlsGracefully is set to false. + However, since the TLS channel negotiation process is quite expensive, great performance benefits will + be gained by using the Spring LDAP Pooling Support, described in . + + + - Custom Authentication Using Acegi + Custom Principal and Credentials Management While the user name (i.e. user DN) and password used for creating an authenticated Context are static by @@ -71,25 +125,26 @@ time an authenticated Context is to be created. - To use the authentication information of the currently logged in - user using Acegi - Security, use the - AcegiAuthenticationSource: + If you are using Spring Security + you can make sure the principal and credentials of the currently logged in user + is used at all times by configuring your ContextSource + with an instance of the SpringSecurityAuthenticationSource + shipped with Spring Security. - The Spring bean definition for an - AcegiAuthenticationSource + The Spring bean definition for a + SpringSecurityAuthenticationSource <beans> ... <bean id="contextSource" class="org.springframework.ldap.core.support.LdapContextSource"> <property name="url" value="ldap://localhost:389" /> <property name="base" value="dc=example,dc=com" /> - <property name="authenticationSource" ref="acegiAuthenticationSource" /> + <property name="authenticationSource" ref="springSecurityAuthenticationSource" /> </bean> - <bean id="acegiAuthenticationSource" - class="org.springframework.ldap.authentication.AcegiAuthenticationSource" /> + <bean id="springSecurityAuthenticationSource" + class="org.springframework.security.ldap.SpringSecurityAuthenticationSource" /> ... </beans> @@ -103,8 +158,8 @@ - When using the AcegiAuthenticationSource - you need to use Acegi's + When using the SpringSecurityAuthenticationSource + you need to use Spring Security's LdapAuthenticationProvider to authenticate the users against LDAP. @@ -113,7 +168,7 @@ Default Authentication - When using AcegiAuthenticationSource, + When using SpringSecurityAuthenticationSource, authenticated contexts will only be possible to create once the user is logged in using Acegi. To use default authentication information when no user is logged in, use the @@ -133,13 +188,13 @@ <bean id="authenticationSource" class="org.springframework.ldap.authentication.DefaultValuesAuthenticationSourceDecorator"> - <property name="target" ref="acegiAuthenticationSource" /> + <property name="target" ref="springSecurityAuthenticationSource" /> <property name="defaultUser" value="cn=myDefaultUser" /> <property name="defaultPassword" value="pass" /> </bean> - <bean id="acegiAuthenticationSource" - class="org.springframework.ldap.authentication.AcegiAuthenticationSource" /> + <bean id="springSecurityAuthenticationSource" + class="org.springframework.security.ldap.SpringSecurityAuthenticationSource" /> ... </beans> @@ -147,15 +202,21 @@ - Pooling - - LDAP connection pooling can be turned on/off using the - pooled flag. Default is true. The - configuration of LDAP connection pooling is managed using + Native Java LDAP Pooling + The internal Java LDAP provider provides some very basic pooling capabilities. + This LDAP connection pooling can be turned on/off using the + pooled flag on AbstractContextSource. + The default value is true, i.e. the native Java LDAP pooling will be turned on. + The configuration of LDAP connection pooling is managed using System properties, so this needs to be handled - manually. Details of pooling configuration can be found here. - + manually, outside of the Spring Context configuration. Details of the native pooling configuration + can be found here. + + + There are several serious deficiencies in the built-in LDAP connection pooling, + which is why spring LDAP provides a more sophisticated approach to LDAP connection pooling, + described in . If pooling functionality is required this is the + recommended approach. Advanced ContextSource Configuration @@ -256,4 +317,4 @@ public class PersonService implements PersonService, BaseL If more than one BaseLdapPathSource is defined, you will need to specify which one to use with the baseLdapPathSourceName property. - \ No newline at end of file + diff --git a/mvn-build/src/docbkx/spring-ldap-reference.xml b/mvn-build/src/docbkx/spring-ldap-reference.xml index 7b5ed6f8..cc3fea19 100644 --- a/mvn-build/src/docbkx/spring-ldap-reference.xml +++ b/mvn-build/src/docbkx/spring-ldap-reference.xml @@ -6,8 +6,8 @@ Spring LDAP Reference Documentation - Version 1.2.2 - June 2008 + Version 1.3-RC1 + 2008 Mattias @@ -46,4 +46,5 @@ + diff --git a/mvn-build/src/docbkx/user-authentication.xml b/mvn-build/src/docbkx/user-authentication.xml new file mode 100644 index 00000000..40817f5d --- /dev/null +++ b/mvn-build/src/docbkx/user-authentication.xml @@ -0,0 +1,101 @@ + + + + User Authentication using Spring LDAP + + While the core functionality of the ContextSource is to provide + DirContext instances for use by LdapTemplate, + it may also be used for authenticating users against an LDAP server. The + getContext(principal, credentials) method of ContextSource + will do exactly that; construct a DirContext instance according to the + ContextSource configuration, authenticating the context using the + supplied principal and credentials. + + + Using <literal>ContextSource</literal> for user authentication + +public boolean authenticate(String userDn, String credentials) { + DirContext ctx = null; + try { + ctx = contextSource.getContext(userDn, credentials); + + return true; + } catch (Exception e) { + // Context creation failed - authentication did not succeed + logger.error("Login failed", e); + return false; + } finally { + // It is imperative that the created DirContext instance is always closed + LdapUtils.closeContext(ctx); + } +} + + + + + The userDn supplied to the authenticate method needs to be the full + DN of the user to authenticate (regardless of the base setting on the + ContextSource). You will typically need to perform an LDAP search + based on e.g. the user name to get this DN: + + + + Finding a user based on uid attribute. +private String getDnForUser(String uid) { + Filter f = new EqualsFilter("uid", uid); + List result = ldapTemplate.search(DistinguishedName.EMPTY_PATH, f.toString(), new AbstractContextMapper() { + protected Object doMapFromContext(DirContextOperations ctx) { + return ctx.getNameInNamespace(); + } + }); + + if(result.size() != 1) { + throw new RuntimeException("User not found or not unique"); + } + + return (String)result.get(0); +} + + + + + Some authentication schemes and LDAP servers require some operation to be + performed on the created DirContext instance for the actual + authentication to occur. You should test and make sure how your server setup and + authentication schemes behave; failure to do so might result in that users + will be admitted into your system regardless of the DN/credentials supplied. + + + + Performing LDAP operation on returned <literal>DirContext</literal> objects. + +public boolean authenticate(String userDn, String credentials) { + DirContext ctx = null; + try { + ctx = contextSource.getContext(userDn, credentials); + // Take care here - if a base was specified on the ContextSource + // that needs to be removed from the user DN for the lookup to succeed. + ctx.lookup(userDn); + + return true; + } catch (Exception e) { + // Context creation failed - authentication did not succeed + logger.error("Login failed", e); + return false; + } finally { + // It is imperative that the created DirContext instance is always closed + LdapUtils.closeContext(ctx); + } +} + + + + + While the approach above may be sufficient for very simple authentication scenarios, requirements in this + area commonly expand rapidly. There is a multitude of aspects that apply to this area, including + authentication, authorization, web integration, user context management, etc. If you + suspect that the requirements might expand you should definitely consider using + Spring Security for your security purposes instead. + It is a full-blown, mature security framework addressing the above aspects as well as several others. + + \ No newline at end of file