Web Container Authentication via LDAP


Planning your use case#

By Default, JSPWiki uses XML user database files for authentication. This is good for small standalone applications but in enterprise environments, user accounts are centrally stored in systems like Active Directory, Lotus Domino, LDAP Servers (i.e.: OpenLDAP, Sun One Directory Server, etc.). So in an enterprise environment, you can use an LDAP service to manage your wiki users and groups. If you are running Tomcat as your servlet container, you can configure your JSPWiki to use Tomcat JNDIRealm feature so that LDAP users can log into JSPWiki system without any additional efforts.

In order to achieve this, you need to have enough information about your LDAP environment, Tomcat configuration details, and JSPWiki application web.xml. You need several steps to make this happen:

  1. Setup a working LDAP Server if you don't already have one.
  2. Change the configuration of tomcat to work with LDAP
  3. Change the configuration of JSPWiki to let LDAP users log in successfully

Environment Setup for this tutorial#

LDAP ServerOpenLDAP Server 2.3.43 (cygwin)
TomcatTomcat 6.0.30
JSPWikiJSPWiki 2.8.4
LDAP Directory Information

LDAP Server Configuration#

If you do not have a working LDAP server, you can install from scratch. There are lot of LDAP servers you can choose from, open source or commercial. OpenLDAP is one of the most popular LDAP Servers. You can get the latest build, docs from its website: http://www.openldap.org. You can get enough information from the web about how to setup/configure an LDAP server. The focus here is on configuration details of your LDAP server.

LDAP Configuration and Directory Information Tree#

You need to have some entries on your LDAP instance, both users and groups. You need to get the following information about your LDAP server and directory information. Please consult your LDAP administrator if you don't know.
ItemNoteExample
LDAP HostLDAP server host name or IP addresslocalhost
LDAP Port389 for ldap:// (default value)
636 for ldaps:// (default value)
Base DN The root DN of your DIT. All the entries are created under this entry. dc=example,dc=com
User Base The DN where all your user entries are createdou=people,dc=example,dc=com
Group Base The DN where all group entries are createdou=groups,dc=example,dc=com
root DNThe DN of the administrator. This may be used later cn=Manager,dc=example,dc=com
root DN password Password for the admin
If all your users and groups are created under the same parent entry, use the same parent DN for group base and user base.

Get to know about access control#

Try to get the current configuration for LDAP access control. This is quite useful for later debugging. The following is an example of ACL definition in OpenLDAP. You can use it as a template.
access to dn.sub="ou=groups,dc=example,dc=com"
	by self write
	by * read

access to dn.base="" by * read
access to dn.base="cn=Subschema" by * read

access to *
	by self write
	by users read
	by anonymous search

Where:

  • For entries under ou=groups,dc=example,dc=com, read access is granted to roles except self. Anonymous user can read group members under this configuration
  • For other entries, the currently logged in user can edit entries of their own. Other authenticated users can read the values while anonymous only has search privilege.

Tomcat Configuration#

The LDAP support is implemented by JNDIRealm in Tomcat. You can add a Realm element to your Tomcat server.xml file. You can add the node in the XML elements below:
  • Inside an <Engine> element - This Realm will be shared across ALL web applications on ALL virtual hosts, UNLESS it is overridden by a Realm element nested inside a subordinate <Host> or <Context> element.
  • Inside a <Host> element - This Realm will be shared across ALL web applications for THIS virtual host, UNLESS it is overridden by a Realm element nested inside a subordinate <Context> element.
  • Inside a <Context> element - This Realm will be used ONLY for THIS web application.

For more information about Tomcat Realm and JNDIRealm, please refer to Tomcat 6.0 documentation http://tomcat.apache.org/tomcat-6.0-doc/realm-howto.html.

bind mode v.s. comparison mode#

Tomcat can use either bind mode or comparison mode for authenticating user. You need to make the right choice for this.
This configuration in this tutorial uses bind mode for now. Comparison mode configuration is not available.
For detailed information about these two modes, please check Tomcat documentation: http://tomcat.apache.org/tomcat-6.0-doc/realm-howto.html#JNDIRealm.

