我有一个应用程序,它已经在使用Spring Framework和Spring JDBC,其中有一个使用SimpleJdbcTemplate和RowMapper类的DAO层。对于从数据库读取的小类结构,这似乎工作得很好。但是,我们需要加载包含其他对象集合的对象,这些对象仍然包含其他对象的集合。
这个问题的“显而易见”解决方案是创建一个命名的RowMapper类或我们的对象,并在构造函数中传递对适当DAO对象的引用。例如:
public class ProjectRowMapper implements ParameterizedRowMapper {
public ProjectRowMapper(AccountDAO accountDAO, ) {
this.accountDAO = accountDAO;
}
public Project mapRow(ResultSet rs, int rowNum) throws SQLException {
Project project= new Project ();
project.setProjecttId( rs.getString("project_id") );
project.setStartDate( rs.getDate("start_date") );
// project.setEtcetera(...);
// this is where the problems start
project.setAccounts( accountDAO.getAccountsOnProject(project.getProjectId()) );
}
}
问题是,即使ProjectDAO和Account DAO共享同一个DataSource实例(在我们的示例中,这是一个连接池),任何数据库访问都是通过不同的连接完成的。
如果对象层次结构甚至有三层深,使用此实现会导致(a)框架对datasource.getConnection()的多次调用,以及(2)更糟糕的结果,因为我们限制了连接池中允许的连接数量,当多个线程试图从数据库加载项目时,可能会出现竞争情况。
在Spring中有没有更好的方法(不需要另一个成熟的ORM工具)来实现这样的对象层次结构的加载?
谢谢,保罗
发布于 2010-06-26 13:36:37
我猜您不使用ORM是有原因的,ORM是解决这类问题的理想工具。
多个连接的问题是递归调用另一个DAO。为了避免使用额外的连接,Account对象应该在项目实例被获取之后检索。在获取项目时,帐户it也会被获取,但不会“实例化”到account实例-它们仍然是it列表,然后在项目DAO完成其工作后填充。
例如,您可以构建一个采用ID列表和DAO实现的自定义列表类型。该列表仅填充ProjectRowMapper中的is,并分配给项目的accounts属性。ID对于列表是私有的--它们不是列表的“内容”,而是以后产生真实内容的一种手段。
一旦Project DAO从RowMapper获取了项目,它就可以指示列表获取保存在列表中的in的帐户。这些帐户是作为的非嵌套操作获取的,因此整个过程在任何时候都只使用一个连接。然而,fetch是在DAO方法的作用域内完成的,所以fetch是急切地完成的-所以没有延迟加载问题需要处理。
https://stackoverflow.com/questions/3085124
复制