1   /*
2    *   Copyright 2004 The Apache Software Foundation
3    *
4    *   Licensed under the Apache License, Version 2.0 (the "License");
5    *   you may not use this file except in compliance with the License.
6    *   You may obtain a copy of the License at
7    *
8    *       http://www.apache.org/licenses/LICENSE-2.0
9    *
10   *   Unless required by applicable law or agreed to in writing, software
11   *   distributed under the License is distributed on an "AS IS" BASIS,
12   *   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   *   See the License for the specific language governing permissions and
14   *   limitations under the License.
15   *
16   */
17  package org.apache.ldap.server;
18  
19  
20  import java.io.File;
21  import java.io.IOException;
22  import java.io.InputStream;
23  import java.util.Hashtable;
24  
25  import javax.naming.Context;
26  import javax.naming.InitialContext;
27  import javax.naming.Name;
28  import javax.naming.NamingException;
29  import javax.naming.directory.Attributes;
30  import javax.naming.ldap.InitialLdapContext;
31  import javax.naming.ldap.LdapContext;
32  
33  import junit.framework.TestCase;
34  
35  import org.apache.commons.io.FileUtils;
36  import org.apache.ldap.common.exception.LdapConfigurationException;
37  import org.apache.ldap.common.ldif.LdifIterator;
38  import org.apache.ldap.common.ldif.LdifParser;
39  import org.apache.ldap.common.ldif.LdifParserImpl;
40  import org.apache.ldap.common.message.LockableAttributesImpl;
41  import org.apache.ldap.common.name.LdapName;
42  import org.apache.ldap.server.configuration.MutableServerStartupConfiguration;
43  import org.apache.ldap.server.configuration.ShutdownConfiguration;
44  import org.apache.ldap.server.jndi.ServerContextFactory;
45  import org.apache.mina.util.AvailablePortFinder;
46  
47  
48  /***
49   * A simple testcase for testing JNDI provider functionality.
50   *
51   * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
52   * @version $Rev: 264732 $
53   */
54  public abstract class AbstractServerTest extends TestCase
55  {
56      /*** the context root for the system partition */
57      protected LdapContext sysRoot;
58  
59      /*** flag whether to delete database files for each test or not */
60      protected boolean doDelete = true;
61  
62      protected MutableServerStartupConfiguration configuration = new MutableServerStartupConfiguration();
63  
64      protected int port = -1;
65  
66      /***
67       * Get's the initial context factory for the provider's ou=system context
68       * root.
69       *
70       * @see junit.framework.TestCase#setUp()
71       */
72      protected void setUp() throws Exception
73      {
74          super.setUp();
75  
76          doDelete( configuration.getWorkingDirectory() );
77          port = AvailablePortFinder.getNextAvailable( 1024 );
78          configuration.setLdapPort( port );
79  
80          setSysRoot( "uid=admin,ou=system", "secret" );
81      }
82  
83  
84      /***
85       * Deletes the Eve working directory.
86       */
87      protected void doDelete( File wkdir ) throws IOException
88      {
89          if ( doDelete )
90          {
91              if ( wkdir.exists() )
92              {
93                  FileUtils.deleteDirectory( wkdir );
94              }
95              if ( wkdir.exists() )
96              {
97                  throw new IOException( "Failed to delete: " + wkdir );
98              }
99          }
100     }
101 
102 
103     /***
104      * Sets and returns the system root.  Values of user and password used to
105      * set the respective JNDI properties.  These values can be overriden by the
106      * overrides properties.
107      *
108      * @param user the username for authenticating as this user
109      * @param passwd the password of the user
110      * @return the sysRoot context which is also set
111      * @throws NamingException if there is a failure of any kind
112      */
113     protected LdapContext setSysRoot( String user, String passwd ) throws NamingException
114     {
115         Hashtable env = new Hashtable( configuration.toJndiEnvironment() );
116 
117         env.put( Context.SECURITY_PRINCIPAL, user );
118         env.put( Context.SECURITY_CREDENTIALS, passwd );
119         env.put( Context.SECURITY_AUTHENTICATION, "simple" );
120 
121         return setSysRoot( env );
122     }
123 
124 
125     /***
126      * Sets the system root taking into account the extras and overrides
127      * properties.  In between these it sets the properties for the working
128      * directory, the provider URL and the JNDI InitialContexFactory to use.
129      *
130      * @param env an environment to use while setting up the system root.
131      * @return the sysRoot context which is also set
132      * @throws NamingException if there is a failure of any kind
133      */
134     protected LdapContext setSysRoot( Hashtable env ) throws NamingException
135     {
136         Hashtable envFinal = new Hashtable( env );
137         envFinal.put( Context.PROVIDER_URL, "ou=system" );
138         envFinal.put( Context.INITIAL_CONTEXT_FACTORY, ServerContextFactory.class.getName() );
139 
140         return sysRoot = new InitialLdapContext( envFinal, null );
141     }
142 
143 
144     /***
145      * Sets the system context root to null.
146      *
147      * @see junit.framework.TestCase#tearDown()
148      */
149     protected void tearDown() throws Exception
150     {
151         super.tearDown();
152 
153         Hashtable env = new Hashtable();
154 
155         env.put( Context.PROVIDER_URL, "ou=system" );
156 
157         env.put( Context.INITIAL_CONTEXT_FACTORY, "org.apache.ldap.server.jndi.ServerContextFactory" );
158 
159         env.putAll( new ShutdownConfiguration().toJndiEnvironment() );
160 
161         env.put( Context.SECURITY_PRINCIPAL, "uid=admin,ou=system" );
162 
163         env.put( Context.SECURITY_CREDENTIALS, "secret" );
164 
165         try { new InitialContext( env ); } catch( Exception e ) {}
166 
167         sysRoot = null;
168         doDelete( configuration.getWorkingDirectory() );
169         configuration = new MutableServerStartupConfiguration();
170     }
171 
172 
173     /***
174      * Imports the LDIF entries packaged with the Eve JNDI provider jar into
175      * the newly created system partition to prime it up for operation.  Note
176      * that only ou=system entries will be added - entries for other partitions
177      * cannot be imported and will blow chunks.
178      *
179      * @throws NamingException if there are problems reading the ldif file and
180      * adding those entries to the system partition
181      */
182     protected void importLdif( InputStream in ) throws NamingException
183     {
184         Hashtable env = new Hashtable();
185 
186         env.putAll( sysRoot.getEnvironment() );
187 
188         LdapContext ctx = new InitialLdapContext( env, null );
189 
190         LdifParser parser = new LdifParserImpl();
191 
192         try
193         {
194             LdifIterator iterator = new LdifIterator( in );
195 
196             while ( iterator.hasNext() )
197             {
198                 Attributes attributes = new LockableAttributesImpl();
199 
200                 String ldif = ( String ) iterator.next();
201 
202                 parser.parse( attributes, ldif );
203 
204                 Name dn = new LdapName( ( String ) attributes.remove( "dn" ).get() );
205 
206                 dn.remove( 0 );
207 
208                 ctx.createSubcontext( dn, attributes );
209             }
210         }
211         catch ( Exception e )
212         {
213             String msg = "failed while trying to parse system ldif file";
214 
215             NamingException ne = new LdapConfigurationException( msg );
216 
217             ne.setRootCause( e );
218 
219             throw ne;
220         }
221     }
222 }