JDO技术分析及如何进入企业应用的研究
持久对象查询
JDO查询主要有以下两种方式。
使用Extend查询
Extend可以查询指定类及子类的持久对象。
PersistenceManager
manager = persistenceManagerFactory.
getPersistenceManager();
manager.currentTransaction().begin();
Extend extend =
manager.getExtend(Book.class,true);
//true表明同时查询子类
Iterator it = extend.iterator();
while(it.hasNext())
{
Book book = (Book)it.next();
System.out.println(book.getISBN());
}
extend.closeAll();
manager.currentTransaction().commit();
Extend查询方法,提供了一种基于类的查询途径,它可以与下面的Query构成更为强大的查询。
使用Query查询
Query可以指定过滤条件,是一种常用的查询方式。
下例是查找条件为“书名以‘Java设计模式’开头且出版日期小于今天”的书籍。
String filter =
“((String)name).startsWith(\”Java设计模式\”)
&& publishDate < today”;
Query query =
pm.getQuery(Book.class,filter);
query.declareImports(“import java.util.Date”);
query.declareParameters(“Date today);
Date today = new Date();
results = (Collection)
query.execute(today);
//传入参数值today
if (results.isEmpty())
{
System.out.println(“No data!”);
}else{
Iterator it = results.iterator();
while(it.hasNext())
{
Book book = (Book)it.next();
System.out.println
(“Book Name:” + book.getName()
+ “, ISBN:” + book.getISBN());
}
}
注:该条件使用了一个变元‘today’,通过“declareParameters”来声明该变量,并在“execute”方法中传入该变量的实例。这种带参数的查询,很类似于我们以前采用JDBC的带?的查询方式。
其中startsWith(String s)是JDO提供的标准字符方法,类似的方法还有endsWith(String s)。
JDOQL:上述使用的就是一个JDOQL样例,JDOQL是JDO规范一个组成部分。使用JDOQL可以使用应用在不同的JDO实现上运行。为了解决JDOQL的某些不足,JDO规范提供了支持特定JDO供应商查询语句接口。
查询排序
下例是将查询结果按“出版日期降序、书名升序”进行排序。
Query query =
pm.newQuery(Book.class, filter);
String orderStr =
“publishDate decending, name ascending”;
query.setOrdering(orderStr);
results = query.execute(today);
对象更新
当客户端对业务数据进行了更新后,需要通过业务过程将其更新到持久层中。这有两个过程,首先根据主键找到该实例,接着更新字段及提交。如下例,将指定书目编号的书本的出版日期进行更改。
public void updateBookPublishDate
(String isbn, Date newDate)
{
PersistenceManager pm = null;
try{
pm = pmf.getPersistenceManager();
Object obj =
pm.newObjectIdInstance(Book.class,isbn);
Book book =
(Book)pm.getObjectById(obj,true);
book.setPublishDate(newDate);
}catch(Exception e)
{
xxxContext.setRollbackOnly();
throw new Exception(e);
}finally{
try{
if (pm != null && !pm.isClosed())
{
pm.close();
}
}catch(Exception ex)
{
System.out.println(ex);
}
}
注,在PersistenceManager使用newObjectIdInstance()方法时,JDO是如何知道通过书目编号ISBN来找到该对象呢?其实在本可持久类Book的jdo描述文件中,还需提供如下信息:
<?xml version=“1.0”
encoding = “UTF-8”?>
<!DOCTYPE jdo SYSTEM “jdo.dtd”>
<jdo>
<package name = “business.model”>
<class name = “Book”
identity-type=“application”
objectid-class=“BookKey” >
<field name=“isbn”
primary-key=“true”/>
</class>
</package>
</jdo>
其中“identity-type=“application””声明可持久类Book采用程序标识方式,即应用程序传入ID(字段isbn为“primary-key”)信息,JDO实现构造出指定的“objectid-class”的实例(即newObjectIdInstance过程),并由JDO来检索出指定的持久化对象(即getObjectById)。
BookKey类源码如下:
package businesss.model;
public class BookKey implements
java.io.Serializable
{
public String isbn;
public BookKey()
{
}
public BookKey(String oid)
{
isbn = oid;
}
public String toString()
{
return isbn;
}
public Boolean equals(Object obj)
{
return isbn.equals
((BookKey)obj).isbn);
}
public int hashCode()
{
return isbn.hashCode();
}
}
符合 JDO 的“objectid-class”类,如“BookKey”,须具备以下条件:
类声明为 public,并实现 java.io.Serializable;
带有一个公有且不带参数的构造方法;
当字段作为主键时,须有公有的,且名称和类型与持久类的字段一致,如:public String isbn;
equals 和 hashCode 须使用全部(特指多字段的联合主键)的主键字段值;
类必须有一个构造方法,与 toString 方法的处理过程是逆向过程;即将 toString 的输出值,作为该构造方法的输入值,又可以重新生成该实例(如构造方法“public BookKey(String oid)”)。
0
相关文章