声明:
1、解决办法是从一个英文网站找到的,现在找不到了,不是我自己解决的
2、连接ldap的方法,也是从网上拷贝,因为方法是固定和通用的
3、欢迎拍砖和开骂,真的,但是至少骂完后告诉我哪里不对,教小弟几招
前一阵子需要做一个从第三方ldap同步用户到本地系统的功能,本地后台服务是java写的,考虑到数据同步的一致性,使用ldap获取的数据中的的objectGUID作为两个系统的唯一标示
但是问题来了,objectGUID这个东西貌似是octString类型的,本地服务获取时,居然出现了乱码。在网上找了好多方法,无外乎都是转换成String然后getBytes(),然后通过一系列的算法操作转换为16进制码等等。
好吧,基本上,是这样的
......//连接ldap和查询代码省略
if("objectGUID".equals(Attr.getID())){
String st = getGUID(Attr.get().toString().getBytes()); //objectGUID
......//后续处理代码省略
}//方法结束
private static String getGUID(byte[] inArr) {
StringBuffer guid = new StringBuffer();
for (int i = 0; i < inArr.length; i++) {
StringBuffer dblByte = new StringBuffer(
Integer.toHexString(inArr[i] & 0xff));
if (dblByte.length() == 1) {
guid.append("0");
}
guid.append(dblByte);
}
return guid.toString();
}
不知道是我没有搞清楚原理还是什么原因,上面这种方法,因为先把取出来的值toString了一次,在不同的服务器(计算机)上,转换出来的十六进制码是不同的,具体原因待查。这样对将来的备份和数据迁移肯定是灾难!!!
下面这种方法就好多了,而且还原了ldap服务器上的呈现形式,比如:
objectGUID:{751837D8-A40F-4F78-AE6C-29E2AD8D9921}
public static void main(String[] args) {
String adminName = "test@com.cn"; // 账号
String adminPassword = "123456"; // 密码
String ldapURL = "ldap://192.168.0.123:389"; // 地址
Properties env = new Properties();
env.put(Context.INITIAL_CONTEXT_FACTORY,"com.sun.jndi.ldap.LdapCtxFactory");
env.put(Context.SECURITY_AUTHENTICATION, "simple");// "none","simple","strong"
env.put(Context.SECURITY_PRINCIPAL, adminName);
env.put(Context.SECURITY_CREDENTIALS, adminPassword);
env.put(Context.PROVIDER_URL, ldapURL);
// **解决 乱码 的关键一句
env.put("java.naming.ldap.attributes.binary","objectGUID");
try {
// 建立连接
LdapContext ctx = new InitialLdapContext(env, null);
// 定义要取出的属性
String returnedAtts[] = {
"cn",
"sn",
"givenname",
"distinguishedName",
"displayname",
"objectCategory",
"objectClass",
"objectGUID",
"objectSid",
"userAccountControl",
"name",
"distinguishedName"
};
SearchControls searchCtls = new SearchControls();
searchCtls.setSearchScope(SearchControls.SUBTREE_SCOPE);
searchCtls.setReturningAttributes(returnedAtts);
// 定义条件
String searchFilter = "(&(objectClass=person)(objectClass=organizationalPerson)(objectClass=user)(!(objectClass=computer)))";
String searchBase = "DC=com,DC=cn";
// 执行查询
NamingEnumeration<SearchResult> answer = ctx.search(searchBase,searchFilter, searchCtls);
while (answer.hasMoreElements()) {
SearchResult sr = (SearchResult) answer.next();
// System.out.println(sr.getAttributes().get("distinguishedName")
// .toString()
// + " || "
// + sr.getAttributes().get("userAccountControl").toString()
// + " || "
// + sr.getAttributes().get("objectClass").toString()
// + " || "
// + sr.getAttributes().get("name").toString()
// + " || "
// + sr.getAttributes().get("objectGUID").toString());
byte[] GUID = (byte[])sr.getAttributes().get("objectGUID").get();
String strGUID = "";
String byteGUID = "";
//Convert the GUID into string using the byte format
for (int c=0;c<GUID.length;c++) {
byteGUID = byteGUID + "\\" + AddLeadingZero((int)GUID[c] & 0xFF);
}
strGUID = "{";
strGUID = strGUID + AddLeadingZero((int)GUID[3] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[2] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[1] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[0] & 0xFF);
strGUID = strGUID + "-";
strGUID = strGUID + AddLeadingZero((int)GUID[5] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[4] & 0xFF);
strGUID = strGUID + "-";
strGUID = strGUID + AddLeadingZero((int)GUID[7] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[6] & 0xFF);
strGUID = strGUID + "-";
strGUID = strGUID + AddLeadingZero((int)GUID[8] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[9] & 0xFF);
strGUID = strGUID + "-";
strGUID = strGUID + AddLeadingZero((int)GUID[10] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[11] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[12] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[13] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[14] & 0xFF);
strGUID = strGUID + AddLeadingZero((int)GUID[15] & 0xFF);
strGUID = strGUID + "}";
System.out.println(sr.getAttributes().get("name"));
System.out.println("GUID (String format): " + strGUID);
//System.out.println("GUID (Byte format): " + byteGUID);
}
ctx.close();
} catch (NamingException e) {
e.printStackTrace();
System.err.println("Problem searching directory: " + e);
}
}
public static String AddLeadingZero(int k) {
return (k <= 0xF) ? "0" + Integer.toHexString(k) : Integer
.toHexString(k);
}