什么是LDAP,百度百科一堆专业术语的描述。

我总结为一句话:轻量级目录访问协议,有数据库的数据存储功能,以树状层次型存储方式,就好像你的电话薄那样。

在一次项目中,由于该项目是教育性管理项目,客户要求项目必须部署在内网。那么在内网的话,就代表用户需要去拨VPN才能进行内网的访问。

其实当时我想到的是,单独开个注册映射到外网,让用户自己注册,管理员进行审核,然后用VPN去读数据库中的账号和密码就行了。这样,我们的系统和vpn就

相当于统一账号。但是当我确认需求的时候,那个老师告诉我们,他不会读什么数据库,他能够LDAP或者windows域,当时我直接蒙逼了。没听过这个,最后花时间

看了下,发现也不是那么吊。切入正题

(1) 在官网上下载LDAP并安装,注意两点,1、第二步你输入的密码一定要记着,默认是secret;2、到“backend configuration” 这一步的时候,选择“BDB”

其他的你就一直下一步。安装完成的LDAP 默认是启动。你不用管他

(2)找到你安装的LDAP位置,找到“slapd.conf”这个配置文件。打开它。

里面有两行默认的配置

suffix   "dc=maxcrc,dc=com"

rootdn  "cn=Manager,dc=maxcrc,dc=com"

这两行东西其实是可以随便改的。只要能和你接下来要导入的conf文件中的配置匹配就可以。

其实,上面的两行属性可以理解为用户名和匹配项,用户名:cn=manager,匹配项:dc=maxcrc,dc=com

(3)写一个ynjy.conf文件

利用这个文件,你可以导入你的初始ldap的管理员

dn: uid=lrd,ou=People,dc=maxcrc,dc=com
uid: lrd
objectClass: inetOrgPerson
mail: 782122271@qq.com
userPassword: 123456
labeledURI: http://www.maxcrc.com
sn: Sun
cn: lrd Sun

上面的uid就类似于你的标示,ou=People,类似于你的电话薄名儿,里面存什么待会儿我们利用java来进行添加。

dc=maxcrc,dc=com  这句必须要和你的“slapd.conf”中的匹配,就是我上面说的匹配项。

注意点来了,LDAP可以自定义属性,通过schema自定义,但初次不要去试,因为容易失败,ldap的资料还是比较少。解决问题有时候摸不着头绪

ldap提供了本身自带的属性,就是我们上的uid,mail,userPassword,labeledURI,sn,cn等,,记住,这几个属性必须不能改它。大小写都认。不然导不进去。

(4)导入ynjy.conf进入ldap

cmd进入命令窗口,定位到你的ldap目录中

输入命令:ldapadd -x -D "cn=Manager,dc=maxcrc,dc=com" -w secret -f ynjy.ldif

你会看见执行条目成功的提示

你可以下载一个ldapBrowser进行查看。

上面的初步ldap平台的准备工作就完了

接下来,我们准备Java的访问

其实和连接JDBC方式是一样的。注意的就是LDAP的cn,dc这些属性要匹配。相当于账号!!!

我就直接将我的LDAPHelper代码贴出来。并且附上一段简单将数据读进LDAP中的代码

package util;

import java.util.Hashtable;
import javax.naming.AuthenticationException;
import javax.naming.Context;
import javax.naming.NamingEnumeration;
import javax.naming.NamingException;
import javax.naming.directory.BasicAttribute;
import javax.naming.directory.BasicAttributes;
import javax.naming.directory.SearchControls;
import javax.naming.directory.SearchResult;
import javax.naming.ldap.Control;
import javax.naming.ldap.InitialLdapContext;
import javax.naming.ldap.LdapContext;

