Який Java ORM ви віддаєте перевагу і чому? [зачинено]


262

Це досить відкрите питання. Я буду починати новий проект і розглядаю різні ORM для інтеграції з доступом до бази даних.

У вас є якісь фаворити? Чи є якісь рекомендації, щоб ви не трималися осторонь?



Погляньте на мікроорганізми - тонкі обгортки навколо технології доступу до БД платформи - як sql2o для Java github.com/aaberg/sql2o або ServiceStack.OrmLite для .NET github.com/ServiceStack/ServiceStack.OrmLite
tomaszkubacki

3
Після використання ORM більше 5 років моїм особистим вибором є Spring JDBC над ORM, а другим кращим є iBatis (MyBatis), мені не подобається сплячий стан через криву навчання, менший рівень контролю та ефективність роботи.

Тут (також закрито) перелік легких обгорток , які JDBC можна використовувати в якості альтернативи повномасштабних ORMs: stackoverflow.com/questions/7137929 / ...
Vadzim

Відповіді:


237

Я перестав використовувати ORM.

Причина - не якась велика вада в концепції. Зимова сплячка працює добре. Натомість я виявив, що запити мають низькі накладні витрати, і я можу вмістити безліч складних логік у великі SQL запити і перенести багато моєї обробки в базу даних.

Тому подумайте просто про використання пакету JDBC.


81
Це та сама історія знову і знову з ORM: хороший швидкий початковий розвиток та великий витрата ваших ресурсів далі на проекті при відстеженні помилок та неефективності, пов'язаних з ORM. Я також ненавиджу той факт, що, здається, дає розробникам уявлення, що їм ніколи не доводиться писати конкретні оптимізовані запити.
Eelco

7
Гей, чи все це правда для великих реальних проектів?
santiagobasulto

30
Я згоден. Я використовую ORM вже понад 3 роки, і я не можу сказати, скільки часу було витрачено (все ще є) для вирішення завдань, що стосуються наполегливості. У нас немає жодного контролю над тим, що відбувається "під кришкою", конфігурацій занадто багато, щоб ефективно керувати, і є поведінки, які можуть звести з розуму одного. З іншого боку, я маю підтримку основних баз даних і ніколи не повинен переживати за їх відмінності.
marcolopes

58
чому б не використовувати обидва, залежно від складності запиту / транзакції? це не так, як вони взаємно виключають.
амфібій

6
@WillSheppard так Буде. Я дуже багато використовую Django ORM, і він чудово працює. Я думаю, що різниця може бути в динамічному характері пітона (і perl). Використання ORM на Java - це біль. Але в динамічних мовах це може бути справді виразним. Існує кілька чудових проектів для вбудування операцій ORM, таких як DSL в Python, і вони чудові.
santiagobasulto

97

Ні, тому що наявність ORM забирає занадто багато контролю з невеликими перевагами. Отримані заощадження часу легко знімаються, коли вам доведеться налагоджувати відхилення, що виникають внаслідок використання ORM. Крім того, ORM відштовхують розробників від вивчення SQL і того, як працюють реляційні бази даних, і використовують це на свою користь.


4
Я згоден з цим твердженням. Скільки від загального часу розробки буде витрачено на написання наполегливого коду? Я думаю, що менше 10-15%
adrian.tarau

16
Це залежить. Звичайно, якщо ви використовуєте лише один конкретний вид бази даних, легко уникнути, не використовуючи ORM. Однак, коли вам потрібно підтримувати інші види баз даних, вона може швидко стати менш керованою.
Джейсон Бейкер

3
"Отримані заощадження часу легко знімаються, коли вам доведеться налагоджувати відхилення внаслідок використання ORM" Це неправда, коли крива навичок є гідним фактором при виборі технологій.
elsadek

7
Ваш аргумент може бути запропонований проти використання будь-якої бібліотеки. Найбільші вигоди від ORM - такі речі, як одиниці роботи, відображення об'єктів, відстеження змін, ледача завантаження, міграції та взаємозв'язки. Це чудова річ вміти писати user.profile.givenName і не хвилюватись, яку структуру використовували для зберігання даних для неї.
Олексій

