You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Spring JPA中使用PostgreSQL默认值生成字符串类型UUID

解决JPA + Lombok Builder下数据库自动生成UUID字段的非空约束问题

问题根源

你遇到的问题是因为Lombok Builder创建实体时,publicId字段默认被设为null,JPA会将这个null值显式传入数据库插入语句,而数据库的默认值仅在字段未被显式赋值时才会生效,因此触发了非空约束错误。

以下是几种无需手动设置publicId的解决方案:


方案1:JPA主动生成UUID字符串(推荐)

通过JPA注解让框架在持久化前生成UUID,同时配合Lombok的@Builder.Default确保Builder创建实例时自动填充默认值:

import lombok.Builder;
import lombok.Data;
import jakarta.persistence.*;
import java.util.UUID;

@Entity
@Data
@Builder
public class SomeEntity {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    
    private String name;
    
    @Column(nullable = false, unique = true)
    @GeneratedValue(strategy = GenerationType.UUID)
    @Builder.Default
    private String publicId = UUID.randomUUID().toString();
}
  • @GeneratedValue(strategy = GenerationType.UUID):JPA 2.3+支持直接生成UUID字符串,无需依赖数据库函数
  • @Builder.Default:强制Lombok Builder在未指定publicId时使用该默认值,避免生成null
  • 数据库侧的DEFAULT uuid_generate_v4()可以保留作为兜底,但实际插入时会优先使用JPA生成的值

方案2:依赖数据库默认值,禁止JPA插入该字段

如果希望完全依赖数据库的uuid_generate_v4()生成值,可以设置JPA不将publicId纳入插入语句:

import lombok.Builder;
import lombok.Data;
import jakarta.persistence.*;

@Entity
@Data
@Builder
public class SomeEntity {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    
    private String name;
    
    @Column(
        nullable = false,
        insertable = false,
        columnDefinition = "VARCHAR(36) NOT NULL DEFAULT uuid_generate_v4()"
    )
    private String publicId;
}
  • insertable = false:告诉JPA在生成INSERT语句时不包含public_id字段,数据库会自动使用默认值
  • 注意:此方案下无法通过Builder手动设置publicId(插入时会被忽略),如果需要手动赋值场景,优先选方案1

方案3:自定义Lombok Builder默认逻辑

直接修改Lombok生成的Builder类,让它自动填充publicId:

import lombok.Builder;
import lombok.Data;
import jakarta.persistence.*;
import java.util.UUID;

@Entity
@Data
@Builder
public class SomeEntity {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    
    private String name;
    
    @Column(nullable = false)
    private String publicId;
    
    // 自定义Builder,默认生成UUID
    public static class SomeEntityBuilder {
        private String publicId = UUID.randomUUID().toString();
    }
}

使用时直接调用SomeEntity.builder().name("test").build()即可,publicId会自动生成。


内容的提问来源于stack exchange,提问作者fckNewbee

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 06:46:23