public class LDAPHelper {
private final String URL = "ldap://192.168.2.19:389/";
private final String BASEDN = "ou=People,dc=maxcrc,dc=com"; // 根据自己情况进行修改
private final String FACTORY = "com.sun.jndi.ldap.LdapCtxFactory";
private LdapContext ctx = null;
private final Control[] connCtls = null;

private void LDAP_connect() {
Hashtable<String, String> env = new Hashtable<String, String>();
env.put(Context.INITIAL_CONTEXT_FACTORY, FACTORY);
env.put(Context.PROVIDER_URL, URL + BASEDN);
env.put(Context.SECURITY_AUTHENTICATION, "simple");

String root = "cn=Manager,dc=maxcrc,dc=com"; //根据自己情况修改
env.put(Context.SECURITY_PRINCIPAL, root); // 管理员
env.put(Context.SECURITY_CREDENTIALS, "daqsoft"); // 管理员密码

try {
ctx = new InitialLdapContext(env, connCtls);
System.out.println( "连接成功" );

} catch (javax.naming.AuthenticationException e) {
System.out.println("连接失败:");
e.printStackTrace();
} catch (Exception e) {
System.out.println("连接出错:");
e.printStackTrace();
}

}
private void closeContext(){
if (ctx != null) {
try {
ctx.close();
}
catch (NamingException e) {
e.printStackTrace();
}

}
}
private String getUserDN(String uid) {
String userDN = "";
LDAP_connect();
try {
SearchControls constraints = new SearchControls();
constraints.setSearchScope(SearchControls.SUBTREE_SCOPE);

NamingEnumeration<SearchResult> en = ctx.search("", "uid=" + uid, constraints);

if (en == null || !en.hasMoreElements()) {
System.out.println("未找到该用户");
}
// maybe more than one element
while (en != null && en.hasMoreElements()) {
Object obj = en.nextElement();
if (obj instanceof SearchResult) {
SearchResult si = (SearchResult) obj;
userDN += si.getName();
userDN += "," + BASEDN;
} else {
System.out.println(obj);
}
}
} catch (Exception e) {
System.out.println("查找用户时产生异常。");
e.printStackTrace();
}

return userDN;
}

public boolean authenricate(String UID, String password) {
boolean valide = false;
String userDN = getUserDN(UID);

try {
ctx.addToEnvironment(Context.SECURITY_PRINCIPAL, userDN);
ctx.addToEnvironment(Context.SECURITY_CREDENTIALS, password);
ctx.reconnect(connCtls);
System.out.println(userDN + " 验证通过");
valide = true;
} catch (AuthenticationException e) {
System.out.println(userDN + " 验证失败");
System.out.println(e.toString());
valide = false;
} catch (NamingException e) {
System.out.println(userDN + " 验证失败");
valide = false;
}
closeContext();
return valide;
}


public boolean addUser(String usr, String pwd,String uid,String description) {
try {
LDAP_connect();
BasicAttributes attrsbu = new BasicAttributes();
BasicAttribute objclassSet = new BasicAttribute("objectclass");
objclassSet.add("inetOrgPerson");
attrsbu.put(objclassSet);
attrsbu.put("sn", usr);
attrsbu.put("cn", usr);
attrsbu.put("uid", uid);
attrsbu.put("userPassword", pwd);
attrsbu.put("description", description);
ctx.createSubcontext("uid="+uid+"", attrsbu);

return true;
} catch (NamingException ex) {
ex.printStackTrace();
}
closeContext();
return false;
}

//测试
public static void main(String[] args) {
LDAPHelper ldap = new LDAPHelper();

//ldap.LDAP_connect();

if(ldap.authenricate("yorker", "daqsoft") == true){

System.out.println( "该用户认证成功" );

}
//ldap.addUser("yorker","secret");

}
}

上面的代码是我从另外一张表获得的用户信息写进了ldap。

ldap的操作就介绍完毕。有问题的大家可以一起讨论。我也是刚用到将这个东西勉强用起来

posted on 2015-12-10 14:40  请叫我端东、  阅读(10102)  评论(0编辑  收藏  举报