1
Його можна використовувати проти будь-якої бібліотеки, але в різній мірі. Взагалі я великий прихильник використання бібліотек - навіщо знову винаходити колесо? Однак у цьому випадку я відчуваю, що сплячий режим для більшості використовує занадто велику вагу, і більш легкий ОРМ буде більш кращим. Мій досвід ґрунтується на багаторічному досвіді, який розвивався зі сплячої зірки та ретельно вивчав його додаткові та вихідні результати.
симон

92

Багато ORM чудові, ви повинні знати, чому ви хочете додати абстракцію поверх JDBC. Я можу порекомендувати вам http://www.jooq.org (відмова від відповідальності: я творець jOOQ, тому ця відповідь упереджена). jOOQ містить таку парадигму:

  • SQL - хороша річ. Багато речей можна досить добре виразити в SQL. Немає необхідності в повній абстракції SQL.
  • Модель реляційних даних - хороша річ. Це доведена найкраща модель даних за останні 40 років. Немає потреби в базах даних XML або справді об'єктно-орієнтованих моделей даних. Натомість ваша компанія запускає кілька примірників Oracle, MySQL, MSSQL, DB2 або будь-яких інших RDBMS.
  • SQL має структуру та синтаксис. Вона не повинна виражатися за допомогою конкатенації рядків "низького рівня" в JDBC - або "високого рівня" String конкатенації в HQL - обидві вони схильні приймати синтаксичні помилки.
  • Змінна прив'язка має тенденцію бути дуже складною для вирішення основних запитів. ТО - це те, що слід абстрагувати.
  • POJO відмінно під час написання коду Java, маніпулювання даними бази даних.
  • POJO - це біль писати та підтримувати вручну. Генерація коду - це шлях. Ви матимете безпечні для компіляції запити, включаючи безпеку типу даних.
  • База даних виходить першою. Хоча додаток, що знаходиться поверх вашої бази даних, може змінюватися з часом, сама база даних, ймовірно, триватиме довше.
  • Так, у вас є збережені процедури та визначені користувачем типи (UDT) у вашій застарілій базі даних. Ваш інструмент бази даних повинен це підтримувати.

Є багато інших хороших ОРМ. Особливо сплячий або iBATIS мають велике співтовариство. Але якщо ви шукаєте інтуїтивно зрозумілий, простий, я скажу, спробуйте jOOQ. Вам сподобається! :-)

Перевірте цей приклад SQL:

  // Select authors with books that are sold out
  SELECT * 
    FROM T_AUTHOR a
   WHERE EXISTS (SELECT 1
                   FROM T_BOOK
                  WHERE T_BOOK.STATUS = 'SOLD OUT'
                    AND T_BOOK.AUTHOR_ID = a.ID);

І як це можна виразити в jOOQ:

  // Alias the author table
  TAuthor a = T_AUTHOR.as("a");

  // Use the aliased table in the select statement
  create.selectFrom(a)
        .whereExists(create.selectOne()
                           .from(T_BOOK)
                           .where(T_BOOK.STATUS.equal(TBookStatus.SOLD_OUT)
                           .and(T_BOOK.AUTHOR_ID.equal(a.ID))))));

1
Інструменти ORM такі чудові, як вам вдасться правильно їх використовувати. Є проекти, де інструменти ORM працюють як принади, а в інших вони взагалі не підходять. Врешті-решт, відповідальність на те, щоб вибрати правильний інструмент для своїх проектних вимог, належить команді розробників. Інструменти ORM є складними. На жаль, лише частина всіх розробників витратить час, щоб зрозуміти, як вони працюють. Решта просто звинувачують інструмент і скажуть, що це погано. Питання полягає в тому: чи дає найбільш відповідна відповідь найкращі поради? > Тому подумайте просто про використання пакету JDBC. Ми дійсно хочемо використовувати звичайний JDBC?
Влад Міхалча

Я намагаюся не пускати "База даних приходить першою." Додаток містить бізнес-правила щодо функцій, про які вимагає клієнт, і вони майже ніколи не просять створити базу даних. Це технічна деталь, визначена під час впровадження.
Kwebble

58

Впадає в сплячку, оскільки це в основному стандарт дефакто на Яві і був однією з рушійних сил у створенні JPA. Він отримує чудову підтримку навесні, і майже кожен Java-сервіс підтримує його. Нарешті, GORM - це дійсно крута обгортка навколо неї, яка робить динамічні шукачі тощо, використовуючи Groovy.

