2023年6月21日发(作者:)
Spring ldap 中文文档(一)
第一章 介绍
1.1 概览
Spring-LDAP是一个java简单应用在LDAP开发的一个库,是采取类似Spring JDBC中的JdbcTemplate的原理建立的。它使得我们完全没必要考虑LdapContext的生成和关闭以及NamingEnumeration的循环。在Spring's DataAccessException基础上建立的Spring-LDAP提供一个更加全面且不用检查的异常处理机制。作为补充,Spring-LDAP也有了动态建立LDAP
filters和DNs(Distinguished Names)的类。
举个例子来说,如实现一个获取所有人员进入并返回存有他们名字的list的方法。用JDBC,我们得先生成一个connection,用statement执行一个query。然后我们要遍历resultset,找到我们需要的那个column,把它放入到list。类似地,用Java LDAP,我们先生成一个context,用search filter执行一个search。然后循环遍历resulting namingenumeration,找到需要的那个attribute,把它加入到list。
按传统的实现方法,用Java LDAP实现查找人员名称看起来应该是这样的:
package ;
public class TraditionalPersonDaoImpl implements PersonDao {
public List getAllPersonNames() {
Hashtable env = new Hashtable();
(L_CONTEXT_FACTORY, "xFactory");
(ER_URL, “ldap://localhost:389/dc=example,dc=com”);
DirContext ctx;
try {
ctx = new InitialDirContext(env);
} catch (NamingException e) {
throw new RuntimeException(e);
}
LinkedList list = new LinkedList();
NamingEnumeration results = null;
try {
SearchControls controls = new SearchControls();
rchScope(E_SCOPE);
results = ("", "(objectclass=person)", controls);
while (e()) {
SearchResult searchResult = (SearchResult) ();
Attributes attributes = ributes();
Attribute attr = ("cn");
String cn = (String) ();
(cn);
}
} catch (NameNotFoundException e) {
// The base context was not found.
// Just clean up and exit.
} catch (NamingException e) {
throw new RuntimeException(e);
} finally {
if (results != null) {
try {
();
} catch (Exception e) {
// Never mind this.
}
}
if (ctx != null) {
try {
();
} catch (Exception e) {
// Never mind this.
}
}
}
return list;
}
}
通过spring的LDAP AttributesMapper,我们可以通过下面的代码实现完全一样的功能:
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
public void setLdapTemplate(LdapTemplate ldapTemplate) {
mplate = ldapTemplate;
}
public List getAllPersonNames() {
return (
"", "(objectclass=person)",
new AttributesMapper() {
public Object mapFromAttributes(Attributes attrs)
throws NamingException {
return ("cn").get();
}
});
}
}
1.2 包
用Spring LDAP最小需要:
spring-ldap(spring-ldap包)
spring-core(用于框架内部的丰富的工具类)
spring-beans(方便操作java beans的接口和类)
spring-context(增加通过一致API为应用对象获取资源的能力)
spring-dao(使经常性的错误处理跟使用中的数据访问分开的异常处理机制)
commons-logging(简单的日志处理,内部使用)
在您的Spring context文件中设置需要的beans,然后把LdapTemplate注入到您的数据访问对象:
...
1.3 包架构
这部分包提供了Spring LDAP源代码的逻辑包架构的视图。每个包的依赖性清晰的标注。一个包依赖性是指需要依赖的包来编译这个包,但是运行的时候就不是必须的(依赖您自己要用的这个包)。例如,Spring LDAP 和Acegi Security一起用继承了ecurity这个包的使用。
1.3.1
这个ldap包包含了整个库的中心内容。这些内容包括AttributesMapper,ContextSource,和NameClassPairCallbackHandler.这个也包括中心类LdapTemplate.
依赖:spring-core,spring-beans,spring-context,spring-dao,commons-logging(TBD).
1.3.2 t
support包有支持中心接口实现类和DirContextAdapter abstraction。
依赖:ldap
1.3.3 tication
support authentication包有用于acegi security的认证资源接口的实现。
依赖:ldap,acegi-security(optional)
1.3.4
support filter包有Filter 抽象接口和几个它的实现类。
依赖:commons-lang
1.4 支持
Spring LDAP 1.0.3支持Spring 1.2.7以上版本
第二章 基本操作
2.1 使用 AttributesMapper
在下面的例子中我们将用AttributesMapper很容易地得到所有person对象的名字的结果列表。
Example 2.1. AttributesMapper 返回一个简单属性
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
public void setLdapTemplate(LdapTemplate ldapTemplate) {
mplate = ldapTemplate;
}
public List getAllPersonNames() {
return (
"", "(objectclass=person)",
new AttributesMapper() {
public Object mapFromAttributes(Attributes attrs)
throws NamingException {
return ("cn").get();
}
});
} }
上面粗题字部分是AttributesMapper的实现,它通过属性名称获取到了需要的属性值,然后返回结果。中心代码是LdapTemplate枚举了所有发现的数据入口,通过调用对每个入口特定的AttributesMapper收集得到结果,然后把结果放入list。list通过search方法返回结果值。
如果你有标志一个入口的distinguished name(dn),你就可以直接获取这个入口,而不用去搜索它。这个在Java LDAP就叫着一个lookup。下面的例子就展示了一个lookup怎样得到person对象的结果集的。
Example 2.3. A lookup resulting in a Person object
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
public Person findPerson(String dn) {
return (Person) (dn, new PersonAttributesMapper());
}
}
这里将遍历特别的dn,把发现的属性集发送到已经提供的AttributesMapper,然后得到person对象的结果集。
2.2 建立动态的Filters
我们可以使用包里的类建立动态filters实现在搜索中的应用。我们来做下面所需要的filter:(&(objectclass=person)(sn=?)这里我们要用参数lastName的值去取代?的值。下面展示如何实现这个filter:
Example 2.4. Building a search filter dynamically
package ; ?/P>
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
public List getPersonNamesByLastName(String lastName) {
AndFilter filter = new AndFilter();
(new EqualsFilter("objectclass", "person"));
(new EqualsFilter("sn", lastName));
return (
"", (),
new AttributesMapper() {
public Object mapFromAttributes(Attributes attrs)
throws NamingException {
return ("cn").get();
}
});
}
}
为了完成一个通配符搜索,可能要用到WhitespaceWildcardsFilter:
Example 2.5. Building a wildcard search filter
AndFilter filter = new AndFilter();
(new EqualsFilter("objectclass", "person"));
(new WhitespaceWildcardsFilter("cn", cn));
2.3 建立动态dn
标准的Name interface代表了一个普通的名称,它基本上是一个一定规则的组件序列。在那个序列的Name interface也提供了基本的一些操作,比如添加和删除。LdapTemplate提供了Name interface的实现:DistinguishedName。用这个类将大大的简化了建立distinguished
names(dn),特别考虑到有时关于escapings和encodings的复杂规则。下面的例子阐述了DistinguishedName是怎样被用来构造一个dn的。
Example 2.6. Building a distinguished name dynamically
package ;
import guishedName;
import ;
public class PersonDaoImpl implements PersonDao {
public static final String BASE_DN = "dc=example,dc=com";
...
protected Name buildDn(Person p) {
DistinguishedName dn = new DistinguishedName(BASE_DN);
("c", ntry());
("ou", pany());
("cn", lname());
return dn;
}
}
假如一个person有以下属性:
country
Sweden
company
Some Company
fullname
Some Person
上面的代码将产生下面dn的结果:
cn=Some Person, ou=Some Company, c=Sweden, dc=example, dc=com
在java5中,有个Name interface的实现:LdapName。
如果你是在用java5,你可能需要用到LdapName。当然,如果你希望用DistinguishedName,那你可以还用DistinguishedName。
2.4 绑定和解绑定
2.4.1 数据绑定
在Java LDAP中插入数据叫做绑定。为了做到绑定,一个唯一标志新entry的dn是必须的。下面的例子展示了数据是如何通过LdapTemplate绑定的:
Example 2.7. Binding data using Attributes
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
...
public void create(Person p) {
Name dn = buildDn(p);
(dn, null, buildAttributes(p));
}
private Attributes buildAttributes(Person p) { Attributes attrs = new BasicAttributes();
BasicAttribute ocattr = new BasicAttribute("objectclass");
("top");
("person");
(ocattr);
("cn", "Some Person");
("sn", "Person");
return attrs;
}
}
Attributes的建立是在减少和冗长时候起了足够的作用。当然他对进一步的地简化绑定操作提供了可能,这个将在第三章描述。
2.4.2 解绑定数据
在Java LDAP中删除数据就叫着解绑定数据,入口(entry)是需要dn来唯一标志,就像绑定操作一样。下面的例子展示了使用LdapTemplate怎样来解绑定数据:
Example 2.8. Unbinding data
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
...
public void delete(Person p) {
Name dn = buildDn(p);
(dn);
} }
2.5 修改
在Java LDAP,数据修改可以有两种方式:使用rebind或者modifyAttributes。
2.5.1 使用rebind修改
使用rebind修改数据是一种比较鲁莽的方式。它基本上就是跟在绑定后面的解绑定。它看起来像这样:
Example 2.9. Modifying using rebind
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
...
public void update(Person p) {
Name dn = buildDn(p);
(dn, null, buildAttributes(p));
}
}
2.5.2 使用modifyAttributes修改
如果需要修改的属性应该被取代,有一个获取一组修正的方法叫modifyAttributes。
Example 2.10. Modifying using modifyAttributes
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
...
public void updateDescription(Person p) {
Name dn = buildDn(p);
Attribute attr = new BasicAttribute("description", cription())
ModificationItem item = new ModificationItem(E_ATTRIBUTE, attr);
Attributes(dn, new ModificationItem[] {item});
}
}
2023年6月21日发(作者:)
Spring ldap 中文文档(一)
第一章 介绍
1.1 概览
Spring-LDAP是一个java简单应用在LDAP开发的一个库,是采取类似Spring JDBC中的JdbcTemplate的原理建立的。它使得我们完全没必要考虑LdapContext的生成和关闭以及NamingEnumeration的循环。在Spring's DataAccessException基础上建立的Spring-LDAP提供一个更加全面且不用检查的异常处理机制。作为补充,Spring-LDAP也有了动态建立LDAP
filters和DNs(Distinguished Names)的类。
举个例子来说,如实现一个获取所有人员进入并返回存有他们名字的list的方法。用JDBC,我们得先生成一个connection,用statement执行一个query。然后我们要遍历resultset,找到我们需要的那个column,把它放入到list。类似地,用Java LDAP,我们先生成一个context,用search filter执行一个search。然后循环遍历resulting namingenumeration,找到需要的那个attribute,把它加入到list。
按传统的实现方法,用Java LDAP实现查找人员名称看起来应该是这样的:
package ;
public class TraditionalPersonDaoImpl implements PersonDao {
public List getAllPersonNames() {
Hashtable env = new Hashtable();
(L_CONTEXT_FACTORY, "xFactory");
(ER_URL, “ldap://localhost:389/dc=example,dc=com”);
DirContext ctx;
try {
ctx = new InitialDirContext(env);
} catch (NamingException e) {
throw new RuntimeException(e);
}
LinkedList list = new LinkedList();
NamingEnumeration results = null;
try {
SearchControls controls = new SearchControls();
rchScope(E_SCOPE);
results = ("", "(objectclass=person)", controls);
while (e()) {
SearchResult searchResult = (SearchResult) ();
Attributes attributes = ributes();
Attribute attr = ("cn");
String cn = (String) ();
(cn);
}
} catch (NameNotFoundException e) {
// The base context was not found.
// Just clean up and exit.
} catch (NamingException e) {
throw new RuntimeException(e);
} finally {
if (results != null) {
try {
();
} catch (Exception e) {
// Never mind this.
}
}
if (ctx != null) {
try {
();
} catch (Exception e) {
// Never mind this.
}
}
}
return list;
}
}
通过spring的LDAP AttributesMapper,我们可以通过下面的代码实现完全一样的功能:
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
public void setLdapTemplate(LdapTemplate ldapTemplate) {
mplate = ldapTemplate;
}
public List getAllPersonNames() {
return (
"", "(objectclass=person)",
new AttributesMapper() {
public Object mapFromAttributes(Attributes attrs)
throws NamingException {
return ("cn").get();
}
});
}
}
1.2 包
用Spring LDAP最小需要:
spring-ldap(spring-ldap包)
spring-core(用于框架内部的丰富的工具类)
spring-beans(方便操作java beans的接口和类)
spring-context(增加通过一致API为应用对象获取资源的能力)
spring-dao(使经常性的错误处理跟使用中的数据访问分开的异常处理机制)
commons-logging(简单的日志处理,内部使用)
在您的Spring context文件中设置需要的beans,然后把LdapTemplate注入到您的数据访问对象:
...
1.3 包架构
这部分包提供了Spring LDAP源代码的逻辑包架构的视图。每个包的依赖性清晰的标注。一个包依赖性是指需要依赖的包来编译这个包,但是运行的时候就不是必须的(依赖您自己要用的这个包)。例如,Spring LDAP 和Acegi Security一起用继承了ecurity这个包的使用。
1.3.1
这个ldap包包含了整个库的中心内容。这些内容包括AttributesMapper,ContextSource,和NameClassPairCallbackHandler.这个也包括中心类LdapTemplate.
依赖:spring-core,spring-beans,spring-context,spring-dao,commons-logging(TBD).
1.3.2 t
support包有支持中心接口实现类和DirContextAdapter abstraction。
依赖:ldap
1.3.3 tication
support authentication包有用于acegi security的认证资源接口的实现。
依赖:ldap,acegi-security(optional)
1.3.4
support filter包有Filter 抽象接口和几个它的实现类。
依赖:commons-lang
1.4 支持
Spring LDAP 1.0.3支持Spring 1.2.7以上版本
第二章 基本操作
2.1 使用 AttributesMapper
在下面的例子中我们将用AttributesMapper很容易地得到所有person对象的名字的结果列表。
Example 2.1. AttributesMapper 返回一个简单属性
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
public void setLdapTemplate(LdapTemplate ldapTemplate) {
mplate = ldapTemplate;
}
public List getAllPersonNames() {
return (
"", "(objectclass=person)",
new AttributesMapper() {
public Object mapFromAttributes(Attributes attrs)
throws NamingException {
return ("cn").get();
}
});
} }
上面粗题字部分是AttributesMapper的实现,它通过属性名称获取到了需要的属性值,然后返回结果。中心代码是LdapTemplate枚举了所有发现的数据入口,通过调用对每个入口特定的AttributesMapper收集得到结果,然后把结果放入list。list通过search方法返回结果值。
如果你有标志一个入口的distinguished name(dn),你就可以直接获取这个入口,而不用去搜索它。这个在Java LDAP就叫着一个lookup。下面的例子就展示了一个lookup怎样得到person对象的结果集的。
Example 2.3. A lookup resulting in a Person object
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
public Person findPerson(String dn) {
return (Person) (dn, new PersonAttributesMapper());
}
}
这里将遍历特别的dn,把发现的属性集发送到已经提供的AttributesMapper,然后得到person对象的结果集。
2.2 建立动态的Filters
我们可以使用包里的类建立动态filters实现在搜索中的应用。我们来做下面所需要的filter:(&(objectclass=person)(sn=?)这里我们要用参数lastName的值去取代?的值。下面展示如何实现这个filter:
Example 2.4. Building a search filter dynamically
package ; ?/P>
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
public List getPersonNamesByLastName(String lastName) {
AndFilter filter = new AndFilter();
(new EqualsFilter("objectclass", "person"));
(new EqualsFilter("sn", lastName));
return (
"", (),
new AttributesMapper() {
public Object mapFromAttributes(Attributes attrs)
throws NamingException {
return ("cn").get();
}
});
}
}
为了完成一个通配符搜索,可能要用到WhitespaceWildcardsFilter:
Example 2.5. Building a wildcard search filter
AndFilter filter = new AndFilter();
(new EqualsFilter("objectclass", "person"));
(new WhitespaceWildcardsFilter("cn", cn));
2.3 建立动态dn
标准的Name interface代表了一个普通的名称,它基本上是一个一定规则的组件序列。在那个序列的Name interface也提供了基本的一些操作,比如添加和删除。LdapTemplate提供了Name interface的实现:DistinguishedName。用这个类将大大的简化了建立distinguished
names(dn),特别考虑到有时关于escapings和encodings的复杂规则。下面的例子阐述了DistinguishedName是怎样被用来构造一个dn的。
Example 2.6. Building a distinguished name dynamically
package ;
import guishedName;
import ;
public class PersonDaoImpl implements PersonDao {
public static final String BASE_DN = "dc=example,dc=com";
...
protected Name buildDn(Person p) {
DistinguishedName dn = new DistinguishedName(BASE_DN);
("c", ntry());
("ou", pany());
("cn", lname());
return dn;
}
}
假如一个person有以下属性:
country
Sweden
company
Some Company
fullname
Some Person
上面的代码将产生下面dn的结果:
cn=Some Person, ou=Some Company, c=Sweden, dc=example, dc=com
在java5中,有个Name interface的实现:LdapName。
如果你是在用java5,你可能需要用到LdapName。当然,如果你希望用DistinguishedName,那你可以还用DistinguishedName。
2.4 绑定和解绑定
2.4.1 数据绑定
在Java LDAP中插入数据叫做绑定。为了做到绑定,一个唯一标志新entry的dn是必须的。下面的例子展示了数据是如何通过LdapTemplate绑定的:
Example 2.7. Binding data using Attributes
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
...
public void create(Person p) {
Name dn = buildDn(p);
(dn, null, buildAttributes(p));
}
private Attributes buildAttributes(Person p) { Attributes attrs = new BasicAttributes();
BasicAttribute ocattr = new BasicAttribute("objectclass");
("top");
("person");
(ocattr);
("cn", "Some Person");
("sn", "Person");
return attrs;
}
}
Attributes的建立是在减少和冗长时候起了足够的作用。当然他对进一步的地简化绑定操作提供了可能,这个将在第三章描述。
2.4.2 解绑定数据
在Java LDAP中删除数据就叫着解绑定数据,入口(entry)是需要dn来唯一标志,就像绑定操作一样。下面的例子展示了使用LdapTemplate怎样来解绑定数据:
Example 2.8. Unbinding data
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
...
public void delete(Person p) {
Name dn = buildDn(p);
(dn);
} }
2.5 修改
在Java LDAP,数据修改可以有两种方式:使用rebind或者modifyAttributes。
2.5.1 使用rebind修改
使用rebind修改数据是一种比较鲁莽的方式。它基本上就是跟在绑定后面的解绑定。它看起来像这样:
Example 2.9. Modifying using rebind
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
...
public void update(Person p) {
Name dn = buildDn(p);
(dn, null, buildAttributes(p));
}
}
2.5.2 使用modifyAttributes修改
如果需要修改的属性应该被取代,有一个获取一组修正的方法叫modifyAttributes。
Example 2.10. Modifying using modifyAttributes
package ;
public class PersonDaoImpl implements PersonDao {
private LdapTemplate ldapTemplate;
...
public void updateDescription(Person p) {
Name dn = buildDn(p);
Attribute attr = new BasicAttribute("description", cription())
ModificationItem item = new ModificationItem(E_ATTRIBUTE, attr);
Attributes(dn, new ModificationItem[] {item});
}
}
发布评论