#!/usr/bin/env python

import ldap

def main():
    # It looks something like this: 
    server = "localhost"
    who = "cn=Manager,dc=example,dc=com"
    cred = "secret"


    #Now we need to make a keyword set to what we want our search string to be. I use my first name for this sample program:
    keyword = "Donald Duck"

    #Next, we need to bind to the LDAP server. Doing so creates an object named "l" that is then used throughout the program.
    try:
        los = ldap.open(server)
        los.simple_bind_s(who, cred)
        print "Successfully bound to server.\n"


        #We're now ready to query the server. We also now catch any possible errors if there is a problem authenticating:
        print "Searching..\n"
        my_search(los, keyword)
    except ldap.LDAPError, error_message:
        print "Couldn't Connect. %s " % error_message


def my_search(los, keyword):

    #In a moment we will be calling python-ldap's built-in search method on our l object. Four variables--base, scope, filter and retrieve_attributes--are the parameters of that search method. Base is used for the DN (distinguished name) of the entry where the search should start. You can leave it blank for this example:
    base = "ou=People,dc=example,dc=com"

    #For scope we use SCOPE_SUBTREE to search the object and all its descendants:
    scope = ldap.SCOPE_SUBTREE

    #Our search filter consists of a cn (common name) and our keyword. Putting asterisks around our keyword (ryan) will match anything with the string ryan, such as Bryant.
    filter_s = "cn=" + keyword


    #The last argument we pass to the search method is used to return all the attributes of each entry:
    retrieve_attributes = None

    #Now, let's setup a few more variables, including a counter to keep track of the number of results returned:
    count = 0

    #a list to append the results to:
    result_set = []

    #and a variable to specify the length, in seconds, we're willing to wait for a response from the server:
    timeout = 0

    #Now we can begin our search by calling python-ldap's search method on our l object:
    try:
        result_id = los.search(base, scope, filter_s, retrieve_attributes)

        #Store any results in the result_set list
        while 1:
            result_type, result_data = los.result(result_id, timeout)
            if (result_data == []):
                break
            else:
                if result_type == ldap.RES_SEARCH_ENTRY:
                    result_set.append(result_data)


        #If we were to print result_set now, it might look like a big list of tuples and dicts. Instead, step through it and select only the data we want to see
        if len(result_set) == 0:
            print "No Results."
            return
        for i in range(len(result_set)):
            for entry in result_set[i]:
                print entry
                try:
                    name = entry[1]['cn'][0]
                    email = entry[1]['mail'][0]
                    phone = entry[1]['telephonenumber'][0]
                    desc = entry[1]['description'][0]
                    count = count + 1


                    #Display the data, if any was found, in the following format:
                    #1.    Name:    Description:    E-mail:    Phone:    2.    Name:    Description:    E-mail:    Phone:    etc..
                    print "%d.\nName: %s\nDescription: %s\nE-mail: %s\nPhone: %s\n" %\
                           (count, name, desc, email, phone)
                except:
                    pass

    except ldap.LDAPError, error_message:
        print error_message


#Running the Program
#You probably are anxious now to run the program and see it in action. But first, you need to append the following code to call the main() function. It should go at the end of your script before you run it.
if __name__ == '__main__':
    main()