Його навіть перенесли в .NET (NHibernate), щоб ви могли використовувати його і там.


4
Я голосую Hib теж, але з важливим доповненням: ми повинні використовувати JPA API тільки навіть якщо реалізація JPA є фактично наданої Hib.
Володимир Дюжев

52

Зимує, тому що:

  • стабільна - існуючи стільки років, їй не вистачає великих проблем
  • диктує стандарти в області ORM
  • реалізує стандарт (JPA), крім того, щоб його диктувати.
  • має багато інформації про це в Інтернеті. Існує багато навчальних посібників, поширених рішень проблем тощо
  • є потужним - ви можете перевести дуже складну об'єктну модель у реляційну модель.
  • він підтримує будь-які великі та середні RDBMS
  • з ним легко працювати, як тільки ви його добре навчитеся

Кілька пунктів про те, чому (і коли) використовувати ORM:

  • ви працюєте з об’єктами у вашій системі (якщо ваша система добре розроблена). Навіть якщо ви користуєтеся JDBC, ви в кінцевому підсумку зробите деякий шар перекладу, щоб ви перенесли свої дані вашим об'єктам. Але я думаю, що сплячий режим краще перекладати, ніж будь-яке рішення на замовлення.
  • це не позбавляє вас контролю. Ви можете керувати речами дуже дрібними деталями, а якщо в API немає певної віддаленої функції - виконайте власний запит, і він у вас є.
  • будь-яка система середнього або більшого розміру не може дозволити собі одну тону запитів (будь то в одному місці або розкидана по всьому), якщо вона спрямована на підтримку
  • якщо продуктивність не є критичною. Hibernate додає накладні результати, які в деяких випадках не можна ігнорувати.

Коли я порівнюю сплячку та JPA, я переходжу до сплячки, а якщо порівнюю JPA та JDO - я йду на JDO! Мені дуже подобається JDO, але мені подобаються дві особливості Hibernate (які відсутні в JDO), одна - @Filters, а інша - ви можете зіставити поля версій (для оптимістичного блокування) у звичайні поля, що неможливо в JDO .
Амір Пашазаде

27

Я рекомендую використовувати MyBatis . Це тонкий шар на вершині JDBC, дуже просто зіставити об’єкти в таблиці і все ще використовувати звичайний SQL, все під вашим контролем.


10
Ібатіс для складних зчитувань і сплячий режим для створення, оновлення видалення та простого читання - ідеальний вибір.
Дарпет

19

Я мав по-справжньому хороший досвід роботи з Avaje Ebean, коли я писав заявку JavaSE середнього розміру.

Він використовує стандартні анотації JPA для визначення об'єктів, але відкриває набагато простіший API (No EntityManager або будь-яке з цього прикріпленого / відокремленого об'єкта лайно). Він також дозволяє легко використовувати запити SQL або звичайні дзвінки JDBC про події, коли це необхідно.

Він також має дуже приємний для живлення та безпечний тип API для запитів. Ви можете писати такі речі, як:

List<Person> boys = Ebean.find(Person.class)
                                  .where()
                                       .eq("gender", "M")
                                       .le("age", 18)
                                  .orderBy("firstName")
                                  .findList();

6
Мені повинно бути трохи дивно ... виберіть із Особи, де стать = 'М' та вік <18 за наказом firstName просто виглядає мені набагато краще :-)
Eelco

4
Це одна з кращих орм, яку я бачив у Java. Рішення використовувати сингл є освіжаючим і надає йому величезну практичну перевагу перед іншими.
opsb

Я думаю , що ви маєте в виду вільно не рідина.
Мондід'єр

@opsb Я думаю, що технічно це моностата, а не сингл.
Мондід'єр

Як розпочати роботу з Avaje Ebean ORM? Будь-які відео Підручники ??
Авінаш

11

SimpleORM , тому що це прямо і не магічно. Він визначає всі метадані структури даних у коді Java і є дуже гнучким.

