Spring JPA/HIbernate:重复的键值违反了唯一约束

Spring JPA/HIbernate:重复的键值违反了唯一约束,hibernate,spring-data-jpa,Hibernate,Spring Data Jpa,在现有答案中搜索没有得到有效结果。这就是我找不到原因的错误。 我有一个实体类MeteoRecord和Daydege定义如下: @Getter @塞特 @实体 公共类MeteoRecord扩展了AbstractEntity{ @时态(TemporalType.DATE) 日期; ... //其他属性 } @实体 @吸气剂 @塞特 公共类DayDegree扩展了AbstractEntity{ @许多酮 @JoinColumn(name=“meteo\u record\u id”) 私人气象记录; .

在现有答案中搜索没有得到有效结果。这就是我找不到原因的错误。 我有一个实体类
MeteoRecord
Daydege
定义如下:

@Getter
@塞特
@实体
公共类MeteoRecord扩展了AbstractEntity{
@时态(TemporalType.DATE)
日期;
...
//其他属性
}
@实体
@吸气剂
@塞特
公共类DayDegree扩展了AbstractEntity{
@许多酮
@JoinColumn(name=“meteo\u record\u id”)
私人气象记录;
...
//其他属性
}
所有实体扩展
AbstractEntity
类:

@MappedSuperclass
@吸气剂
@塞特
公共抽象类AbstractEntity实现了可序列化{
@访问权限(AccessType.PROPERTY)
@身份证
@GeneratedValue(策略=GenerationType.IDENTITY)
私人长id;
公共长getId(){
返回id;
}
公共无效集合id(长id){
this.id=id;
}
@CreationTimestamp
@时态(TemporalType.TIMESTAMP)
@列(name=“DATCRE”)
公开日期datcre;
@UpdateTimestamp
@时态(TemporalType.TIMESTAMP)
@列(name=“DATMOD”)
公开日期datmod;
}
保存新的
MeteoRecord
时,如下所示:

可选meteoByDate=meteoRecordRepository.findByDate(dateAsDate);
流星记录;
if(meteoByDate.isPresent()){
meteoRecord=meteoByDate.get();
}否则{
流星记录=新流星记录();
meteoRecord.setDate(dateAsDate);
}
MeteoRecord savedMeteoRecord=meteoRecordRepository.save(MeteoRecord);
...
它引发了一个错误:

rg.postgresql.util.PSQLException: ERROR: duplicate key value violates unique constraint "meteo_record_pkey"
  Detail: Key (id)=(1680) already exists.
“流星定位法”只是扩展了“流星定位法”:

@存储库
公共接口MeteoRecordRepository扩展了JpaRepository{
...
可选findByDate(日期);
}
我激活了更多日志以查看SQL查询,但没有看到其他查询创建新的
MeteoRecord
,也没有在其他地方插入
DayDegree
记录:

11:33:55.664 [http-nio-8080-exec-1] DEBUG org.hibernate.SQL - 
    select
        meteorecor0_.id as id1_33_,
        meteorecor0_.datcre as datcre2_33_,
        meteorecor0_.datmod as datmod3_33_,
        meteorecor0_.date as date4_33_,
        meteorecor0_.degree_day_15 as degree_d5_33_,
        meteorecor0_.degree_day_15_eq as degree_d6_33_,
        meteorecor0_.station as station7_33_,
        meteorecor0_.temp_avg as temp_avg8_33_,
        meteorecor0_.temp_avg_eq as temp_avg9_33_ 
    from
        meteo_record meteorecor0_ 
    where
        meteorecor0_.date=?
Hibernate: 
    select
        meteorecor0_.id as id1_33_,
        meteorecor0_.datcre as datcre2_33_,
        meteorecor0_.datmod as datmod3_33_,
        meteorecor0_.date as date4_33_,
        meteorecor0_.degree_day_15 as degree_d5_33_,
        meteorecor0_.degree_day_15_eq as degree_d6_33_,
        meteorecor0_.station as station7_33_,
        meteorecor0_.temp_avg as temp_avg8_33_,
        meteorecor0_.temp_avg_eq as temp_avg9_33_ 
    from
        meteo_record meteorecor0_ 
    where
        meteorecor0_.date=?
11:33:55.677 [http-nio-8080-exec-1] DEBUG o.s.d.r.c.s.TransactionalRepositoryProxyPostProcessor$CustomAnnotationTransactionAttributeSource - Adding transactional method 'save' with attribute: PROPAGATION_REQUIRED,ISOLATION_DEFAULT
11:33:55.679 [http-nio-8080-exec-1] DEBUG o.s.orm.jpa.JpaTransactionManager - Found thread-bound EntityManager [SessionImpl(1454087429<open>)] for JPA transaction
11:33:55.680 [http-nio-8080-exec-1] DEBUG o.s.orm.jpa.JpaTransactionManager - Creating new transaction with name [org.springframework.data.jpa.repository.support.SimpleJpaRepository.save]: PROPAGATION_REQUIRED,ISOLATION_DEFAULT
11:33:55.680 [http-nio-8080-exec-1] DEBUG o.h.e.t.internal.TransactionImpl - On TransactionImpl creation, JpaCompliance#isJpaTransactionComplianceEnabled == false
11:33:55.680 [http-nio-8080-exec-1] DEBUG o.h.e.t.internal.TransactionImpl - begin
11:33:55.681 [http-nio-8080-exec-1] DEBUG o.s.orm.jpa.JpaTransactionManager - Exposing JPA transaction as JDBC [org.springframework.orm.jpa.vendor.HibernateJpaDialect$HibernateConnectionHandle@27864a10]
11:33:55.696 [http-nio-8080-exec-1] DEBUG org.hibernate.engine.spi.ActionQueue - Executing identity-insert immediately
11:33:55.703 [http-nio-8080-exec-1] DEBUG org.hibernate.SQL - 
    insert 
    into
        meteo_record
        (datcre, datmod, date, degree_day_15, degree_day_15_eq, station, temp_avg, temp_avg_eq) 
    values
        (?, ?, ?, ?, ?, ?, ?, ?)
Hibernate: 
    insert 
    into
        meteo_record
        (datcre, datmod, date, degree_day_15, degree_day_15_eq, station, temp_avg, temp_avg_eq) 
    values
        (?, ?, ?, ?, ?, ?, ?, ?)
11:33:55.732 [http-nio-8080-exec-1] DEBUG o.h.e.jdbc.spi.SqlExceptionHelper - could not execute statement [n/a]
org.postgresql.util.PSQLException: ERROR: duplicate key value violates unique constraint "meteo_record_pkey"
  Detail: Key (id)=(1681) already exists.
11:33:55.664[http-nio-8080-exec-1]DEBUG org.hibernate.SQL-
选择
流星通讯器id为id1\U 33,
Meteolecor0.datcre作为datcre2\u 33,
Meteolecor0。datmod作为datmod3\u 33,
meteorecor0.日期为日期4\u 33\u,
流星星座0度0天15度5度33度,
流星星座0度日15度eq为度6度33度,
meteorecor0站作为7站33站,
meteorecor0平均温度为8平均温度33,
meteorecor0.温度平均值等于温度平均值9\u 33\u
从…起
气象记录
哪里
meteorecor0.date=?
冬眠:
选择
流星通讯器id为id1\U 33,
Meteolecor0.datcre作为datcre2\u 33,
Meteolecor0。datmod作为datmod3\u 33,
meteorecor0.日期为日期4\u 33\u,
流星星座0度0天15度5度33度,
流星星座0度日15度eq为度6度33度,
meteorecor0站作为7站33站,
meteorecor0平均温度为8平均温度33,
meteorecor0.温度平均值等于温度平均值9\u 33\u
从…起
气象记录
哪里
meteorecor0.date=?
11:33:55.677[http-nio-8080-exec-1]调试o.s.d.r.c.s.TransactionalRepositoryProxyPostProcessor$CustomAnnotationTransactionalAttributeSource-添加具有以下属性的事务方法“保存”:传播\必需,隔离\默认
11:33:55.679[http-nio-8080-exec-1]调试o.s.orm.jpa.JpaTransactionManager-找到jpa事务的线程绑定实体管理器[SessionImpl(1454087429)]
11:33:55.680[http-nio-8080-exec-1]调试o.s.orm.jpa.JpaTransactionManager-创建名为[org.springframework.data.jpa.repository.support.simplejpeparepository.save]的新事务:需要传播,默认隔离
11:33:55.680[http-nio-8080-exec-1]调试o.h.e.t.internal.TransactionImpl-在创建TransactionImpl时,JpaCompliance#isJpaTransactionComplianceEnabled==false
11:33:55.680[http-nio-8080-exec-1]调试o.h.e.t.internal.TransactionImpl-开始
11:33:55.681[http-nio-8080-exec-1]调试o.s.orm.jpa.JpaTransactionManager-将jpa事务公开为JDBC[org.springframework.orm.jpa.vendor.HibernateJpaDialect$HibernateConnectionHandle@27864a10]
11:33:55.696[http-nio-8080-exec-1]调试org.hibernate.engine.spi.ActionQueue-立即执行标识插入
11:33:55.703[http-nio-8080-exec-1]调试org.hibernate.SQL-
插入
进入
气象记录
(datcre、datmod、日期、度数、度数、度数、度数、度数、平均值、平均值)
价值观
(?, ?, ?, ?, ?, ?, ?, ?)
冬眠:
插入
进入
气象记录
(datcre、datmod、日期、度数、度数、度数、度数、度数、平均值、平均值)
价值观
(?, ?, ?, ?, ?, ?, ?, ?)
11:33:55.732[http-nio-8080-exec-1]调试o.h.e.jdbc.spi.SqlExceptionHelper-无法执行语句[n/a]
org.postgresql.util.PSQLException:错误:重复的键值违反了唯一约束“meteo_record_pkey”
详细信息:键(id)=(1681)已存在。
我错过了什么?我的印象是,这是因为在
daydege
实体中定义了一个关系,但没有看到对
daydege
实体的查询或使用

谢谢。

根据以下内容:

当我检查表meteo_记录时,当然,总有一条记录 使用错误中指示的id:从meteo_记录mr中选择* 其中mr.id=1678

我可以假设问题在DB中。
Hibernate
不会通过创建新记录来查找记录,但它只需要数据库中的下一个标识。由于它
IDENTITY
它将获得策略的下一个值(+1..或其他值)。现在让我们想象一下,您已经将递增策略定义为递增1,当前值为12。所以很明显,在实体持久化期间,下一个值将是13。但不知何故(例如,通过使用
id
select max(id) + 1 from meteo_record;
ALTER TABLE meteo_record ALTER COLUMN id RESTART WITH x;
CREATE TABLE public.meteo_record (     
    id bigint NOT NULL DEFAULT nextval('meteo_record_id_seq'::regclass),     
    datcre timestamp without time zone,     
    datmod timestamp without time zone,     
    date date,     
    degree_day_15 double precision,     
    degree_day_15_eq double precision,     
    station character varying(255) COLLATE pg_catalog."default",     
    temp_avg double precision,     
    temp_avg_eq double precision,     
    CONSTRAINT meteo_record_pkey PRIMARY KEY (id) 
)
ALTER SEQUENCE meteo_record_id_seq RESTART WITH 1973;