A Oracle hibernação problema gerador de sequência
-
16-09-2019 - |
Pergunta
Estou desenvolvendo uma aplicação utilizando o Oracle 11g, Java (struts2) e Hibernate.
Eu tenho tabela chamada mytemp com mytemp_id coluna que é do tipo NUMBER (22,0).
Na minha id arquivo mytemp.hbm.xml é dado abaixo
<id name="mytempId" type="big_decimal">
<column name="MYTEMP_ID" precision="22" scale="0" />
<generator class="sequence">
<param name="sequence">MYTEMP_TEMP_ID_SEQ</param>
</generator>
</id>
Na minha seqüência de banco de dados Oracle com o nome "MYTEMP_TEMP_ID_SEQ" é criado e funcionando bem em Oracle.
Agora, quando eu tentar inserir registro usando hibernate, dá-me seguinte erro
org.hibernate.id.IdentifierGenerationException: este gerador id gera long, integer, short ou string
Parece que a minha seqüência retorna Número, hibenate considerando-a como BigDecimal, enquanto classe gerador sequece de hibernação considerando valores que são longas, integer, short e corda só.
O Hibernate não deve ter problema com BigDecimal. Mas acho que eles não têm implementado BigDecimal para gerador de seqüência
Pode qualquer um ajudar-me resolver o problema?
Graças.
Solução
Para ser honesto com você, eu não posso imaginar por que você insiste em ter seu ID como BigDecimal em vez de comprimento. valor a longo máximo é 9,223,372,036,854,775,807
que, embora se admita que é de cerca de um milésimo do valor máximo NUMBER (22), deve realmente ser o bastante . Se você fosse para gerar um milhões identificadores cada segundo , você teria que fazer isso para 300.000 anos , a fim de esgotar a sua sequência.
Dito isto, a fim de ter o seu identificador gerado como BigDecimal você terá que escrever o seu próprio gerador. Você pode fazer isso através da extensão built-in SequenceGenerator e substituindo seu método generate()
do Hibernate. Em vez de chamar até IdentifierGeneratorFactory.get()
que suporta apenas long / int / short / String que você obter o seu valor de seqüência de conjunto de resultados como BigDecimal.
Você precisará, então, declarar seu gerador especificando o nome completo da classe:
<generator class="com.mypackage.BigDecimalGenerator">
<param name="sequence">MYTEMP_TEMP_ID_SEQ</param>
</generator>
Outras dicas
Você definir o dialeto correto? Isso deve ser suficiente para fazer Hibernate compreender o resultado da seqüência.
[EDIT] O problema é que o tipo de sua seqüência não coincide com o tipo de sua coluna. A seqüência (como por mensagem de erro do Hibernate) pode ser convertido para long, integer, short ou corda enquanto sua seqüência retorna um BigDecimal.
Eu sugiro para especificar o tipo da coluna ID como "longa", mesmo que a Oracle não sabe que tipo. Internamente, o Hibernate deve, então, ser capaz de tudo elenco para todos corretamente.
Com certeza. Longo id deve ser suficiente sempre considerando número de registros exclusivos ele pode gerar. O gerador especial mera ter valores especiais pode ser diferente de inteira tipo ou ter controle sobre o inteira valores de tipo por alguma razão (pode ser específico do projeto).
Além disso, o gerador é específico do banco de dados como sequência para a Oracle, assim definição dialact importa também.