java - example - spring datasource initialization mode always
Hibernate hbm2ddl.auto posibles valores y lo que hacen? (13)
Tengo muchas ganas de saber más sobre la actualización, la exportación y los valores que se pueden dar a hibernate.hbm2ddl.auto
¿Necesito saber cuándo usar la actualización y cuándo no? ¿Y cuál es la alternativa?
Estos son cambios que podrían suceder sobre DB:
- nuevas mesas
- Nuevas columnas en tablas antiguas.
- columnas eliminadas
- el tipo de datos de una columna cambió
- Un tipo de columna cambió sus atributos.
- mesas caídas
- valores de una columna cambiados
¿En cada caso cuál es la mejor solución?
Aunque es un post bastante antiguo, pero como hice algunas investigaciones sobre el tema, pensé en compartirlo.
hibernate.hbm2ddl.auto
Según la documentación puede tener cuatro valores válidos:
crear | actualizar | validar | crear-soltar
La siguiente es la explicación del comportamiento mostrado por estos valores:
- crear : - cree el esquema, los datos previamente presentes (si existen) en el esquema se pierden
- actualización: - actualice el esquema con los valores dados.
- validar: - validar el esquema. No hace ningún cambio en el DB.
- create-drop: crea el esquema con la destrucción de los datos presentes anteriormente (si existe). También elimina el esquema de la base de datos cuando se cierra SessionFactory.
Los siguientes son los puntos importantes que vale la pena destacar:
- En caso de actualización , si el esquema no está presente en la base de datos, se creará el esquema.
- En caso de validación , si el esquema no existe en la base de datos, no se crea. En su lugar, generará un error: -
Table not found:<table name>
- En caso de crear y soltar , el esquema no se elimina al cerrar la sesión. Cae solo al cerrar el SessionFactory.
En caso de que si le diera algún valor a esta propiedad (digamos abc, en lugar de los cuatro valores mencionados anteriormente) o simplemente se deje en blanco. Muestra el siguiente comportamiento:
-Si el esquema no está presente en la base de datos: - Crea el esquema
-Si el esquema está presente en la base de datos: - actualice el esquema.
Creo que deberías concentrarte en el
SchemaExport Class
Esta clase hace que su configuración sea dinámica. Así que le permite elegir las suites que mejor se adapten ...
De la documentación comunitaria :
hibernate.hbm2ddl.auto Valida o exporta automáticamente el esquema DDL a la base de datos cuando se crea SessionFactory. Con create-drop, el esquema de la base de datos se eliminará cuando SessionFactory se cierre explícitamente.
por ejemplo, validar | actualizar | crear | crear-soltar
Así que la lista de opciones posibles son,
- validar : validar el esquema, no realiza cambios en la base de datos.
- actualizar : actualizar el esquema.
- crear : crea el esquema, destruyendo los datos anteriores.
- create-drop : descarta el esquema cuando SessionFactory se cierra explícitamente, generalmente cuando se detiene la aplicación.
Estas opciones parecen ser herramientas para desarrolladores y no para facilitar bases de datos de nivel de producción; es posible que desee consultar la siguiente pregunta; Hibernate: hbm2ddl.auto = ¿actualización en producción?
Dediqué una publicación de blog para las estrategias de generación de DDL de Hibernate más comunes:
- El
hibernate.hbm2ddl.auto="update"
es conveniente pero menos flexible si planea agregar funciones o ejecutar algunos scripts personalizados. - El enfoque más flexible es utilizar Flyway .
Sin embargo, incluso si usa Flyway, aún puede generar el script de migración inicial utilizando hbm2ddl. En este artículo , puede ver cómo puede combinar el modelo de entidad JPA con el modelo de tabla jOOQ.
En teoría, puede configurar hibernate.hbm2ddl.auto = update para actualizar su base de datos con cambios en su modelo, pero no confiaría eso en una base de datos de producción. Una versión anterior de la documentación decía que esto era experimental, al menos; No sé el estado actual.
Por lo tanto, para nuestra base de datos de producción, no configure hibernate.hbm2ddl.auto; el valor predeterminado es no realizar cambios en la base de datos. En su lugar, creamos manualmente un script de actualización de DDL de SQL que aplica los cambios de una versión a la siguiente.
La propiedad de configuración se llama hibernate.hbm2ddl.auto
En nuestro entorno de desarrollo, configuramos hibernate.hbm2ddl.auto=create-drop
para eliminar y crear una base de datos limpia cada vez que implementamos, para que nuestra base de datos se encuentre en un estado conocido.
En teoría, puede configurar hibernate.hbm2ddl.auto=update
para actualizar su base de datos con cambios en su modelo, pero no confiaría eso en una base de datos de producción. Una versión anterior de la documentación decía que esto era experimental, al menos; No sé el estado actual.
Por lo tanto, para nuestra base de datos de producción, no configure hibernate.hbm2ddl.auto
; el valor predeterminado es no realizar cambios en la base de datos. En su lugar, creamos manualmente un script de actualización de DDL de SQL que aplica los cambios de una versión a la siguiente.
Si no desea utilizar cadenas en su aplicación y está buscando constantes predefinidas, eche un vistazo a la clase org.hibernate.cfg.AvailableSettings
incluida en el JAR de Hibernate, donde encontrará una constante para todas las configuraciones posibles. En tu caso por ejemplo:
/**
* Auto export/update schema using hbm2ddl tool. Valid values are <tt>update</tt>,
* <tt>create</tt>, <tt>create-drop</tt> and <tt>validate</tt>.
*/
String HBM2DDL_AUTO = "hibernate.hbm2ddl.auto";
También está el valor no documentado de "ninguno" para desactivarlo por completo.
Yo usaría liquibase para actualizar tu db. La función de actualización del esquema de Hibernate en realidad solo está bien para un desarrollador mientras desarrollan nuevas funciones. En una situación de producción, la actualización db debe manejarse con más cuidado.
validar: validar el esquema, no cambiar pasa a la base de datos. actualización: actualice el esquema con la consulta actualmente ejecutada. crear: crea nuevos esquemas cada vez, y destruye datos anteriores. create-drop: descarta el esquema cuando la aplicación se detiene o SessionFactory se cierra explícitamente.
hibernate.hbm2ddl.auto
valida automáticamente y exporta DDL al esquema cuando se crea la sessionFactory.
Por defecto, no realiza ninguna creación o modificación automáticamente en la base de datos. Si el usuario establece uno de los valores a continuación, está haciendo cambios de esquema DDL automáticamente.
crear - haciendo crear un esquema
<entry key="hibernate.hbm2ddl.auto" value="create">
actualizar - actualizando el esquema existente
<entry key="hibernate.hbm2ddl.auto" value="update">
validar - validar esquema existente
<entry key="hibernate.hbm2ddl.auto" value="validate">
create-drop: crea y elimina el esquema automáticamente cuando una sesión se inicia y finaliza
<entry key="hibernate.hbm2ddl.auto" value="create-drop">
validate
: valida el esquema y no realiza cambios en la base de datos.
Supongamos que ha agregado una nueva columna en el archivo de mapeo y realiza la operación de inserción, lanzará una Excepción "falta la columna XYZ" porque el esquema existente es diferente al objeto que va a insertar. Si modifica la tabla agregando esa nueva columna manualmente y luego realiza la operación Insertar, definitivamente insertará todas las columnas junto con la nueva columna a la Tabla. Significa que no hace ningún cambio / altera el esquema / tabla existente.
update
: altera la tabla existente en la base de datos cuando realiza la operación. Puedes agregar o eliminar columnas con esta opción de hbm2ddl. Pero si va a agregar una nueva columna que es ''NOT NULL'', ignorará agregar esa columna en particular a la base de datos. Porque la tabla debe estar vacía si desea agregar una columna ''NO NULA'' a la tabla existente.
Desde 5.0 , ahora puede encontrar esos valores en un Enum
dedicado: org.hibernate.boot.SchemaAutoTooling
(mejorado con el valor NONE
desde 5.2).
O incluso mejor, desde la org.hibernate.tool.schema.Action
5.1 , también puede usar org.hibernate.tool.schema.Action
Enum
que combina JPA 2 y las acciones "heredadas" de DDL de Hibernate.
Pero , todavía no puede configurar un DataSource
programáticamente con esto. Sería mejor usar esto combinado con org.hibernate.cfg.AvailableSettings#HBM2DDL_AUTO
pero el código actual espera un valor de String
(extracto tomado de SessionFactoryBuilderImpl
):
this.schemaAutoTooling = SchemaAutoTooling.interpret( (String) configurationSettings.get( AvailableSettings.HBM2DDL_AUTO ) );
... y los valores de enum
internos de org.hibernate.boot.SchemaAutoTooling
y org.hibernate.tool.schema.Action
no se exponen públicamente.
A continuación, se muestra una configuración de DataSource
programática de ejemplo (utilizada en algunas de mis aplicaciones Spring Boot) que utiliza un gambito gracias a .name().toLowerCase()
pero solo funciona con valores sin guión (por ejemplo, no create-drop
):
@Bean(name = ENTITY_MANAGER_NAME)
public LocalContainerEntityManagerFactoryBean internalEntityManagerFactory(
EntityManagerFactoryBuilder builder,
@Qualifier(DATA_SOURCE_NAME) DataSource internalDataSource) {
Map<String, Object> properties = new HashMap<>();
properties.put(AvailableSettings.HBM2DDL_AUTO, SchemaAutoTooling.CREATE.name().toLowerCase());
properties.put(AvailableSettings.DIALECT, H2Dialect.class.getName());
return builder
.dataSource(internalDataSource)
.packages(JpaModelsScanEntry.class, Jsr310JpaConverters.class)
.persistenceUnit(PERSISTENCE_UNIT_NAME)
.properties(properties)
.build();
}