Hibernate: hbm2ddl.auto = обновление в производстве?

Можно ли запускать приложения Hibernate, настроенные с помощью hbm2ddl.auto=update, для обновления схемы базы данных в рабочей среде?

Ответы

Ответ 1

Нет, это небезопасно.

Несмотря на все усилия команды Hibernate, вы просто не можете полагаться на автоматические обновления в производстве. Напишите свои собственные исправления, просмотрите их с помощью DBA, проверьте их, затем примените их вручную.

Теоретически, если hbm2ddl update работал в разработке, он также должен работать в производстве. Но на самом деле это не всегда так.

Даже если он работает нормально, он может оказаться неоптимальным. Администраторы баз данных оплачиваются по какой-то причине.

Ответ 2

Мы делаем это на производстве, хотя приложение не является критически важным и не имеет высокооплачиваемых администраторов баз данных для персонала. Это всего лишь один менее ручной процесс, который подвержен человеческой ошибке - приложение может обнаружить разницу и сделать правильную вещь, плюс вы предположительно протестировали ее в различных средах разработки и тестирования.

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

Ответ 3

Создатели Hibernate не рекомендуют это делать в производственной среде в своей книге "Яркость Java с Hibernate" :

ПРЕДУПРЕЖДЕНИЕ. Мы видели пользователей Hibernate, пытающихся использовать SchemaUpdate для автоматического обновления схемы производственной базы данных. Это может быстро закончиться катастрофой и не будет разрешено вашим администратором баз данных.

Ответ 4

Зайдите в LiquiBase XML для хранения изменений в обновлениях. Я никогда не использовал его до этого года, но я обнаружил, что он очень прост в освоении и делает управление ревизией/миграцией/управлением изменениями БД очень надежным. Я работаю над проектом Groovy/Grails, а Grails использует Hibernate под всем своим ORM (называемым "GORM" ). Мы используем Liquibase для управления всеми изменениями схемы SQL, которые мы делаем довольно часто, поскольку наше приложение развивается с новыми функциями.

В принципе, вы сохраняете XML файл изменений, который вы по-прежнему добавляете по мере развития вашего приложения. Этот файл хранится в git (или независимо от того, что вы используете) с остальной частью вашего проекта. Когда ваше приложение развернуто, Liquibase проверяет таблицу изменений в базе данных, к которой вы подключаетесь, поэтому она будет знать, что уже было применено, тогда она разумно применяет все изменения, которые еще не были применены в файле. На практике он работает отлично, и если вы используете его для всех изменений схемы, то вы можете быть на 100% увереннее, что код, который вы проверяете и развертываете, всегда сможет подключиться к полностью совместимой схеме базы данных.

Удивительно, что я могу взять полностью чистую базу данных mysql на моем ноутбуке, запустить приложение, и сразу же схема настроена для меня. Это также упрощает проверку изменений схемы, применяя их сначала к локальному dev или промежуточному db.

Самый простой способ начать работу с ним - это, вероятно, взять вашу существующую БД, а затем использовать Liquibase для создания исходного файла baseline.xml. Затем в будущем вы можете просто добавить к нему и позволить Liquibase взять на себя управление изменениями схемы.

http://www.liquibase.org/

Ответ 5

Я бы не голосовал. Hibernate, похоже, не понимает, когда изменились типы данных для столбцов. Примеры (с использованием MySQL):

String with @Column(length=50)  ==> varchar(50)
changed to
String with @Column(length=100) ==> still varchar(50), not changed to varchar(100)

@Temporal(TemporalType.TIMESTAMP,TIME,DATE) will not update the DB columns if changed

Есть, вероятно, и другие примеры, такие как толкание длины столбца String выше 255 и просмотр его преобразования в текст, средний текст и т.д. и т.д.

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

Flyway - хороший вариант для решения этой проблемы:

http://flywaydb.org

Ответ 6

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

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

Я использовал его в течение многих лет на множестве разных проектов и никогда не имел ни одной проблемы. Это не хромой ответ, а это не ковбойское кодирование. Это исторический факт.

Человек, который говорит "никогда не делайте этого в производстве", думает о конкретном наборе производственных развертываний, а именно о тех, с которыми он знаком (его компания, его индустрия и т.д.).

Вселенная "производственных развертываний" обширна и разнообразна.

Опытный разработчик Hibernate точно знает, какой DDL будет получен из данной конфигурации сопоставления. Пока вы проверяете и проверяете, что то, что вы ожидаете, попадает в DDL (в dev, qa, staging и т.д.), Вы в порядке.

Когда вы добавляете множество функций, автоматические обновления схем могут быть в режиме реального времени.

Список обновлений автозапуска не будет бесконечным, но некоторые примеры - перенос данных, добавление столбцов с нулевыми значениями, изменение имени столбца и т.д. и т.д.

Также вам нужно позаботиться о кластеризованных средах.

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

Ответ 7