SimpleORM надає функціонал, подібний до режиму глибокого сну, шляхом відображення даних у реляційній базі даних на об'єкти Java в пам'яті. Запити можна задавати в термінах об'єктів Java, ідентифікація об'єкта вирівнюється з ключами бази даних, відносини між об'єктами підтримуються, а модифіковані об'єкти автоматично передаються в базу даних з оптимістичними блокуваннями.

Але на відміну від Hibernate, SimpleORM використовує дуже просту структуру об'єктів та архітектуру, що дозволяє уникнути необхідності складного розбору, обробки байтового коду і т.д. залежність (Slf4j). (Зимова сплячка становить понад 2400 КК та близько 2000 КЗ залежних банок.) Це робить SimpleORM легким для розуміння та значно зменшує технічний ризик.


Не використовував його, але ActiveObjects описує себе як такий, що перебуває у сплячому режимі на їхньому веб-сайті, тому напевно є деяка схожість.
Абдулла Джибалі

10

Eclipse Link , з багатьох причин, але помітно, я відчуваю, що в ньому менше набряку, ніж у інших основних потокових рішень (принаймні, менше у вас в обличчі).

Oh та Eclipse Link були обрані для опорної реалізації для JPA 2.0


5

Хоча я поділяю занепокоєння щодо заміни Java для запитів у форматі SQL у вільній формі, я дійсно думаю, що люди, що критикують ORM, роблять це через загально поганий дизайн додатків.

True OOD керується класами та відносинами, і ORM дає вам послідовне відображення різних типів відносин та об'єктів. Якщо ви використовуєте інструмент ORM і в кінцевому підсумку кодуєте вирази запитів будь-якою мовою запиту, яку підтримує рамка ORM (включаючи, але не обмежуючись ними, дерева виразів Java, методи запитів, OQL тощо), ви, безумовно, робите щось не так, тобто модель вашого класу швидше за все, не підтримує ваші вимоги так, як слід. Чистий дизайн програми насправді не потребує запитів на рівні програми. Я рефакторинг багатьох проектів, коли люди почали використовувати рамку ORM так само, як і їх використовували для вбудовування струнних констант SQL у свій код, і врешті-решт, всі здивувались тому, наскільки просто та ремонтоване отримує вся програма, коли ви співпадаєте доповнити модель класу за допомогою моделі використання. Зрозуміло, для таких речей, як функціональність пошуку тощо, вам потрібна мова запитів, але навіть тоді запити настільки обмежені, що створювати навіть складний перегляд та відображення, що для стійкого класу, що читається лише набагато приємніше підтримувати та переглядати, ніж будувати вирази якоюсь мовою запитів у коді вашої програми. Підхід VIEW також використовує можливості бази даних і завдяки матеріалізації може бути набагато кращим за продуктивність, ніж будь-який написаний вручну SQL у вашому джерелі Java. Отже, я не бачу жодної причини для нетривіальної програми НЕ використовувати ORM. але навіть тоді запити настільки обмежені, що створювати навіть складний VIEW та відображати, що для стійкого класу, який є лише для читання, набагато приємніше підтримувати та переглядати, ніж будувати вирази на якійсь мові запитів у коді вашої програми. Підхід VIEW також використовує можливості бази даних і завдяки матеріалізації може бути набагато кращим за продуктивність, ніж будь-який написаний вручну SQL у вашому джерелі Java. Отже, я не бачу жодної причини для нетривіальної програми НЕ використовувати ORM. але навіть тоді запити настільки обмежені, що створювати навіть складний VIEW та відображати, що для стійкого класу, який є лише для читання, набагато приємніше підтримувати та переглядати, ніж будувати вирази на якійсь мові запитів у коді вашої програми. Підхід VIEW також використовує можливості бази даних і завдяки матеріалізації може бути набагато кращим за продуктивність, ніж будь-який написаний вручну SQL у вашому джерелі Java. Отже, я не бачу жодної причини для нетривіальної програми НЕ використовувати ORM.


11
Якщо ви будуєте додатки поверх стійкого магазину, як багато хто з нас, будь то RDBMS або якийсь аромат NoSQL, цей магазин матиме власний ефективний спосіб доступу до нього. Намагатися абстрагуватися від цього занадто багато - це просто переобладнання. Будучи надто завзятим щодо "справжнього OOD", вони отримують архітектури космонавтів, для яких Java є сумнозвісною.
Eelco
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.