2011-09-28 27 views
6

¿Hay una forma fácil de configurar hibernación para utilizar identificadores de clave primaria diferentes para cada tabla con postgres? He intentado utilizar postgres dialecto en el origen de datos:Hibernate y postgreSQL con Grails

dialect = org.hibernate.dialect.PostgreSQLDialect 
or 
dialect = net.sf.hibernate.dialect.PostgreSQLDialect 

Pero no funciona. Gracias

Respuesta

13

La respuesta corta es no, no hay un fácil forma de hacerlo. Sin embargo, he encontrado una solución que funciona. Básicamente, necesitas implementar un dialecto personalizado. Aquí hay una implementación (tenga en cuenta la fuente original de la implementación dentro de los comentarios).

package com.my.custom; 

import java.util.Properties; 

import org.hibernate.dialect.Dialect; 
import org.hibernate.dialect.PostgreSQLDialect; 
import org.hibernate.id.PersistentIdentifierGenerator; 
import org.hibernate.id.SequenceGenerator; 
import org.hibernate.type.Type; 


/** 
* Creates a sequence per table instead of the default behavior of one sequence. 
* 
* From <a href='http://www.hibernate.org/296.html'>http://www.hibernate.org/296.html</a> 
* @author Burt 
*/ 
public class TableNameSequencePostgresDialect extends PostgreSQLDialect { 

    /** 
    * Get the native identifier generator class. 
    * @return TableNameSequenceGenerator. 
    */ 
    @Override 
    public Class<?> getNativeIdentifierGeneratorClass() { 
      return TableNameSequenceGenerator.class; 
    } 

    /** 
    * Creates a sequence per table instead of the default behavior of one sequence. 
    */ 
    public static class TableNameSequenceGenerator 
      extends SequenceGenerator { 

      /** 
      * {@inheritDoc} 
      * If the parameters do not contain a {@link SequenceGenerator#SEQUENCE} name, we 
      * assign one based on the table name. 
      */ 
      @Override 
      public void configure(
          final Type type, 
          final Properties params, 
          final Dialect dialect) { 
        if (params.getProperty(SEQUENCE) == null 
            || params.getProperty(SEQUENCE).length() == 0) { 
          String tableName = params.getProperty(PersistentIdentifierGenerator.TABLE); 
          if (tableName != null) { 
            params.setProperty(SEQUENCE, "seq_" + tableName); 
          } 
        } 
        super.configure(type, params, dialect); 
      } 
    } 

} 

La aplicación anterior se debe almacenar bajo como TableNameSequencePostgresDialect.javasrc/java/com/my/custom dentro de su proyecto Grails.

A continuación, actualice su DataSource.groovy para usar este nuevo dialecto personalizado.

dialect = com.my.custom.TableNameSequencePostgresDialect 

Eso es todo. No fácil pero se puede hacer.

+0

Muchas gracias. simplemente funciona – Pietro

+0

De nada. Pasé bastante tiempo investigando esto yo mismo y me decepcionó que tuviera que recurrir a una implementación personalizada. Sin embargo, como dijiste, funciona. :) –

+4

Esto fue encontrado en http://grails.1312388.n4.nabble.com/One-hibernate-sequence-is-used-for-all-Postgres-tables-td1351722.html –