Как я объяснил в этой статье, не рекомендуется использовать hbm2ddl.auto в производстве.

Единственный способ управлять схемой базы данных - использовать инкрементные сценарии миграции, потому что:

  • сценарии будут находиться в VCS по вашей базе кода. Когда вы проверяете ветку, вы воссоздаете всю схему с нуля.
  • инкрементные скрипты могут быть протестированы на сервере QA, прежде чем применяться в производстве
  • нет необходимости в ручном вмешательстве, так как сценарии могут выполняться Flyway, следовательно, это уменьшает вероятность человеческой ошибки, связанной с запуск сценариев вручную.

Даже в Hibernate User Guide советуем избегать использования инструмента hbm2ddl для производственных сред.

введите описание изображения здесь

Ответ 8

Я бы не рискнул, потому что вы можете потерять данные, которые должны были быть сохранены. hbm2ddl.auto = update - это просто простой способ обновить базу данных разработчиков.

Ответ 9

Мы делаем это в проекте, который работает в течение нескольких месяцев, и до сих пор у него не было проблемы. Имейте в виду 2 ингредиента, необходимые для этого рецепта:

  • Создайте свою объектную модель с помощью подхода обратной совместимости, то есть обесценить объекты и атрибуты, а не удалять/изменять их. Это означает, что если вам нужно изменить имя объекта или атрибута, оставьте старый как есть, добавьте новый и напишите какую-то миграцию script. Если вам нужно изменить связь между объектами, если вы уже находитесь в производстве, это означает, что ваш дизайн был неправильным в первую очередь, поэтому попробуйте подумать о новом способе выражения новых отношений, не затрагивая старые данные.

  • Всегда резервное копирование базы данных до развертывания.

Я считаю, что после прочтения этой статьи 90% людей, принимающих участие в этом обсуждении, ужасаются только мыслью об использовании таких автоматических технологий в производственной среде. Некоторые бросают мяч в DBA. Подумайте, хотя подумайте, что не все производственные среды обеспечат DBA, и не многие команды разработчиков могут позволить себе один (по крайней мере, для проектов среднего размера). Итак, если мы говорим о командах, где все должны делать все, мяч на них.

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

Лично я никогда не вернусь к написанию сценариев вручную для расширения любого типа схемы, но это только мое мнение. И после того, как в последнее время я начал использовать базы данных без схемы NoSQL, я вижу, что более чем скоро все эти операции на основе схем будут принадлежать прошлому, поэтому вам лучше начать менять свою перспективу и смотреть вперед.

Ответ 10

  • В моем случае (Hibernate 3.5.2, Postgresql, Ubuntu) установка hibernate.hbm2ddl.auto=update создавала новые таблицы и создавала новые столбцы в уже существующих таблицах.

  • Он не удалял ни таблицы, ни столбцы, ни столбцы. Его можно назвать безопасным вариантом, но что-то вроде hibernate.hbm2ddl.auto=create_tables add_columns будет более понятным.

Ответ 11

Это не безопасно, не рекомендуется, но возможно.

У меня есть опыт использования приложения с автоматическим обновлением на рабочем месте.

Итак, основные проблемы и риски, обнаруженные в этом решении:

  • Развернуть в неправильной базе данных. Если вы допустите ошибку, чтобы запустить сервер приложений со старой версией приложения (EAR/WAR/etc) в неправильной базе данных... У вас будет много новых столбцов, таблиц, внешних ключей и ошибок. Та же проблема может возникнуть с простой ошибкой в файле источника данных (скопировать/вставить файл и забыть изменить базу данных). В резюме, ситуация может быть катастрофой в вашей базе данных.
  • Запуск сервера приложений занимает слишком много времени. Это происходит потому, что Hibernate пытается найти все созданные таблицы/столбцы/и т.д. Каждый раз, когда вы запускаете приложение. Он должен знать, что (таблица, столбец и т.д.) Нужно создать. Эта проблема будет только усугубляться по мере роста таблиц базы данных.
  • Инструменты базы данных практически невозможно использовать. Чтобы создать сценарии DDL или DML базы данных для запуска с новой версией, вам нужно подумать о том, что будет создано при автообновлении после запуска сервера приложений. Например, если вам нужно заполнить новый столбец некоторыми данными, вам нужно запустить сервер приложений, подождать, пока Hibernate создаст новый столбец, и только после этого запустить скрипт SQL. Как видите, инструменты миграции баз данных (такие как Flyway, Liquibase и т.д.) Практически невозможно использовать с включенным автообновлением.
  • Изменения в базе данных не централизованы. С возможностью создания таблиц Hibernate и всего остального трудно наблюдать за изменениями в базе данных в каждой версии приложения, поскольку большинство из них вносятся автоматически.
  • Поощряет сбор мусора в базе данных. Из-за "легкого" использования автообновления есть вероятность, что ваша команда пренебрегает удалением старых столбцов и старых таблиц, потому что автообновление в спящем режиме не может этого сделать.
  • Грядущая катастрофа. Неизбежный риск некоторой катастрофы на производстве (как некоторые люди упоминали в других ответах). Даже если приложение работает и обновляется годами, я не считаю его безопасным выбором. Я никогда не чувствовал себя в безопасности при использовании этой опции.

