1
I read several articles here on Stackoverflow on how to get the value of the attribute "unicodePwd" in AD (Active Directory), but none of these articles helped me in this situation.
Well, why do I need this information? I’ll explain:
I have here several java routines that unify user information from different systems with each other. These routines take the necessary information from a main Oracle database and then enter the information into other databases (Oracle and Mysql, basically).
For example: I have an internal private cloud system that runs on a Centos Linux operating system and has its own Mysql data flock. To unify user information, including access passwords, I take the information from this main Oracle database and enter it into the Mysql database of the system, to unify user details and login information.
As I said, I have several routines that are working properly without problems, but now we have a new challenge.
I need to do the same unification with our AD users (Active Directory), IE, I need to get the user information in the main Oracle database, including the password, to enter in the same AD users.
I have already managed to update the password field successfully on some test users in AD, but I do not want the password to be updated every time this routine runs, but only when the password is changed in the main Oracle database.
Example: When a user changes their password in the main Oracle database, the java routine will collect all the information to enter into the same user, only from the AD. To do this properly, the routine takes the same information in the AD and then compares the passwords (Oracle password and AD password) and finally, if the passwords are different, the routine will update the AD password using the Oracle password, but if the passwords are equal, routine won’t do anything.
That’s why I need to retrieve/retrieve the value of the "unicodePwd" attribute in Active Directory.
Follows part of the code:
import java.util.Hashtable;
import javax.naming.Context;
import javax.naming.NamingEnumeration;
import javax.naming.NamingException;
import javax.naming.directory.*;
import org.apache.commons.mail.EmailException;
import javax.naming.ldap.InitialLdapContext;
import javax.naming.ldap.LdapContext;
public class ldapQuery {
String distinguishedName = "";
String department = "";
String physicalDeliveryOfficeName = "";
String telephoneNumber = "";
String mobile = "";
String title = "";
String sAMAccountName = "";
String unicodePwd = "";
public ldapQuery(String mail) {
try {
final Hashtable<String, String> env = new Hashtable<String, String>();
final String adminName = "CN=MY DOMAIN ADMIN,CN=MY DOMAIN ADMIN FOLDER LOCALIZATION,DC=MY DOMAIN,DC=MY DOMAIN,DC=MY DOMAIN";
final String adminPasswd = "MY DOMAIN ADMIN PASSWORD";
final String ldapUrl = "ldaps://MY ACTIVE DIRECTORY SERVER:636";
final String factory = "com.sun.jndi.ldap.LdapCtxFactory";
final String authType = "simple";
final String protocol = "ssl";
env.put(Context.INITIAL_CONTEXT_FACTORY, factory);
env.put(Context.SECURITY_AUTHENTICATION, authType);
env.put(Context.SECURITY_PRINCIPAL, adminName);
env.put(Context.SECURITY_CREDENTIALS, adminPasswd);
env.put(Context.SECURITY_PROTOCOL, protocol);
env.put(Context.PROVIDER_URL, ldapUrl);
DirContext ctx = new InitialLdapContext (env,null);
SearchControls searchCtls = new SearchControls();
String returnedAtts[] = {"sAMAccountName", "distinguishedName","department", "physicalDeliveryOfficeName", "telephoneNumber", "mobile", "title", "unicodePwd"};
searchCtls.setReturningAttributes(returnedAtts);
searchCtls.setSearchScope(SearchControls.SUBTREE_SCOPE);
String searchFilter = "(&(objectClass=user)(mail=" + mail +"))";
String searchBase = "DC=MY DOMAIN,DC=MY DOMAIN,DC=MY DOMAIN";
int totalResults = 0;
NamingEnumeration<SearchResult> answer =ctx.search(searchBase, searchFilter, searchCtls);
while (answer.hasMoreElements()) {
SearchResult sr = (SearchResult)answer.next();
totalResults++;
Attributes attrs = sr.getAttributes();
if (attrs != null) {
distinguishedName = (String) attrs.get("distinguishedName").get();
department = (String) attrs.get("department").get();
physicalDeliveryOfficeName = (String) attrs.get("physicalDeliveryOfficeName").get();
telephoneNumber = (String) attrs.get("telephoneNumber").get();
mobile = (String) attrs.get("mobile").get();
title = (String) attrs.get("title").get();
sAMAccountName = (String) attrs.get("sAMAccountName").get();
Attribute passwd = attrs.get("unicodePwd");
unicodePwd = unicodePwd + passwd;
if (department == null) {
department = "";
}
if (physicalDeliveryOfficeName == null) {
physicalDeliveryOfficeName = "";
}
if (telephoneNumber == null) {
telephoneNumber = "";
}
if (mobile == null) {
mobile = "";
}
if (title == null) {
title = "";
}
}
}
}
catch (NamingException e){
System.err.println("FAIL MESSAGE: " + e);
}
}
public String ldapSearchResultDistinguishedName() {
return distinguishedName;
}
public String ldapSearchResultDepartment() {
return department;
}
public String ldapSearchResultPhysicalDeliveryOfficeName() {
return physicalDeliveryOfficeName;
}
public String ldapSearchResultTelephoneNumber() {
return telephoneNumber;
}
public String ldapSearchResultMobile() {
return mobile;
}
public String ldapSearchResultTitle() {
return title;
}
public String ldapSearchResultUnicodePwd() {
return unicodePwd;
}
public String ldapSearchResultSAMAccountName() {
return sAMAccountName;
}
}
After running this code, all variables returned the correct values, except for the "unicodePwd" variable, which returned "null", even if the user in question has a valid password.
I know about the UTF-16LE byte business and that the "unicodePwd" field in Active Directory is encrypted, but as I explained before, I need this information to be returned decrypted in a String variable.
Any idea?