Bonjour,

j'ai un soucis qui me prend un peu le choux

Pour faire simple, j'ai une table en auto increment + une autre table avec foreign key.

Passé une certaine valeur d'auto increment (qui curieusement se situe dans les 65536), l'id généré coté hibernate est négatif. Il est bien positif dans la DB. Résultat, quand hibernate tente de sauver un élément ayant une foreign key, ça finis en ConstraintViolationException, la db lui signifiant que, non, désolé, y a rien à ce numéro...


Je n'arrive pas à comprendre pourquoi hibernate ramène l'id généré à un short. Pour faire simple: le code d'insertion qui tourne en boucle:

Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
em.getTransaction().begin();
        GLOBAL global;
        global = factory.createGlobal();
        em.persist(global);
        em.flush();
        for (int i = 0; i < 20; i++) {
          Log<ID, GLOBAL, COR> log = factory.createLog();
          log.setGlobal(global);
          em.persist(log);
        }
        em.getTransaction().commit();
le global en question et l'id dont il hérite
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
 
@Entity
public class GlobalImpl extends IdImpl implements Global<BigInteger, GlobalImpl, CorImpl> {
....
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
 
@MappedSuperclass
public class IdImpl implements Id<BigInteger> {
  private BigInteger id;
 
  @Override
  @javax.persistence.Id
  @GeneratedValue(strategy = GenerationType.IDENTITY)
  public BigInteger getId() {
    return id;
  }
 
  @Override
  public void setId(BigInteger id) {
    this.id = id;
  }
 
}
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
 
public interface Id<ID> {
 
  public ID getId();
 
  public void setId(ID id);
 
}
la table mariadb
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
 
CREATE TABLE `GlobalImpl` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci
Et le persistence unit tout simple
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
 
    <persistence-unit name="hibernateInteger" transaction-type="RESOURCE_LOCAL">
 
    	<class>com.xxx.entity.pkey.CorImpl</class>
    	<class>com.xxx.entity.pkey.GlobalImpl</class>
    	<class>com.xxx.entity.pkey.LogImpl</class>
    	<exclude-unlisted-classes>true</exclude-unlisted-classes>
    	<properties>
     	    <property name="hibernate.show_sql" value="true"/>
    		<property name="javax.persistence.jdbc.url" value="jdbc:mariadb://***/testAutoincrement"/>
    		<property name="javax.persistence.jdbc.user" value="***"/>
    		<property name="javax.persistence.jdbc.password" value="***"/>
    	</properties>
    </persistence-unit>
L'erreur rapporté par hibernate:

Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
ERROR: Cannot add or update a child row: a foreign key constraint fails (`testAutoincrement`.`LogImpl`, CONSTRAINT `FKns2pbmx0h1qnwv9cxx4cmn2ir` FOREIGN KEY (`global_id`) REFERENCES `GlobalImpl` (`id`))
Query is: insert into LogImpl (global_id) values (?)
Et quand je trace mes erreurs

Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32758 last successful id was 32688 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32764 last successful id was 32697 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32728 last successful id was 32724 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32722 last successful id was 32739 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32737 last successful id was 32712 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32725 last successful id was 32730 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32734 last successful id was 32700 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32752 last successful id was 32694 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32746 last successful id was 32703 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32743 last successful id was 32679 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32740 last successful id was 32718 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32761 last successful id was 32658 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32749 last successful id was 32673 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32731 last successful id was 32742 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32767 last successful id was 32682 -> java.math.BigInteger
insert failed: org.hibernate.exception.ConstraintViolationException: could not execute statement global id was -32755 last successful id was 32706 -> java.math.BigInteger
les ids sont bien des BigInteger comme on voit. Pour chaque thread, on commence à récupérer des ids négatifs.