Поэтому я не буду рекомендовать использовать автообновление в производстве.

Если вы действительно хотите использовать автообновление в производственной среде, я рекомендую:

  • Раздельные сети. Ваша тестовая среда не может получить доступ к среде гомологов. Это помогает предотвратить развертывание, которое должно быть в тестовой среде, изменить базу данных омологации.
  • Управление порядком скриптов. Вам необходимо организовать выполнение сценариев перед развертыванием (изменение таблицы структур, удаление таблицы/столбцов) и сценариев после развертывания (заполнить информацию для новых столбцов/таблиц).

И, в отличие от других постов, я не думаю, что автообновление включало его, связанное с "очень хорошо оплачиваемыми" администраторами баз данных (как упоминалось в других постах). У администраторов баз данных есть более важные дела, чем писать операторы SQL для создания/изменения/удаления таблиц и столбцов. Эти простые каждодневные задачи могут быть выполнены и автоматизированы разработчиками и переданы только для рассмотрения администратору БД, не требуя, чтобы Hibernate и администраторы БД "очень хорошо оплачивали" их написание.

Ответ 12

  • Обычно корпоративные приложения в крупных организациях работают со сниженными привилегиями.

  • Имя пользователя базы данных может не иметь привилегии DDL для добавления столбцов, которые требуется hbm2ddl.auto=update.

Ответ 13

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

Ответ 14

Я согласен с Владимиром. Администраторы в моей компании определенно не оценили бы это, если бы я даже предложил такой курс.

Кроме того, создание SQL script вместо слепого доверия Hibernate дает вам возможность удалять поля, которые больше не используются. Hibernate этого не делает.

И я считаю, что сравнение производственной схемы с новой схемой дает вам еще лучшее представление о том, как вы изменились в модели данных. Вы знаете, конечно, потому что вы это сделали, но теперь вы видите все изменения за один раз. Даже те, которые заставляют вас идти "Что за черт?!".

Есть инструменты, которые могут сделать для вас дельта схемы, так что это даже не тяжелая работа. И тогда вы точно знаете, что произойдет.

Ответ 15

Схема приложений может развиваться во времени; если у вас есть несколько установок, которые могут быть в разных версиях, у вас должен быть какой-то способ убедиться, что ваше приложение, какой-то инструмент или script способен переносить схему и данные с одной версии поэтапно на любой следующий.

Все ваше постоянство в сопоставлениях спящего режима (или аннотации) - очень хороший способ контролировать эволюцию схемы.

Вы должны учитывать, что эволюция схемы имеет несколько аспектов:

  • эволюция схемы базы данных в добавление большего количества столбцов и таблиц

  • удаление старых столбцов, таблиц и отношения

  • заполнение новых столбцов по умолчанию

Инструменты спящего режима важны, в частности, в случае (например, по моему опыту), у вас разные версии одного и того же приложения во многих различных типах баз данных.

Точка 3 очень чувствительна, если вы используете Hibernate, так как в случае, если вы вводите новое значение логического значения или числовое значение, если Hibernate найдет любое нулевое значение в таких столбцах, если возникнет исключение.

Итак, что бы я сделал: действительно используйте возможности инструментов Hibernate для обновления схемы, но вы должны добавить вместе с ним некоторые обратные вызовы обслуживания данных и схемы, например, для заполнения значений по умолчанию, удаления ненужных столбцов и тому подобного. Таким образом, вы получаете преимущества (сценарии обновления базы данных, независимые от базы данных, а также избегаете дублирования кодирования обновлений, в реальном времени и в сценариях), но вы также охватываете все аспекты операции.

Так, например, если обновление версии состоит только в добавлении свойства varchar valued (следовательно, column), которое по умолчанию может иметь значение null, с автоматическим обновлением вы будете сделаны. Там, где требуется дополнительная сложность, потребуется больше работы.

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

Ответ 16

Сейчас я столкнулся с этой проблемой.

Недавно я начал работать в проекте, где в разработке мы используем автоматическое обновление и производство. Серьезно, это не имеет для меня никакого смысла, потому что, если я собираюсь писать sql вручную в конце, давайте сделаем это вручную и в процессе разработки.

Я спросил разработчика старше меня в проекте, и он указал мне на эту тему, но c'mom, если мы не сможем использовать автоматическое обновление в производстве, я не вижу причин использовать его в разработке, потому что он улавливает поддельное чувство продуктивности, но на самом деле это создает большую проблему, как моя команда будет знать, что вы делали, какие таблицы вы обновляете, что мне нужно изменить перед развертыванием в производство.

Мой совет: возьмите ручку автоматического обновления и используйте ее во всем или вообще не используйте.