Showing posts with label openldap. Show all posts
Showing posts with label openldap. Show all posts

Wednesday, August 29, 2012

LDAP Authentication and Search

LDAP is a very widespread way for authentication. In this post I would like to show you how to connect to LDAP server, authenticate user and perform search.

We will use only standard Java classes. So we don't need any dependency. In the example you can see my configurations. Yours may differ (pay attention to Context.SECURITY_PRINCIPAL). Here is the code:
import java.util.Properties;

import javax.naming.Context;
import javax.naming.NamingEnumeration;
import javax.naming.NamingException;
import javax.naming.directory.Attribute;
import javax.naming.directory.Attributes;
import javax.naming.directory.SearchControls;
import javax.naming.directory.SearchResult;
import javax.naming.ldap.InitialLdapContext;

public class LdapTest {
    
    public static void processRequest(InitialLdapContext ctx, String userContext, String filter, String attribute) {
        SearchControls searchControls = new SearchControls();
        searchControls.setSearchScope(SearchControls.SUBTREE_SCOPE);

        NamingEnumeration<SearchResult> searchResults;
        try {
            searchResults = ctx.search(userContext, filter, searchControls);
            
            while (searchResults.hasMoreElements()) {
                SearchResult sr = searchResults.next();
                Attributes attributes = sr.getAttributes();
                Attribute a = attributes.get(attribute);
                if (a != null) {
                    String attrValue = (a.get().toString());
                    System.out.println(attrValue);
                } else {
                    System.out.println("Cannot get data");
                }
            }
        } catch (NamingException e) {
            e.printStackTrace();
        }
    }
        
    private static InitialLdapContext initialiaseLdapContext(String server, int port, String username, String password, String contextDN) {
        boolean initialised = false; 
        Properties properties = new Properties();
        properties.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
        properties.put(Context.PROVIDER_URL, "ldap://" + server + ":"+ port);
        properties.put(Context.SECURITY_AUTHENTICATION, "simple");
        properties.put(Context.SECURITY_PRINCIPAL, "uid=" + username + "," + contextDN); //YOU MAY NEED TO CHANGE CODE HERE
        properties.put(Context.SECURITY_CREDENTIALS, password);

        InitialLdapContext ctx = null;
        try {
            // Create initial context
            ctx = new InitialLdapContext(properties, null);
            initialised = true;
        } catch (NamingException e) {
            initialised = false;
        } finally {
            if (initialised) {
                System.out.println("Initialization success");
            } else {
                System.out.println("Initialization fail");
            }
        }
        return ctx;
    }

    public static void main(String[] args) {
        String contextDN = "dc=test,dc=com";
        InitialLdapContext ctx = initialiaseLdapContext("localhost", 389, "test@test.com", "test" , contextDN);
        try {
            if (ctx != null) {
                processRequest(ctx, contextDN, "(uid=qwertTest@test.com)", "street");
                ctx.close();
            }
        } catch (NamingException e) {
            e.printStackTrace();
        }
    }
}

Wednesday, July 4, 2012

LDAP recovery

If you have suffered from LDAP wreckage then probably you already know how difficult it is to make it work again. In my case all problems started with such message in system log:
slapd[11705]: bdb(dc=xxx,dc=com): PANIC: fatal region error detected; run recovery

Note: my bdb version is 4.7, yours may differ;
slapd stands for Stand-alone LDAP Daemon, your service name may be ldap


At first I tried to recover LDAP using
db4.7_verify -h /var/lib/ldap
db4.7_recover -v -h /var/lib/ldap 

But LDAP got broken again and again.
Thus I decided to recreate whole LDAP folder. Here is the scenario:

  1. Stop the LDAP server
    service slapd stop
  2. Dump the directory structure to a text file
    slapcat -l /etc/ldap/backup/ldap_old.ldif
  3. Recover LDAP
    db4.7_recover -v -h /var/lib/ldap
  4. Dump the directory structure to a text file
    slapcat -l /etc/ldap/backup/ldap.ldif
  5. Verify that ldap.ldif contains your entries. If it does not, or if slapcat returned errors in step 3, try running db4.7_recover in catastrophic mode:
    db4.7_recover -v -h /var/lib/ldap -c
    and repeat step 3
  6. Delete the LDAP directory
    rm -fr /var/lib/ldap/*
  7. Load LDAP directory from the file you have create in step 3
    slapadd -l /etc/ldap/backup/slap.ldif
  8. Make openldap the owner of the LDAP directory
    chown -R openldap:openldap /var/lib/ldap/*
  9. Start the LDAP server
    service slapd start