Существуют ли шаблоны для классов моделей / сущностей? - PullRequest
8 голосов
/ 20 января 2010

Каков наилучший подход при извлечении объектов модели из нескольких источников данных?

Например, у меня в приложении есть некоторые данные, которые хранятся в базе данных mySQL с помощью hibernate. Что если я захочу сохранить некоторые другие объекты в EC2 или Google App Engine? Я понимаю, что DAO абстрагируется от реализации работы с конкретным источником данных, но как быть с самими сущностями?

Сначала я думал, что аннотирование моих сущностей аннотациями jpa было отличным решением, но теперь кажется, что я действительно привязал свои сущности к конкретной реализации. Например, в случае с App Engine некоторые из этих аннотаций не имеют смысла.

Кажется, мне нужен чистый класс POJO для представления моих сущностей, полностью свободный от логики постоянства. Если бы я хотел смоделировать собаку, например (да, не очень удачный выбор, но все равно).
Имеет ли смысл иметь абстрактный класс Dog, а затем определять подклассы для работы с конкретными решениями для постоянства: HibernateDog, GAEDog и т. Д.

Спасибо.

Ответы [ 6 ]

4 голосов
/ 20 января 2010

Это отличный вопрос, даже если проблема не новая. Как отрасль, мы часто меняли «общепринятые взгляды» на эту тему на протяжении многих лет. Ответы, которые вы получаете сегодня, не обязательно те, которые вы получите 5 лет назад или через 5 лет в будущем.

Представляя, как я бы хотел бы обработать этот элемент, я удивляюсь некоторым вещам, которые вы не заявили: является ли ваше приложение "системой записи" для сущностей Dog? Какие другие подсистемы / слои / приложения должны знать об объектах Dog.

В Java, когда вы пишете совершенно новые типы, такие как Animal> Dog, вы получаете следующее вознаграждение: возможность написать целую кучу кода, который знает, как взаимодействовать с объектами Animal и объектами Dog. В 2010 году я менее убежден, что это хорошая идея, чем пять лет назад.

Вы отвечаете за разработку базы данных, в которой хранится информация о собаке? Раньше мы делали это все время, но в настоящее время я обычно чувствую себя интегрированным с записями данных, которые фактически управляются другими системами: API Google, сущностями LDAP, хранилищами данных, такими продуктами, какoplesoft и т. Д.

Если вы не отвечаете за определение, что такое собаки и как они взаимодействуют со вселенной, я бы посмотрел на независимый от домена способ моделирования информации о собаке в памяти. Есть тонны: XML / DOM, JSON, Map и т. Д.

Преимущества перемещения данных других людей в этих форматах многочисленны ...

  • вам не нужно писать POJOs
  • они богаты функциями, документацией и тестированием
  • существует множество существующих API для преобразования, манипулирования и сериализации этих существ
  • вы можете повторно использовать ваш вид / контроллер / другой код в других доменах

С другой стороны ... если вы являетесь системой записи данных Dog, рассмотрите возможность использования интерфейсов вместо абстрактных классов. Или, возможно, интерфейсы и абстрактных классов. Java имеет только одно наследование; привязать ваш view / controller / other code к интерфейсам, чтобы гарантировать максимальную гибкость в будущем.

2 голосов
/ 20 января 2010

Вы правы в использовании слоя DAO для абстрагирования деталей источника данных от других слоев. Таким образом, уровень модели фактически не должен знать, какой метод хранения данных или какая база данных используется.

Ответ на ваш вопрос будет следующим: Использовать слой службы. Это слой, где вы размещаете весь свой бизнес-код. Какой объект создать, какой DAO использовать, как подтвердить данные, разграничение транзакций и т. Д.

Итак, сервисный уровень должен отвечать за загрузку / сохранение ваших сущностей. И именно здесь вы должны внедрить логику о том, какой источник данных / базу данных использовать. Используйте инъекцию зависимостей Spring, чтобы помочь вам в этом. Добавьте ваш выбор DAO, сущностей в слой Service.

Классы сущностей: собака, кошка

Классы обслуживания: AnimalCenterService

Классы DAO: AnimalCenterHibernate, AnimalCenterJDBC

