ApacheDS - How to create a new user with Java JNDI and setting the password?

16.3k Views Asked by At

I have the following JNDI code to generate the password in a new user into Apache DS:

 private String digest(String algorithm,String password) throws NoSuchAlgorithmException {
        String r = null;
        byte [] b = null;
        MessageDigest md = MessageDigest.getInstance(algorithm);
        BASE64Encoder encoder;

        md.update(password.getBytes());
        b = md.digest();

        encoder = new BASE64Encoder();

        System.out.println(encoder.encode(b));

        r = encoder.encode(b);

        return r;
    }

This code adds the new user:

 public User create(User t) throws PersistenceException {
     NamingEnumeration answer = null;
     Attributes matchAttrs = null;
     Attribute objectClass = new BasicAttribute("objectClass");

     try {
         matchAttrs = new BasicAttributes(true); // ignore attribute name case
         matchAttrs.put(new BasicAttribute("uid",t.getCommonId()));

         answer = getConnection().search(userContext, matchAttrs);

         if( ! answer.hasMore() )
         {
             matchAttrs = new BasicAttributes(true);
             objectClass.add("inetOrgPerson");
             objectClass.add("organizationalPerson");
             objectClass.add("person");
             objectClass.add("top");
             matchAttrs.put(objectClass);
             matchAttrs.put(new BasicAttribute("cn", t.getFirstName()));
             matchAttrs.put(new BasicAttribute("sn", t.getLastName()));
             matchAttrs.put(new BasicAttribute("givenName", t.getFirstName()));
             matchAttrs.put(new BasicAttribute("mail", t.getCommonId()));
             matchAttrs.put(new BasicAttribute("userPassword", diggest("MD5",t.getPassword())));                
              getConnection().createSubcontext("uid="+t.getCommonId()+","+userContext,matchAttrs);
         }
         else
             throw new PersistenceException("This user already exists.");

     } catch (NoSuchAlgorithmException ex) {
         throw new PersistenceException("LDAP exception creating user - Hash algorithm not found.");
     } catch (NamingException ex) {
         ex.printStackTrace();
         throw new PersistenceException("LDAP exception creating user.");
     }
     return t;
 }

When I call this code it generates a hash MD5 (I passed "MD5" as algorithm) and then it encodes in Base64 and returns the password to be used to the new user for LDAP (apacheds) server.

However the server always create the user and put "SSHA" as the algorithm for the created user. How can I fix that? I tryied a lot of options not succeeded, now I decided to ask. IS there a way to say to LDAP server the password is encoded with a specific hash?

2

There are 2 best solutions below

0
On

When LDAP stored encrypted password, it stores it in the form:

{MD5}<md5hashInBase64>

Try to add explicitly "{MD5}" like here: http://andrew-stephanie.ca/ldap-md5-java

matchAttrs.put(new BasicAttribute("userPassword", "{MD5}" + digest("MD5",t.getPassword())));
2
On

Try this to add a User...

import java.util.Hashtable;
import java.util.Properties;
import java.util.jar.Attributes;

import javax.naming.Context;
import javax.naming.NamingException;
import javax.naming.directory.Attribute;
import javax.naming.directory.BasicAttribute;
import javax.naming.directory.BasicAttributes;
import javax.naming.directory.DirContext;
import javax.naming.directory.InitialDirContext;

    public class LdapProgram {  


            public static void main(String[] args) {  

                 Hashtable env = new Hashtable();
                 env.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
                 env.put(Context.PROVIDER_URL, "ldap://localhost:10389");
                 env.put(Context.SECURITY_AUTHENTICATION, "simple");
                 env.put(Context.SECURITY_PRINCIPAL,"uid=admin,ou=system"); // specify the username
                 env.put(Context.SECURITY_CREDENTIALS,"secret");// specify the password
                // TODO code application logic here  

                          // entry's DN 
           String entryDN = "uid=user1,ou=system";  

            // entry's attributes  

            Attribute cn = new BasicAttribute("cn", "Test User2");  
            Attribute sn = new BasicAttribute("sn", "Test2");  
            Attribute mail = new BasicAttribute("mail", "[email protected]");  
            Attribute phone = new BasicAttribute("telephoneNumber", "+1 222 3334444");   
                Attribute oc = new BasicAttribute("objectClass");  
            oc.add("top");  
            oc.add("person");  
            oc.add("organizationalPerson");  
            oc.add("inetOrgPerson");  
            DirContext ctx = null;  

            try {  
                // get a handle to an Initial DirContext  
                ctx = new InitialDirContext(env);  

                // build the entry  
                BasicAttributes entry = new BasicAttributes();  
                entry.put(cn);  
                entry.put(sn);  
                entry.put(mail);  
                entry.put(phone);  

                entry.put(oc);  

                // Add the entry  

                ctx.createSubcontext(entryDN, entry);  
      //          System.out.println( "AddUser: added entry " + entryDN + ".");  

            } catch (NamingException e) {  
                System.err.println("AddUser: error adding entry." + e);  
            }  
         }  
    }