Spring Framework JDBC DAO с агрегацией / составлением - PullRequest
4 голосов
/ 21 июня 2010

У меня есть приложение, которое уже использует Spring Framework и Spring JDBC со слоем DAO, используя классы SimpleJdbcTemplate и RowMapper.Кажется, это очень хорошо работает с небольшими структурами классов, считываемыми из базы данных.Однако нам необходимо загрузить объекты, которые содержат коллекции других объектов, которые по-прежнему содержат коллекции других объектов.

«Очевидным» решением этой проблемы является создание именованного класса 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 и DAO учетной записи совместно используют один и тот же экземпляр DataSource (в нашем случае это пул соединений), любой доступ к базе данных осуществляется через другое соединение.

Если иерархия объектов имеет глубину даже три уровня, использование этой реализации приводит к (a) многим вызовам со стороны платформы для datasource.getConnection () и (2) еще хуже, поскольку мы ограничиваем количество соединенийразрешено в нашем пуле соединений потенциальные условия гонки, когда несколько потоков пытаются загрузить проект из базы данных.

Есть ли лучший способ в Spring (без другого полноценного инструмента ORM) добиться загрузки такихиерархии объектов?

Спасибо, Пол

1 Ответ

2 голосов
/ 26 июня 2010

Полагаю, у вас есть причины не использовать ORM, который является идеальным инструментом для решения подобных проблем.

Проблема с несколькими подключениями - рекурсивный вызов другого DAO. Чтобы избежать использования дополнительных подключений, объекты Account должны быть получены позже, после того, как будет извлечен экземпляр проекта. При получении проекта идентификаторы учетной записи также извлекаются, но не «создаются» для экземпляров учетных записей - они остаются в виде списка идентификаторов, которые затем заполняются после того, как DAO проекта выполнил свою работу.

Например, вы можете создать собственный тип List, который принимает список идентификаторов и реализацию DAO. Список заполняется только идентификаторами в ProjectRowMapper и присваивается свойству учетных записей проекта. Идентификаторы являются частными для списка - они не являются «содержимым» списка, а средством для создания реального содержимого позже.

После того, как Project DAO извлек проекты из RowMapper, он может дать указание списку затем выбрать учетные записи для идентификаторов, которые были сохранены в списке. Учетные записи выбираются как не вложенная операция, поэтому весь процесс использует только одно соединение в любое время. Тем не менее, выборка выполняется в рамках метода DAO, поэтому выборка выполняется с нетерпением, поэтому нет проблем с отложенной загрузкой.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...