Дайте мне знать, если понадобится больше объяснений. Просто мои 2 цента

2 голосов
/ 20 января 2010

JPA-аннотации могут быть хороши тем, что позволяют размещать метаданные объектно-реляционного отображения (ORM) в тех же файлах, что и ваши классы сущностей, но вы абсолютно правы в том, что при объединении метаданных JPA возникают проблемы.с "чистыми" POJO.Это компромисс.

Однако есть альтернатива.Вы можете экспортировать конфигурацию ORM в файлы XML и таким образом не допускать этих деталей в свои классы сущностей.JPA предоставляет синтаксис конфигурации XML, но для своих проектов я предпочитаю использовать собственные отображения XML Hibernate для дополнительной гибкости, которую они обеспечивают.Это может быть не так модно, как подход, основанный на аннотациях, но, по моему опыту, он работает довольно хорошо.

2 голосов
/ 20 января 2010

Одна из проблем с Hibernate заключается в том, что он внедряет свои собственные реализации Collection в класс вашего домена, вызывая проблемы, если вы пытаетесь отправить свой класс по проводной связи с использованием сериализации (например, с сервера на клиент).

В приведенном выше примере я бы поставил под сомнение необходимость предоставления подклассов, специфичных для хранилища:

Do / Должны ли классы действительно содержать состояние, относящееся к способу их хранения? Т.е. является ли эта концепция центральной в классе и, следовательно, достойна ли она использовать ваш "один выстрел" при наследовании (в Java)? Я бы сказал, что более полезная иерархия наследования в вашем примере будет выглядеть примерно так:

  • Animal
    • Млекопитающее
      • Собака
      • Cat

Кроме того, с предложенным вами дизайном вы можете столкнуться с проблемами, если, например, вы хотите сохранить экземпляр Dog в Hibernate, но не знаете, является ли Dog HibernateDog, GAEDog и т. д., и на этом этапе должны выполнять проверки / даункастинг.

1 голос
/ 20 января 2010

Вы не захотите, чтобы ваш постоянный код наследовал от ваших классов сущностей, поскольку это сделало бы невозможным использование наследования для ваших классов сущностей домена. Например, если у вас есть HibernateDog, унаследованный от Dog, вам не разрешат иметь Poodle, унаследованный от Dog, без принудительного указания Poodle на Hibernate.

Один из подходов, который работает, заключается в использовании объектов данных, которые являются специфичными для персистентности. Ваши классы сущностей домена делегировали бы объект сущности данных для его постоянных атрибутов через интерфейс. Затем вы можете заменить различные классы сущностей данных, относящиеся к реализации постоянства, при условии, что они соответствуют вашему интерфейсу сущностей данных.

Собачьи ссылки (и делегаты) на интерфейс DogEntity. Пудель наследует от Dog, PoodleEntity наследует от DogEntity.

HibernateDog реализует DogEntity
HibernatePoodle реализует PoodleEntity и наследует от HibernateDog.
...
StubDog реализует DogEntity
StubPoodle реализует PoodleEntity и наследует от StubDog
...

Вы можете иметь столько типов объектов данных, сколько захотите. Объекты данных будут очень тонкими и будут содержать только постоянные переменные-члены и аннотации или любой другой код, необходимый для сохранения.

Доменные объекты будут содержать бизнес-логику, специфичную для объекта.

1 голос
/ 20 января 2010

То, что у вас есть, кажется правильным. Хороший дизайн не означает, что объекты не привязаны к технологии, это просто означает, что если вы меняете технологию, вы только меняете 1 слой вашего приложения.

Объекты с JPA являются хорошим решением, если вы используете JPA. Помимо этих сущностей у вас может быть больше «сущностей» (POJO), которые связаны с GAE и т. Д.

Об абстрактной собаке и подклассах, которые кажутся излишними, если только вам это действительно не нужно. Если вам действительно нужно, пожалуйста, проверьте объекты DTO: http://en.wikipedia.org/wiki/Data_transfer_object

DTOs используются для последовательной передачи объекта на верхние уровни (выше DAO) (и делают его сериализуемым) даже при работе с несколькими источниками данных / технологиями на уровне постоянства.

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