Editing Tomcat server.xml #

In this tutorial, the JNDIRealm will be added inside <Engine> element.

Open your Tomcat configuration file#

Tomcat configuration file server.xml is located in <CATALINA_HOME>/conf. Open it with your favourite text editor. Go to the XML section below Engine/Realm. You can find there by looking for text below:
      <Realm className="org.apache.catalina.realm.UserDatabaseRealm"
             resourceName="UserDatabase"/>

Add JNDI Realm Element#

Add one extra Realm element just after the UserDatabase node. The XML fragment of JNDIRealm configuration is like below:
	<Realm className="org.apache.catalina.realm.JNDIRealm"  debug="99"
		connectionURL="ldap://localhost:389"
		userPattern="cn={0},ou=people,dc=example,dc=com"
		roleBase="ou=groups,dc=example,dc=com"
		roleSubtree="true"
		roleSearch="(member={0})"
		roleName="cn"
		roleNested="true"
	/>

where

  • connectionURLThe LDAP server connection w/ port. The template is (ldap://|ldaps://)<LDAP_Host>[:<LDAP_Port]>.
  • userPattern The DN pattern for LDAP users. This attribute can be used for case like all users are stored under the same parent entry. {0} will be replaced with each user's actual login.
  • roleBase Base DN of your group base
  • roleSubtree Search sub entries if enabled.
  • roleSearch the LDAP search filter for selecting role entries. It optionally includes pattern replacements "{0}" for the distinguished name(i.e.:(uid=user,ou=People, dc=example,dc=com)) and/or "{1}" for the username of the authenticated user. The attribute name depends on which object class you use for your groups. Here are a few attribute names for common groups:
    • member} for objectClass groupOfNames
    • uniqueMember objectClass groupOfUniqueNames
    • memberUid objectClass posixGroup
  • roleName the attribute in a role entry containing the name of that role.
  • roleNested enable nested groups. Set to true if you want to nest groups in groups.

JNDIRealm Configuration Samples#

The JNDIRealm configuration is basically the same for most LDAP servers. The variants may be attribute names for user logins, group member attribute names, etc.

OpenLDAP Server#

	<Realm className="org.apache.catalina.realm.JNDIRealm"  debug="99"
		connectionURL="ldap://localhost:389"
		userPattern="cn={0},ou=people,dc=example,dc=com"
		roleBase="ou=groups,dc=example,dc=com"
		roleSubtree="true"
		roleSearch="(member={0})"
		roleName="cn"
		roleNested="true"
	/>

Configuration for Active Directory#

<Realm className="org.apache.catalina.realm.JNDIRealm"
  	 connectionURL="ldap://domaincontroller-host:389"
     	 connectionName="CN=Ldaplogin,OU=EDP Login,OU=All Users XP,DC=poison,DC=in"
         connectionPassword="***secret***" 
         userBase="OU=All Users XP,DC=domain" 
         userSubtree="true"
         userSearch="(userPrincipalName={0}@yourdomain.com)" 
         userRoleName="memberOf"
         roleBase="CN=Groups,DC=domain" 
         roleName="cn" 
         roleSubtree="true"
         roleSearch="(member={0})" 
       />
 
userSearch can be set to any property that uniquely identifies a user. In this case it is set to identify with your email. It can also be set to
    userSearch="(sAMAccountName={0})"

I am currently trying to figure out a way to authenticate through domain trusts. -JoergMeyer


JSPWiki Configuration#

Now that your Tomcat can start work with your LDAP, the next step is to configure JSPWiki for LDAP authentication through Tomcat.

LDAP groups and wiki groups#

You can also map LDAP groups to wiki groups if you want to enforce JSPWiki ACL to LDAP user groups. You need to change the web.xml to include your wanted groups if you want to use LDAP groups. You can do so by assigning proper privileges to LDAP groups in your JSPWiki policy file.

Editing JSPWiki web.xml#

Open your wiki's web.xml in an editor, and uncomment the CONTAINER-MANAGED AUTH section like below:

   <security-constraint>
       <web-resource-collection>
           <web-resource-name>Administrative Area</web-resource-name>
           <url-pattern>/Delete.jsp</url-pattern>
       </web-resource-collection>
       <auth-constraint>
           <role-name>wiki-admin</role-name>
       </auth-constraint>
       <!--
       <user-data-constraint>
           <transport-guarantee>CONFIDENTIAL</transport-guarantee>
       </user-data-constraint>
       -->
   </security-constraint>
      
   <security-constraint>
       <web-resource-collection>
           <web-resource-name>Authenticated area</web-resource-name>
           <url-pattern>/Edit.jsp</url-pattern>
           <url-pattern>/Comment.jsp</url-pattern>
           <url-pattern>/Login.jsp</url-pattern>
           <url-pattern>/NewGroup.jsp</url-pattern>
           <url-pattern>/Rename.jsp</url-pattern>
           <url-pattern>/Upload.jsp</url-pattern>
           <http-method>DELETE</http-method>
           <http-method>GET</http-method>
           <http-method>HEAD</http-method>
           <http-method>POST</http-method>
           <http-method>PUT</http-method>
       </web-resource-collection>

       <web-resource-collection>
           <web-resource-name>Read-only Area</web-resource-name>
           <url-pattern>/attach</url-pattern>
           <http-method>DELETE</http-method>
           <http-method>POST</http-method>
           <http-method>PUT</http-method>
       </web-resource-collection>

       <auth-constraint>
           <role-name>wiki-admin</role-name>
           <role-name>wiki-users</role-name>

       </auth-constraint>
	  <!--
       <user-data-constraint>
           <transport-guarantee>CONFIDENTIAL</transport-guarantee>
       </user-data-constraint>
       -->
   </security-constraint>

   <login-config>
       <auth-method>FORM</auth-method>
       <form-login-config>
           <form-login-page>/LoginForm.jsp</form-login-page>
           <form-error-page>/LoginForm.jsp</form-error-page>
       </form-login-config>
   </login-config>

   <security-role>
       <description>
           This logical role includes all authenticated users
       </description>
       <role-name>wiki-users</role-name>
   </security-role>

   <security-role>
       <description>
           This logical role includes all administrative users
       </description>
       <role-name>wiki-admin</role-name>
   </security-role>
where:
  • wiki-admin is the LDAP group whose members will have the wiki admin privileges
  • wiki-users is the LDAP group whose members will be normal authenticated wiki users.

I commented the user-data-constraint section since I failed to enable SSL in tomcat.

Updating jspwiki.properties#

You need to uncomment the WebContainerAuthorizer property to use web container authorization. See below
#  AUTHORIZATION (EXTERNAL)
#  For authorization, JSPWiki has a two-tier system. When we want to
#  determine whether a user has permission to perform a certain action,
#  we first consult an external "authorizer" to determine if the user
#  is a member of the required role. By default, JSPWiki uses the
#  servlet container's authorization service for this (that is, it
#  calls HttpServletRequest.isUserInRole(String) ).
#  However, you can use another Authorizer if you wish; specify that
#  class here.

jspwiki.authorizer =com.ecyrd.jspwiki.auth.authorize.WebContainerAuthorizer

Update JSPWiki security policy#

If you would like to set permissions to LDAP groups, you can simply add policy entries on authorize.Role. The following is an entry for wiki-admin group (from LDAP).
grant principal com.ecyrd.jspwiki.auth.authorize.Role "wiki-admin" {
    permission com.ecyrd.jspwiki.auth.permissions.AllPermission "*";
};

References#


Add new attachment

Only authorized users are allowed to upload new attachments.

List of attachments

Kind Attachment Name Size Version Date Modified Author Change note
png
ldap_tree_structure.png 10.7 kB 1 31-Oct-2011 08:22 David Gao LDAP Directory Information Tree
« This page (revision-13) was last changed on 31-Oct-2011 23:23 by Quinn